Skip to content

Commit 78e48b6

Browse files
committed
Add ManageNameIDResponse-element
1 parent 691bbc8 commit 78e48b6

File tree

4 files changed

+223
-5
lines changed

4 files changed

+223
-5
lines changed
Lines changed: 128 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,128 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace SimpleSAML\SAML2\XML\samlp;
6+
7+
use DOMElement;
8+
use SimpleSAML\SAML2\Assert\Assert;
9+
use SimpleSAML\SAML2\Exception\Protocol\RequestVersionTooHighException;
10+
use SimpleSAML\SAML2\Exception\Protocol\RequestVersionTooLowException;
11+
use SimpleSAML\SAML2\Type\SAMLAnyURIValue;
12+
use SimpleSAML\SAML2\Type\SAMLDateTimeValue;
13+
use SimpleSAML\SAML2\Type\SAMLStringValue;
14+
use SimpleSAML\SAML2\XML\saml\Issuer;
15+
use SimpleSAML\XML\SchemaValidatableElementInterface;
16+
use SimpleSAML\XML\SchemaValidatableElementTrait;
17+
use SimpleSAML\XMLSchema\Exception\InvalidDOMElementException;
18+
use SimpleSAML\XMLSchema\Exception\MissingElementException;
19+
use SimpleSAML\XMLSchema\Exception\TooManyElementsException;
20+
use SimpleSAML\XMLSchema\Type\IDValue;
21+
use SimpleSAML\XMLSchema\Type\NCNameValue;
22+
use SimpleSAML\XMLSecurity\XML\ds\Signature;
23+
24+
use function array_pop;
25+
use function strval;
26+
27+
/**
28+
* Class for SAML 2 ManageNameIDResponse messages.
29+
*
30+
* @package simplesamlphp/saml2
31+
*/
32+
class ManageNameIDResponse extends AbstractStatusResponse implements SchemaValidatableElementInterface
33+
{
34+
use SchemaValidatableElementTrait;
35+
36+
37+
/**
38+
* Constructor for SAML 2 response messages.
39+
*
40+
* @param \SimpleSAML\XMLSchema\Type\IDValue $id
41+
* @param \SimpleSAML\SAML2\XML\samlp\Status $status
42+
* @param \SimpleSAML\SAML2\Type\SAMLDateTimeValue $issueInstant
43+
* @param \SimpleSAML\SAML2\XML\saml\Issuer|null $issuer
44+
* @param \SimpleSAML\XMLSchema\Type\NCNameValue|null $inResponseTo
45+
* @param \SimpleSAML\SAML2\Type\SAMLAnyURIValue|null $destination
46+
* @param \SimpleSAML\SAML2\Type\SAMLAnyURIValue|null $consent
47+
* @param \SimpleSAML\SAML2\XML\samlp\Extensions $extensions
48+
*/
49+
final public function __construct(
50+
IDValue $id,
51+
Status $status,
52+
SAMLDateTimeValue $issueInstant,
53+
?Issuer $issuer = null,
54+
?NCNameValue $inResponseTo = null,
55+
?SAMLAnyURIValue $destination = null,
56+
?SAMLAnyURIValue $consent = null,
57+
?Extensions $extensions = null,
58+
) {
59+
parent::__construct(
60+
$id,
61+
$status,
62+
$issueInstant,
63+
$issuer,
64+
$inResponseTo,
65+
$destination,
66+
$consent,
67+
$extensions,
68+
);
69+
}
70+
71+
72+
/**
73+
* Convert XML into a ManageNameIDResponse element.
74+
*
75+
* @throws \SimpleSAML\XMLSchema\Exception\InvalidDOMElementException
76+
* if the qualified name of the supplied element is wrong
77+
* @throws \SimpleSAML\XMLSchema\Exception\MissingAttributeException
78+
* if the supplied element is missing one of the mandatory attributes
79+
* @throws \SimpleSAML\XMLSchema\Exception\MissingElementException
80+
* if one of the mandatory child-elements is missing
81+
*/
82+
public static function fromXML(DOMElement $xml): static
83+
{
84+
Assert::same($xml->localName, static::getLocalName(), InvalidDOMElementException::class);
85+
Assert::same($xml->namespaceURI, static::NS, InvalidDOMElementException::class);
86+
87+
$version = self::getAttribute($xml, 'Version', SAMLStringValue::class);
88+
Assert::true(version_compare('2.0', strval($version), '<='), RequestVersionTooLowException::class);
89+
Assert::true(version_compare('2.0', strval($version), '>='), RequestVersionTooHighException::class);
90+
91+
$signature = Signature::getChildrenOfClass($xml);
92+
Assert::maxCount($signature, 1, 'Only one ds:Signature element is allowed.', TooManyElementsException::class);
93+
94+
$issuer = Issuer::getChildrenOfClass($xml);
95+
Assert::countBetween($issuer, 0, 1);
96+
97+
$status = Status::getChildrenOfClass($xml);
98+
Assert::minCount($status, 1, MissingElementException::class);
99+
Assert::maxCount($status, 1, TooManyElementsException::class);
100+
101+
$extensions = Extensions::getChildrenOfClass($xml);
102+
Assert::maxCount(
103+
$extensions,
104+
1,
105+
'Only one saml:Extensions element is allowed.',
106+
TooManyElementsException::class,
107+
);
108+
109+
$response = new static(
110+
self::getAttribute($xml, 'ID', IDValue::class),
111+
array_pop($status),
112+
self::getAttribute($xml, 'IssueInstant', SAMLDateTimeValue::class),
113+
empty($issuer) ? null : array_pop($issuer),
114+
self::getOptionalAttribute($xml, 'InResponseTo', NCNameValue::class, null),
115+
self::getOptionalAttribute($xml, 'Destination', SAMLAnyURIValue::class, null),
116+
self::getOptionalAttribute($xml, 'Consent', SAMLAnyURIValue::class, null),
117+
empty($extensions) ? null : array_pop($extensions),
118+
);
119+
120+
if (!empty($signature)) {
121+
$response->setSignature($signature[0]);
122+
$response->messageContainedSignatureUponConstruction = true;
123+
$response->setXML($xml);
124+
}
125+
126+
return $response;
127+
}
128+
}

