Passed
Pull Request — master (#305)
by Jaime Pérez
02:19
created

AbstractCondition::fromXML()   A

Complexity

Conditions 3
Paths 4

Size

Total Lines 33
Code Lines 23

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 3
eloc 23
c 0
b 0
f 0
nc 4
nop 1
dl 0
loc 33
rs 9.552
1
<?php
2
3
declare(strict_types=1);
4
5
namespace SimpleSAML\SAML2\XML\saml;
6
7
use DOMElement;
8
use SimpleSAML\Assert\Assert;
9
use SimpleSAML\SAML2\Constants as C;
10
use SimpleSAML\SAML2\Utils;
11
use SimpleSAML\SAML2\XML\ExtensionPointInterface;
12
use SimpleSAML\SAML2\XML\ExtensionPointTrait;
13
use SimpleSAML\XML\Chunk;
14
use SimpleSAML\XML\Exception\InvalidDOMElementException;
15
use SimpleSAML\XML\Exception\SchemaViolationException;
16
17
use function count;
18
use function explode;
19
20
/**
21
 * SAML Condition data type.
22
 *
23
 * @package simplesamlphp/saml2
24
 */
25
abstract class AbstractCondition extends AbstractConditionType implements ExtensionPointInterface
26
{
27
    use ExtensionPointTrait;
28
29
    /** @var string */
30
    public const LOCALNAME = 'Condition';
31
32
    /** @var string */
33
    protected string $type;
34
35
36
    /**
37
     * Initialize a custom saml:Condition element.
38
     *
39
     * @param string $type
40
     */
41
    protected function __construct(string $type)
42
    {
43
        $this->type = $type;
44
    }
45
46
47
    /**
48
     * @inheritDoc
49
     */
50
    public function getXsiType(): string
51
    {
52
        return $this->type;
53
    }
54
55
56
    /**
57
     * Convert an XML element into a Condition.
58
     *
59
     * @param \DOMElement $xml The root XML element
60
     * @return \SimpleSAML\SAML2\XML\saml\AbstractCondition The condition
61
     *
62
     * @throws \SimpleSAML\XML\Exception\InvalidDOMElementException if the qualified name of the supplied element is wrong
63
     */
64
    public static function fromXML(DOMElement $xml): object
65
    {
66
        Assert::same($xml->localName, 'Condition', InvalidDOMElementException::class);
67
        Assert::same($xml->namespaceURI, C::NS_SAML, InvalidDOMElementException::class);
68
        Assert::true(
69
            $xml->hasAttributeNS(C::NS_XSI, 'type'),
70
            'Missing required xsi:type in <saml:Condition> element.',
71
            SchemaViolationException::class
72
        );
73
74
        $type = $xml->getAttributeNS(C::NS_XSI, 'type');
75
        Assert::validQName($type, SchemaViolationException::class);
76
77
        $qname = explode(':', $type, 2);
78
        if (count($qname) === 2) {
79
            list($prefix, $element) = $qname;
80
        } else {
81
            $prefix = null;
82
            list($element) = $qname;
83
        }
84
        $ns = $xml->lookupNamespaceUri($prefix);
85
        $handler = Utils::getContainer()->getExtensionHandler($ns, $element);
0 ignored issues
show
Unused Code introduced by
The call to SimpleSAML\SAML2\Compat\...::getExtensionHandler() has too many arguments starting with $element. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

85
        $handler = Utils::getContainer()->/** @scrutinizer ignore-call */ getExtensionHandler($ns, $element);

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress. Please note the @ignore annotation hint above.

Loading history...
86
        if ($handler === null) {
87
            // we don't have a handler, proceed with unknown condition
88
            return new UnknownCondition(new Chunk($xml), $type);
89
        }
90
91
        Assert::subclassOf(
92
            $handler,
93
            AbstractCondition::class,
94
            'Elements implementing Condition must extend \SimpleSAML\SAML2\XML\saml\AbstractCondition.'
95
        );
96
        return $handler::fromXML($xml);
97
    }
98
99
100
    /**
101
     * Convert this Condition to XML.
102
     *
103
     * @param \DOMElement $parent The element we are converting to XML.
104
     * @return \DOMElement The XML element after adding the data corresponding to this Condition.
105
     */
106
    public function toXML(DOMElement $parent = null): DOMElement
107
    {
108
        $e = $this->instantiateParentElement($parent);
109
110
        $e->setAttribute('xmlns:' . static::getXsiTypePrefix(), static::getXsiTypeNamespaceURI());
111
        $e->setAttributeNS(C::NS_XSI, 'xsi:type', $this->getXsiType());
112
113
        return $e;
114
    }
115
}
116