Transform   A
last analyzed

Complexity

Total Complexity 11

Size/Duplication

Total Lines 127
Duplicated Lines 0 %

Importance

Changes 3
Bugs 0 Features 0
Metric Value
wmc 11
eloc 42
c 3
b 0
f 0
dl 0
loc 127
rs 10

6 Methods

Rating   Name   Duplication   Size   Complexity  
A getInclusiveNamespaces() 0 3 1
A getXPath() 0 3 1
A getAlgorithm() 0 3 1
A __construct() 0 24 3
A toXML() 0 16 4
A fromXML() 0 20 1
1
<?php
2
3
declare(strict_types=1);
4
5
namespace SimpleSAML\XMLSecurity\XML\ds;
6
7
use DOMElement;
8
use SimpleSAML\Assert\Assert;
9
use SimpleSAML\XML\SchemaValidatableElementInterface;
10
use SimpleSAML\XML\SchemaValidatableElementTrait;
11
use SimpleSAML\XMLSchema\Exception\InvalidDOMElementException;
12
use SimpleSAML\XMLSchema\Exception\TooManyElementsException;
13
use SimpleSAML\XMLSchema\Type\AnyURIValue;
14
use SimpleSAML\XMLSecurity\Constants as C;
15
use SimpleSAML\XMLSecurity\XML\ec\InclusiveNamespaces;
16
use SimpleSAML\XPath\Constants as XPATH_C;
17
18
use function array_pop;
19
use function strval;
20
21
/**
22
 * Class representing transforms.
23
 *
24
 * @package simplesamlphp/xml-security
25
 */
26
class Transform extends AbstractDsElement implements SchemaValidatableElementInterface
27
{
28
    use SchemaValidatableElementTrait;
0 ignored issues
show
introduced by
The trait SimpleSAML\XML\SchemaValidatableElementTrait requires some properties which are not provided by SimpleSAML\XMLSecurity\XML\ds\Transform: $message, $line
Loading history...
29
30
31
    /**
32
     * Initialize the Transform element.
33
     *
34
     * @param \SimpleSAML\XMLSchema\Type\AnyURIValue $algorithm
35
     * @param \SimpleSAML\XMLSecurity\XML\ds\XPath|null $xpath
36
     * @param \SimpleSAML\XMLSecurity\XML\ec\InclusiveNamespaces|null $inclusiveNamespaces
37
     */
38
    final public function __construct(
39
        protected AnyURIValue $algorithm,
40
        protected ?XPath $xpath = null,
41
        protected ?InclusiveNamespaces $inclusiveNamespaces = null,
42
    ) {
43
        if ($xpath !== null) {
44
            Assert::nullOrEq(
45
                $algorithm->getValue(),
46
                XPATH_C::XPATH10_URI,
47
                sprintf('Transform algorithm "%s" required if XPath provided.', XPATH_C::XPATH10_URI),
48
            );
49
        }
50
51
        if ($inclusiveNamespaces !== null) {
52
            Assert::oneOf(
53
                $algorithm->getValue(),
54
                [
55
                    C::C14N_INCLUSIVE_WITH_COMMENTS,
56
                    C::C14N_EXCLUSIVE_WITHOUT_COMMENTS,
57
                ],
58
                sprintf(
59
                    'Transform algorithm "%s" or "%s" required if InclusiveNamespaces provided.',
60
                    C::C14N_EXCLUSIVE_WITH_COMMENTS,
61
                    C::C14N_EXCLUSIVE_WITHOUT_COMMENTS,
62
                ),
63
            );
64
        }
65
    }
66
67
68
    /**
69
     * Get the algorithm associated with this transform.
70
     *
71
     * @return \SimpleSAML\XMLSchema\Type\AnyURIValue
72
     */
73
    public function getAlgorithm(): AnyURIValue
74
    {
75
        return $this->algorithm;
76
    }
77
78
79
    /**
80
     * Get the XPath associated with this transform.
81
     *
82
     * @return \SimpleSAML\XMLSecurity\XML\ds\XPath|null
83
     */
84
    public function getXPath(): ?XPath
85
    {
86
        return $this->xpath;
87
    }
88
89
90
    /**
91
     * Get the InclusiveNamespaces associated with this transform.
92
     *
93
     * @return \SimpleSAML\XMLSecurity\XML\ec\InclusiveNamespaces|null
94
     */
95
    public function getInclusiveNamespaces(): ?InclusiveNamespaces
96
    {
97
        return $this->inclusiveNamespaces;
98
    }
99
100
101
    /**
102
     * Convert XML into a Transform element.
103
     *
104
     * @param \DOMElement $xml The XML element we should load.
105
     * @return static
106
     */
107
    public static function fromXML(DOMElement $xml): static
108
    {
109
        Assert::same($xml->localName, 'Transform', InvalidDOMElementException::class);
110
        Assert::same($xml->namespaceURI, Transform::NS, InvalidDOMElementException::class);
111
112
        $xpath = XPath::getChildrenOfClass($xml);
113
        Assert::maxCount($xpath, 1, 'Only one XPath element supported per Transform.', TooManyElementsException::class);
114
115
        $prefixes = InclusiveNamespaces::getChildrenOfClass($xml);
116
        Assert::maxCount(
117
            $prefixes,
118
            1,
119
            'Only one InclusiveNamespaces element supported per Transform.',
120
            TooManyElementsException::class,
121
        );
122
123
        return new static(
124
            self::getAttribute($xml, 'Algorithm', AnyURIValue::class),
125
            array_pop($xpath),
126
            array_pop($prefixes),
127
        );
128
    }
129
130
131
    /**
132
     * Convert this Transform element to XML.
133
     *
134
     * @param \DOMElement|null $parent The element we should append this Transform element to.
135
     * @return \DOMElement
136
     */
137
    public function toXML(?DOMElement $parent = null): DOMElement
138
    {
139
        $e = $this->instantiateParentElement($parent);
140
        $e->setAttribute('Algorithm', strval($this->getAlgorithm()));
141
142
        switch ($this->getAlgorithm()) {
143
            case XPATH_C::XPATH10_URI:
144
                $this->getXPath()?->toXML($e);
145
                break;
146
            case C::C14N_EXCLUSIVE_WITH_COMMENTS:
147
            case C::C14N_EXCLUSIVE_WITHOUT_COMMENTS:
148
                $this->getInclusiveNamespaces()?->toXML($e);
149
                break;
150
        }
151
152
        return $e;
153
    }
154
}
155