src/XML/samlp/NameIDMappingResponse.php

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,12 @@
66

77
use DOMElement;
88
use SimpleSAML\SAML2\Assert\Assert;
9-
use SimpleSAML\SAML2\Constants as C;
109
use SimpleSAML\SAML2\Exception\Protocol\RequestVersionTooHighException;
1110
use SimpleSAML\SAML2\Exception\Protocol\RequestVersionTooLowException;
1211
use SimpleSAML\SAML2\Type\SAMLAnyURIValue;
1312
use SimpleSAML\SAML2\Type\SAMLDateTimeValue;
1413
use SimpleSAML\SAML2\Type\SAMLStringValue;
1514
use SimpleSAML\SAML2\XML\IdentifierTrait;
16-
use SimpleSAML\SAML2\XML\saml\Assertion;
17-
use SimpleSAML\SAML2\XML\saml\EncryptedAssertion;
1815
use SimpleSAML\SAML2\XML\saml\EncryptedID;
1916
use SimpleSAML\SAML2\XML\saml\Issuer;
2017
use SimpleSAML\SAML2\XML\saml\NameID;
@@ -27,7 +24,6 @@
2724
use SimpleSAML\XMLSchema\Type\NCNameValue;
2825
use SimpleSAML\XMLSecurity\XML\ds\Signature;
2926

30-
use function array_merge;
3127
use function array_pop;
3228
use function strval;
3329

