Skip to content

Commit 59850e8

Browse files
committed
Fix broken min/max calculations on groupRef child elements
1 parent 7f748d3 commit 59850e8

5 files changed

Lines changed: 69 additions & 31 deletions

File tree

src/Documentation/StandardDocumentationReader.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,6 @@ public function get(\DOMElement $node): string
3131
}
3232
$doc = preg_replace('/[\t ]+/', ' ', $doc);
3333

34-
return trim($doc);
34+
return mb_trim($doc);
3535
}
3636
}

src/Schema/Element/GroupRef.php

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -58,12 +58,17 @@ public function getElements(): array
5858
* @var Element|ElementRef|ElementSingle|GroupRef $clonedElement
5959
*/
6060
$clonedElement = clone $element;
61-
if (0 < $this->getMax() || -1 === $this->getMax()) {
62-
$clonedElement->setMax($this->getMax());
61+
62+
$groupMax = $this->getMax();
63+
if (1 !== $groupMax) {
64+
$elementMax = $clonedElement->getMax();
65+
$clonedElement->setMax((-1 === $groupMax || -1 === $elementMax) ? -1 : $groupMax * $elementMax);
6366
}
6467

65-
if (1 < $this->getMin() && 1 === $clonedElement->getMin()) {
66-
$clonedElement->setMin($this->getMin());
68+
$groupMin = $this->getMin();
69+
if (1 !== $groupMin) {
70+
$elementMin = $clonedElement->getMin();
71+
$clonedElement->setMin($groupMin * $elementMin);
6772
}
6873

6974
$elements[$k] = $clonedElement;

src/SchemaReader.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ private function extractErrorMessage(): \Exception
110110
$errors = [];
111111

112112
foreach (libxml_get_errors() as $error) {
113-
$errors[] = sprintf("Error[%s] code %s: %s in '%s' at position %s:%s", $error->level, $error->code, trim($error->message), $error->file, $error->line, $error->column);
113+
$errors[] = sprintf("Error[%s] code %s: %s in '%s' at position %s:%s", $error->level, $error->code, mb_trim($error->message), $error->file, $error->line, $error->column);
114114
}
115115
$e = new \Exception(implode('; ', $errors));
116116
libxml_use_internal_errors(false);
@@ -1244,7 +1244,7 @@ private function loadImport(
12441244

12451245
private function createOrUseSchemaForNs(Schema $schema, string $namespace): Schema
12461246
{
1247-
if ('' !== trim($namespace)) {
1247+
if ('' !== mb_trim($namespace)) {
12481248
$newSchema = new Schema();
12491249
$newSchema->addSchema($this->getGlobalSchema());
12501250
$schema->addSchema($newSchema);

src/Utils/UrlUtils.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ class UrlUtils
88
{
99
public static function resolveRelativeUrl(string $base, string $rel): string
1010
{
11-
if ('' === trim($rel)) {
11+
if ('' === mb_trim($rel)) {
1212
return $base;
1313
}
1414

tests/ElementsTest.php

Lines changed: 56 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ public function testBase(): void
6363
/**
6464
* @dataProvider getGroupCounts
6565
*/
66-
public function testGroupOccurrences($item, $min, $max): void
66+
public function testGroupOccurrences($groupItem, array $groupMinMax, array $elementsMinMax): void
6767
{
6868
$schema = $this->reader->readString(
6969
'
@@ -86,7 +86,10 @@ public function testGroupOccurrences($item, $min, $max): void
8686
8787
<xs:group name="myGroup">
8888
<xs:sequence>
89-
<xs:element name="groupEl1" type="xs:string" />
89+
<xs:element name="nullable" type="xs:string" minOccurs="0" />
90+
<xs:element name="list" type="xs:string" minOccurs="0" maxOccurs="unbounded" />
91+
<xs:element name="scoped" type="xs:string" minOccurs="3" maxOccurs="5" />
92+
<xs:element name="single" type="xs:string" minOccurs="1" maxOccurs="1"/>
9093
</xs:sequence>
9194
</xs:group>
9295
</xs:schema>');
@@ -97,39 +100,69 @@ public function testGroupOccurrences($item, $min, $max): void
97100
$myGroup = $schema->findGroup('myGroup', 'http://www.example.com');
98101
self::assertInstanceOf(Group::class, $myGroup);
99102

100-
$myGroupRef = $myType->getElements()[$item];
103+
$myGroupRef = $myType->getElements()[$groupItem];
101104
self::assertInstanceOf(GroupRef::class, $myGroupRef);
102105

103106
$wrappedEls = $myGroupRef->getElements();
104-
if (-1 === $max || $max > 0) {
105-
self::assertEquals($max, $wrappedEls[0]->getMax());
106-
} else {
107-
self::assertEquals(1, $wrappedEls[0]->getMax());
108-
}
109-
110-
if ($min > 1) {
111-
self::assertEquals($max, $wrappedEls[0]->getMin());
112-
} else {
113-
self::assertEquals(1, $wrappedEls[0]->getMin());
107+
foreach ($wrappedEls as $elementIndex => $element) {
108+
[$elementMin, $elementMax] = $elementsMinMax[$elementIndex];
109+
self::assertEquals($elementMin, $element->getMin(), 'Failed asserting on element index ' . $elementIndex);
110+
self::assertEquals($elementMax, $element->getMax(), 'Failed asserting on element index ' . $elementIndex);
114111
}
115112

116113
self::assertEquals('myGroup', $myGroupRef->getName());
117114

118-
self::assertEquals($min, $myGroupRef->getMin());
119-
self::assertEquals($max, $myGroupRef->getMax());
115+
[$groupMin, $groupMax] = $groupMinMax;
116+
self::assertEquals($groupMin, $myGroupRef->getMin());
117+
self::assertEquals($groupMax, $myGroupRef->getMax());
120118
}
121119

122120
public function getGroupCounts(): array
123121
{
124122
return [
125123
// item, min, max
126-
[0, 1, 1],
127-
[1, 2, 2], // if the min = 2, max must be at least 2
128-
[2, 1, 1],
129-
[3, 1, -1],
130-
[4, 1, 1],
131-
[5, 2, 2],
132-
[6, 1, -1],
124+
[0, [1, 1], [
125+
[0, 1],
126+
[0, -1],
127+
[3, 5],
128+
[1, 1],
129+
]],
130+
[1, [2, 2], [
131+
[0, 2],
132+
[0, -1],
133+
[6, 10],
134+
[2, 2],
135+
]],
136+
[2, [1, 1], [
137+
[0, 1],
138+
[0, -1],
139+
[3, 5],
140+
[1, 1],
141+
]],
142+
[3, [1, -1], [
143+
[0, -1],
144+
[0, -1],
145+
[3, -1],
146+
[1, -1],
147+
]],
148+
[4, [1, 1], [
149+
[0, 1],
150+
[0, -1],
151+
[3, 5],
152+
[1, 1],
153+
]],
154+
[5, [2, 2], [
155+
[0, 2],
156+
[0, -1],
157+
[6, 10],
158+
[2, 2],
159+
]],
160+
[6, [1, -1], [
161+
[0, -1],
162+
[0, -1],
163+
[3, -1],
164+
[1, -1],
165+
]],
133166
];
134167
}
135168

@@ -154,7 +187,7 @@ public function testNotQualifiedTargetQualifiedElement(): void
154187
self::assertFalse($schema->getElementsQualification());
155188

156189
/**
157-
* @var $element ElementSingle
190+
* @var ElementSingle $element
158191
*/
159192
$element = $myType->getElements()[0];
160193
self::assertFalse($element->isQualified());

0 commit comments

Comments
 (0)