在工作中,我们有一个Web应用程序,需要使用经过SAML验证的单点登录与另一家公司的Web应用程序进行接口。我们的Web应用程序是用PHP编写的,显然,另一家公司选择的语言并不重要。尽管如此,我需要编写一个简单的API,让这个其他公司可以向其中发送带有SAML请求的SOAP请求,并生成一个SAML响应返回。我之所以从头开始编写它,有三个原因:1)即使我想要使用SAML交互的选项似乎也不多,2)它限制了添加另一个第三方组件所需的开销,以及3)从头开始创建通常会让我对事物有更好的理解,如果需要的话,也会让我更有能力适应它。
无论如何,我对SAML、SOAP和XML标准都相当陌生,所以我只能边学边做。我已经基本完成了我们的目的的API,唯一的例外是,另一家公司已经指定我们的响应将需要使用证书进行数字签名(我们接收到的请求同样也会被数字签名)。因此,我一直在努力弄清楚如何处理/生成XML签名,但老实说,W3C规范并不是易读的。
在OASIS安全标记语言(SAML)V1.1的声明和协议的第5.4.8节文件中(我一直在使用这个文件,因为另一家公司说他们将使用v1.1),包括一个包含签名断言的签名响应的示例,我将在此处引用以供参考:
<Response IssueInstant="2003-04-17T00:46:02Z" MajorVersion="1" MinorVersion="1"
Recipient="www.opensaml.org" ResponseID="_c7055387-af61-4fce-8b98-e2927324b306"
xmlns="urn:oasis:names:tc:SAML:1.0:protocol"
xmlns:samlp="urn:oasis:names:tc:SAML:1.0:protocol"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
<ds:SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"/>
<ds:Reference URI="#_c7055387-af61-4fce-8b98-e2927324b306">
<ds:Transforms>
<ds:Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
<ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#">
<InclusiveNamespaces PrefixList="#default saml samlp ds xsd xsi"
xmlns="http://www.w3.org/2001/10/xml-exc-c14n#"/>
</ds:Transform>
</ds:Transforms>
<ds:DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
<ds:DigestValue>TCDVSuG6grhyHbzhQFWFzGrxIPE=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
<ds:SignatureValue>x/GyPbzmFEe85pGD3c1aXG4Vspb9V9jGCjwcRCKrtwPS6vdVNCcY5rHaFPYWkf+5EIYcPzx+pX1h43SmwviCqXRjRtMANWbHLhWAptaK1ywS7gFgsD01qjyen3CP+m3Dw6vKhaq1ed10BYyrIzb4KkHO4ahNyBVXbJwqv5pUaE4=</ds:SignatureValue>
<ds:KeyInfo>
<ds:X509Data>
<ds:X509Certificate>MIICyjCCAjOgAwIBAgICAnUwDQYJKoZIhvcNAQEEBQAwgakxCzAJBgNVBAYTA1VT ... 8I3bsbmRAUg4UP9hH6ABVq4KQKMknxu1xQxLhpR1y1GPdiowMNTrEG8cCx3w/w==</ds:X509Certificate>
</ds:X509Data>
</ds:KeyInfo>
</ds:Signature>
<Status><StatusCode Value="samlp:Success"/></Status>
<Assertion AssertionID="_a75adf55-01d7-40cc-929f-dbd8372ebdfc"
IssueInstant="2003-04-17T00:46:02Z" Issuer="www.opensaml.org"
MajorVersion="1" MinorVersion="1" xmlns="urn:oasis:names:tc:SAML:1.0:assertion"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<Conditions NotBefore="2003-04-17T00:46:02Z" NotOnOrAfter="2003-04-17T00:51:02Z">
<AudienceRestrictionCondition>
<Audience>http://www.opensaml.org</Audience>
</AudienceRestrictionCondition>
</Conditions>
<AuthenticationStatement AuthenticationInstant="2003-04-17T00:46:00Z"
AuthenticationMethod="urn:oasis:names:tc:SAML:1.0:am:password">
<Subject>
<NameIdentifier Format="urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress">scott@example.org</NameIdentifier>
<SubjectConfirmation>
<ConfirmationMethod>urn:oasis:names:tc:SAML:1.0:cm:bearer</ConfirmationMethod>
</SubjectConfirmation>
</Subject>
<SubjectLocality IPAddress="127.0.0.1"/>
</AuthenticationStatement>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
<ds:SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"/>
<ds:Reference URI="#_a75adf55-01d7-40cc-929f-dbd8372ebdfc">
<ds:Transforms>
<ds:Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
<ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#">
<InclusiveNamespaces PrefixList="#default saml samlp ds xsd xsi"
xmlns="http://www.w3.org/2001/10/xml-exc-c14n#"/>
</ds:Transform>
</ds:Transforms>
<ds:DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
<ds:DigestValue>Kclet6XcaOgOWXM4gty6/UNdviI=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
<ds:SignatureValue>hq4zk+ZknjggCQgZm7ea8fI79gJEsRy3E8LHDpYXWQIgZpkJN9CMLG8ENR4Nrw+n7iyzixBvKXX8P53BTCT4VghPBWhFTSt9tHWu/AtJfOTh6qaAsNdeCyG86jmtp3TDMWuL/cBUj2OtBZOQMFn7jQ9YB7k1Iz3RqVL+wNmeWI4=</ds:SignatureValue>
<ds:KeyInfo>
<ds:X509Data>
<ds:X509Certificate>MIICyjCCAjOgAwIBAgICAnUwDQYJKoZIhvcNAQEEBQAwgakxCzAJBgNVBAYTA1VT ... 8I3bsbmRAUg4UP9hH6ABVq4KQKMknxu1xQxLhpR1y1GPdiowMNTrEG8cCx3w/w==</ds:X509Certificate>
</ds:X509Data>
</ds:KeyInfo>
</ds:Signature>
</Assertion>
</Response>
那么我该如何生成像这样的东西?如果我收到像这样的东西,该如何验证它?还有人能给出一个基本的概念概述吗?这里的标签是什么?似乎在主要的和中都有两个标签,每个都包含自己的、和(并且各自不同)。这些是如何生成的?你能为此提供任何帮助吗?教程或代码示例将更加感激!但现在,如果你能给我一点方向,那就是我真正想要的。目前,所有这些对我来说似乎仍然是一个大黑盒子。顺便说一下,如果有帮助的话,在SAML 1.1规范的其他地方指出,SAML实现应仅使用“独占规范化”方法(Excl-C14N),并且应仅使用“包含的转换”。我仍然不完全确定这是什么意思。
SignedInfo
中的CanonicalizationMethod
是应用于SignedInfo
元素的,转换中的任何规范化都应用于所引用的内容,因此它们适用于不同的事物,这就是为什么你需要两者的原因。另外,签名内容不需要是XML,因此规范化不一定适用。 - JaakkoK