@@ -82,7 +78,7 @@ final public function __construct(
8278

8379

8480
/**
85-
* Convert XML into a Response element.
81+
* Convert XML into a NameIDMappingResponse element.
8682
*
8783
* @throws \SimpleSAML\XMLSchema\Exception\InvalidDOMElementException
8884
* if the qualified name of the supplied element is wrong
Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace SimpleSAML\Test\SAML2\XML\samlp;
6+
7+
use PHPUnit\Framework\Attributes\CoversClass;
8+
use PHPUnit\Framework\Attributes\Group;
9+
use PHPUnit\Framework\TestCase;
10+
use SimpleSAML\SAML2\Constants as C;
11+
use SimpleSAML\SAML2\Type\SAMLAnyURIValue;
12+
use SimpleSAML\SAML2\Type\SAMLDateTimeValue;
13+
use SimpleSAML\SAML2\Type\SAMLStringValue;
14+
use SimpleSAML\SAML2\XML\saml\Issuer;
15+
use SimpleSAML\SAML2\XML\samlp\AbstractMessage;
16+
use SimpleSAML\SAML2\XML\samlp\AbstractSamlpElement;
17+
use SimpleSAML\SAML2\XML\samlp\AbstractStatusResponse;
18+
use SimpleSAML\SAML2\XML\samlp\ManageNameIDResponse;
19+
use SimpleSAML\SAML2\XML\samlp\Status;
20+
use SimpleSAML\SAML2\XML\samlp\StatusCode;
21+
use SimpleSAML\XML\DOMDocumentFactory;
22+
use SimpleSAML\XML\TestUtils\SchemaValidationTestTrait;
23+
use SimpleSAML\XML\TestUtils\SerializableElementTestTrait;
24+
use SimpleSAML\XMLSchema\Type\IDValue;
25+
use SimpleSAML\XMLSchema\Type\NCNameValue;
26+
use SimpleSAML\XMLSecurity\TestUtils\SignedElementTestTrait;
27+
28+
use function dirname;
29+
use function strval;
30+
31+
/**
32+
* Class \SimpleSAML\SAML2\XML\samlp\ManageNameIDResponseTest
33+
*
34+
* @package simplesamlphp/saml2
35+
*/
36+
#[Group('samlp')]
37+
#[CoversClass(ManageNameIDResponse::class)]
38+
#[CoversClass(AbstractStatusResponse::class)]
39+
#[CoversClass(AbstractMessage::class)]
40+
#[CoversClass(AbstractSamlpElement::class)]
41+
final class ManageNameIDResponseTest extends TestCase
42+
{
43+
use SchemaValidationTestTrait;
44+
use SerializableElementTestTrait;
45+
use SignedElementTestTrait;
46+
47+
48+
/**
49+
*/
50+
public static function setUpBeforeClass(): void
51+
{
52+
self::$testedClass = ManageNameIDResponse::class;
53+
54+
self::$xmlRepresentation = DOMDocumentFactory::fromFile(
55+
dirname(__FILE__, 4) . '/resources/xml/samlp_ManageNameIDResponse.xml',
56+
);
57+
}
58+
59+
60+
/**
61+
*/
62+
public function testMarshalling(): void
63+
{
64+
$status = new Status(
65+
new StatusCode(
66+
SAMLAnyURIValue::fromString(C::STATUS_SUCCESS),
67+
),
68+
);
69+
$issuer = new Issuer(
70+
SAMLStringValue::fromString('https://IdentityProvider.com'),
71+
);
72+
73+
$manageNameIdResponse = new ManageNameIDResponse(
74+
id: IDValue::fromString('abc123'),
75+
status: $status,
76+
issuer: $issuer,
77+
destination: SAMLAnyURIValue::fromString('https://example.org/metadata'),
78+
consent: SAMLAnyURIValue::fromString(C::CONSENT_EXPLICIT),
79+
inResponseTo: NCNameValue::fromString('PHPUnit'),
80+
issueInstant: SAMLDateTimeValue::fromString('2021-03-25T16:53:26Z'),
81+
);
82+
83+
$this->assertEquals(
84+
self::$xmlRepresentation->saveXML(self::$xmlRepresentation->documentElement),
85+
strval($manageNameIdResponse),
86+
);
87+
}
88+
}
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
<samlp:ManageNameIDResponse xmlns:samlp="urn:oasis:names:tc:SAML:2.0:protocol" xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion" Version="2.0" ID="abc123" IssueInstant="2021-03-25T16:53:26Z" Destination="https://example.org/metadata" Consent="urn:oasis:names:tc:SAML:2.0:consent:current-explicit" InResponseTo="PHPUnit">
2+
<saml:Issuer>https://IdentityProvider.com</saml:Issuer>
3+
<samlp:Status>
4+
<samlp:StatusCode Value="urn:oasis:names:tc:SAML:2.0:status:Success"/>
5+
</samlp:Status>
6+
</samlp:ManageNameIDResponse>

0 commit comments

Comments
 (0)