Schema::addAttributeGroup()   A
last analyzed

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 1
dl 0
loc 3
ccs 2
cts 2
cp 1
crap 1
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace GoetasWebservices\XML\XSDReader\Schema;
6
7
use GoetasWebservices\XML\XSDReader\Schema\Attribute\AttributeDef;
8
use GoetasWebservices\XML\XSDReader\Schema\Attribute\AttributeItem;
9
use GoetasWebservices\XML\XSDReader\Schema\Attribute\Group as AttributeGroup;
10
use GoetasWebservices\XML\XSDReader\Schema\Element\ElementDef;
11
use GoetasWebservices\XML\XSDReader\Schema\Element\ElementItem;
12
use GoetasWebservices\XML\XSDReader\Schema\Element\Group;
13
use GoetasWebservices\XML\XSDReader\Schema\Exception\SchemaException;
14
use GoetasWebservices\XML\XSDReader\Schema\Exception\TypeNotFoundException;
15
use GoetasWebservices\XML\XSDReader\Schema\Type\Type;
16
17
class Schema
18
{
19
    /**
20
     * @param bool[] $calling
21
     */
22 74
    protected function findSomethingNoThrow(
23
        string $getter,
24
        string $name,
25
        string $namespace = null,
26
        array &$calling = []
27
    ): ?SchemaItem {
28 74
        $calling[spl_object_hash($this)] = true;
29 74
        $cid = "$getter, $name, $namespace";
30
31 74
        if (isset($this->typeCache[$cid])) {
32 74
            return $this->typeCache[$cid];
33
        } elseif (
34 74
            $this->getTargetNamespace() === $namespace
35
        ) {
36
            /**
37
             * @var SchemaItem|null
38
             */
39 74
            $item = $this->$getter($name);
40
41 74
            if ($item instanceof SchemaItem) {
42 74
                return $this->typeCache[$cid] = $item;
43
            }
44
        }
45
46 74
        return $this->findSomethingNoThrowSchemas(
47 74
            $this->getSchemas(),
48 74
            $cid,
49 74
            $getter,
50 74
            $name,
51 74
            $namespace,
52 74
            $calling
53
        );
54
    }
55
56
    /**
57
     * @param Schema[] $schemas
58
     * @param bool[]   $calling
59
     */
60 74
    protected function findSomethingNoThrowSchemas(
61
        array $schemas,
62
        string $cid,
63
        string $getter,
64
        string $name,
65
        string $namespace = null,
66
        array &$calling = []
67
    ): ?SchemaItem {
68 74
        foreach ($schemas as $childSchema) {
69 74
            if (!isset($calling[spl_object_hash($childSchema)])) {
70
                /**
71
                 * @var SchemaItem|null
72
                 */
73 74
                $in = $childSchema->findSomethingNoThrow($getter, $name, $namespace, $calling);
74
75 74
                if ($in instanceof SchemaItem) {
76 74
                    return $this->typeCache[$cid] = $in;
77
                }
78
            }
79
        }
80
81 12
        return null;
82
    }
83
84
    /**
85
     * @param array<mixed> $calling
86
     *
87
     * @throws TypeNotFoundException
88
     */
89 74
    protected function findSomething(string $getter, string $name, string $namespace = null, array &$calling = []): SchemaItem
90
    {
91 74
        $in = $this->findSomethingNoThrow(
92 74
            $getter,
93 74
            $name,
94 74
            $namespace,
95 74
            $calling
96
        );
97
98 74
        if ($in instanceof SchemaItem) {
99 74
            return $in;
100
        }
101
102 6
        throw new TypeNotFoundException(sprintf("Can't find the %s named {%s}#%s.", substr($getter, 3), $namespace, $name));
103
    }
104
105
    /**
106
     * @var bool
107
     */
108
    protected $elementsQualification = false;
109
110
    /**
111
     * @var bool
112
     */
113
    protected $attributesQualification = false;
114
115
    /**
116
     * @var string|null
117
     */
118
    protected $targetNamespace;
119
120
    /**
121
     * @var Schema[]
122
     */
123
    protected $schemas = [];
124
125
    /**
126
     * @var Type[]
127
     */
128
    protected $types = [];
129
130
    /**
131
     * @var ElementDef[]
132
     */
133
    protected $elements = [];
134
135
    /**
136
     * @var Group[]
137
     */
138
    protected $groups = [];
139
140
    /**
141
     * @var AttributeGroup[]
142
     */
143
    protected $attributeGroups = [];
144
145
    /**
146
     * @var AttributeDef[]
147
     */
148
    protected $attributes = [];
149
150
    /**
151
     * @var string|null
152
     */
153
    protected $doc;
154
155
    /**
156
     * @var \GoetasWebservices\XML\XSDReader\Schema\SchemaItem[]
157
     */
158
    protected $typeCache = [];
159
160 1
    public function getElementsQualification(): bool
161
    {
162 1
        return $this->elementsQualification;
163
    }
164
165 74
    public function setElementsQualification(bool $elementsQualification): void
166
    {
167 74
        $this->elementsQualification = $elementsQualification;
168 74
    }
169
170
    public function getAttributesQualification(): bool
171
    {
172
        return $this->attributesQualification;
173
    }
174
175 74
    public function setAttributesQualification(bool $attributesQualification): void
176
    {
177 74
        $this->attributesQualification = $attributesQualification;
178 74
    }
179
180 74
    public function getTargetNamespace(): ?string
181
    {
182 74
        return $this->targetNamespace;
183
    }
184
185 74
    public function setTargetNamespace(?string $targetNamespace): void
186
    {
187 74
        $this->targetNamespace = $targetNamespace;
188 74
    }
189
190
    /**
191
     * @return Type[]
192
     */
193 6
    public function getTypes(): array
194
    {
195 6
        return $this->types;
196
    }
197
198
    /**
199
     * @return ElementDef[]
200
     */
201 4
    public function getElements(): array
202
    {
203 4
        return $this->elements;
204
    }
205
206
    /**
207
     * @return Schema[]
208
     */
209 74
    public function getSchemas(): array
210
    {
211 74
        return $this->schemas;
212
    }
213
214
    /**
215
     * @return AttributeDef[]
216
     */
217 1
    public function getAttributes(): array
218
    {
219 1
        return $this->attributes;
220
    }
221
222
    /**
223
     * @return Group[]
224
     */
225 2
    public function getGroups(): array
226
    {
227 2
        return $this->groups;
228
    }
229
230
    public function getDoc(): ?string
231
    {
232
        return $this->doc;
233
    }
234
235 74
    public function setDoc(string $doc): void
236
    {
237 74
        $this->doc = $doc;
238 74
    }
239
240 74
    public function addType(Type $type): void
241
    {
242 74
        $this->types[(string) $type->getName()] = $type;
243 74
    }
244
245 74
    public function addElement(ElementDef $element): void
246
    {
247 74
        $this->elements[$element->getName()] = $element;
248 74
    }
249
250 74
    public function addSchema(self $schema, string $namespace = null): void
251
    {
252 74
        if ($namespace === null) {
253 74
            $this->schemas[] = $schema;
254
255 74
            return;
256
        }
257
258 74
        if ($schema->getTargetNamespace() !== $namespace) {
259
            throw new SchemaException(sprintf("The target namespace ('%s') for schema, does not match the declared namespace '%s'", $schema->getTargetNamespace(), $namespace));
260
        }
261
262 74
        if (isset($this->schemas[$namespace])) {
263 1
            $this->schemas[$namespace]->addSchema($schema);
264
265 1
            return;
266
        }
267
268 74
        $this->schemas[$namespace] = $schema;
269 74
    }
270
271 74
    public function addAttribute(AttributeDef $attribute): void
272
    {
273 74
        $this->attributes[$attribute->getName()] = $attribute;
274 74
    }
275
276 74
    public function addGroup(Group $group): void
277
    {
278 74
        $this->groups[$group->getName()] = $group;
279 74
    }
280
281 74
    public function addAttributeGroup(AttributeGroup $group): void
282
    {
283 74
        $this->attributeGroups[$group->getName()] = $group;
284 74
    }
285
286
    /**
287
     * @return AttributeGroup[]
288
     */
289 1
    public function getAttributeGroups(): array
290
    {
291 1
        return $this->attributeGroups;
292
    }
293
294 74
    public function getGroup(string $name): ?Group
295
    {
296 74
        if (isset($this->groups[$name])) {
297 74
            return $this->groups[$name];
298
        }
299
300
        return null;
301
    }
302
303 74
    public function getElement(string $name): ?ElementItem
304
    {
305 74
        if (isset($this->elements[$name])) {
306 74
            return $this->elements[$name];
307
        }
308
309 1
        return null;
310
    }
311
312 74
    public function getType(string $name): ?Type
313
    {
314 74
        if (isset($this->types[$name])) {
315 74
            return $this->types[$name];
316
        }
317
318 1
        return null;
319
    }
320
321 74
    public function getAttribute(string $name): ?AttributeItem
322
    {
323 74
        if (isset($this->attributes[$name])) {
324 74
            return $this->attributes[$name];
325
        }
326
327
        return null;
328
    }
329
330 74
    public function getAttributeGroup(string $name): ?AttributeGroup
331
    {
332 74
        if (isset($this->attributeGroups[$name])) {
333 74
            return $this->attributeGroups[$name];
334
        }
335
336
        return null;
337
    }
338
339
    public function __toString(): string
340
    {
341
        return sprintf('Target namespace %s', $this->getTargetNamespace());
342
    }
343
344 74
    public function findType(string $name, string $namespace = null): Type
345
    {
346 74
        $out = $this->findSomething('getType', $name, $namespace);
347
348 74
        if (!($out instanceof Type)) {
349
            throw new TypeNotFoundException(sprintf("Can't find the %s named {%s}#%s.", 'Type', $namespace, $name));
350
        }
351
352 74
        return $out;
353
    }
354
355 74
    public function findGroup(string $name, string $namespace = null): Group
356
    {
357 74
        $out = $this->findSomething('getGroup', $name, $namespace);
358
359 74
        if (!($out instanceof Group)) {
360
            throw new TypeNotFoundException(sprintf("Can't find the %s named {%s}#%s.", 'Group', $namespace, $name));
361
        }
362
363 74
        return $out;
364
    }
365
366 74
    public function findElement(string $name, string $namespace = null): ElementDef
367
    {
368 74
        $out = $this->findSomething('getElement', $name, $namespace);
369
370 74
        if (!($out instanceof ElementDef)) {
371
            throw new TypeNotFoundException(sprintf("Can't find the %s named {%s}#%s.", 'Element', $namespace, $name));
372
        }
373
374 74
        return $out;
375
    }
376
377 74
    public function findAttribute(string $name, string $namespace = null): AttributeItem
378
    {
379 74
        $out = $this->findSomething('getAttribute', $name, $namespace);
380
381 74
        if (!($out instanceof AttributeItem)) {
382
            throw new TypeNotFoundException(sprintf("Can't find the %s named {%s}#%s.", 'Attribute', $namespace, $name));
383
        }
384
385 74
        return $out;
386
    }
387
388 74
    public function findAttributeGroup(string $name, string $namespace = null): AttributeGroup
389
    {
390 74
        $out = $this->findSomething('getAttributeGroup', $name, $namespace);
391
392 74
        if (!($out instanceof AttributeGroup)) {
393
            throw new TypeNotFoundException(sprintf("Can't find the %s named {%s}#%s.", 'AttributeGroup', $namespace, $name));
394
        }
395
396 74
        return $out;
397
    }
398
}
399