Under Web Browser SSO with the HTTP POST binding, why is a signature over only the <samlp:Response> not enough?
answer
- the binding decides the requirement
- a browser relay is untrusted
- envelope integrity versus portable claim
- MUST under POST, MAY under artifact
- detach it and the envelope proof vanishes
basics
~20 sThe Web Browser SSO profile requires the assertions themselves to be signed when the HTTP POST binding is used. A response-level signature is a statement about one envelope: it does not travel with an assertion and does not stand alone.
solid answer
~50 sSAML draws a distinction candidates routinely flatten. Under the Web Browser SSO profile, assertions in a response **MUST** be signed when the HTTP POST binding is used, and **MAY** be signed when the HTTP-Artifact binding is used. The reason is what carried the message. With HTTP POST the document passes through the user's browser, an untrusted relay, so the assertion needs message-level authenticity of its own. With HTTP-Artifact the service provider resolved a short reference over a direct back-channel call to the identity provider, and that channel already authenticates the source. A signature over the enclosing `<samlp:Response>` does cover its descendants while they stay inside it, so it is not worthless — but it binds the assertion to that one envelope: detach the assertion, relay it, or store it, and the proof is gone. Signing both is common and is what many deployments configure.
code
xml · 19 lines<samlp:Response ID="_r7" Version="2.0" InResponseTo="_q4"
IssueInstant="2026-09-19T10:14:02Z">
<saml:Issuer>https://idp.research-federation.example/idp</saml:Issuer>
<ds:Signature>
<ds:SignedInfo>
<ds:Reference URI="#_r7">
<ds:DigestValue>Rr41ZGlnZXN0b2ZyZXNwb25zZQ==</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
<ds:SignatureValue>Vg8ka2V5c2lnbmF0dXJldmFsdWU=</ds:SignatureValue>
</ds:Signature>
<samlp:Status>
<samlp:StatusCode Value="urn:oasis:names:tc:SAML:2.0:status:Success"/>
</samlp:Status>
<saml:Assertion ID="_a9" Version="2.0" IssueInstant="2026-09-19T10:14:02Z">
<saml:Issuer>https://idp.research-federation.example/idp</saml:Issuer>
<saml:Subject>...</saml:Subject>
</saml:Assertion>
</samlp:Response>go deeper
Recall that a signature can sit on the response or on the assertion, and that those protect different things even though both look like one signed document.
Explain the profile rule and its reason: under HTTP POST the browser relays the document, so the assertion needs authenticity of its own.
Read the failure the other way: a partner tightening its receiver breaks logins from a deployment that only ever signed the envelope, with no change on either side.
Decide the house rule across many counterparties — what you require inbound, what you emit outbound, and what a stricter default costs in integration time.
## Two places a signature can sit A SAML 2.0 response can carry a `<ds:Signature>` at two levels, and they are not the same statement: - **On the `<samlp:Response>`.** The reference names the response's `ID`, so the digest covers the response element and everything nested inside it — including the assertions, while they remain there. The statement is "the issuer of this response assembled exactly this message". - **On each `<saml:Assertion>`.** The reference names the assertion's `ID` and covers that assertion alone. The statement is "the issuer asserts exactly these claims about this subject", and it remains true wherever the assertion afterwards travels. Both are legal. A response may be signed, unsigned, or signed alongside signed assertions. ## What the profile requires, and why the binding decides it The rule is binding-specific, and the reasoning is worth being able to state: | Binding | Assertions in the response | Why | |---|---|---| | HTTP POST | **MUST** be signed | The document is relayed by the user's browser, an untrusted party that can modify what it posts on | | HTTP-Artifact | **MAY** be signed | The service provider fetched the message itself over a direct back-channel call to the identity provider, which authenticates the source at the transport level | So "we sign the response, that is the same thing" is wrong on the profile's own terms when HTTP POST is in use. This also disposes of the broader claim that "SAML assertions are always signed" — the specification is more precise than that, and the precision is exactly what an interviewer probes. ## What a response-level signature does and does not buy It buys real things. While the assertion is inside the signed response, a digest over the response covers it; inserting a fabricated assertion into that digested subtree changes the octets and breaks verification. For a receiver that verifies the response and consumes only from within the element it verified, the integrity property is genuine. What it does not buy: - **Portability.** Detach the assertion — pass it to another component, cache it, forward it, or place it in a different message — and nothing signed accompanies it. An assertion signed in its own right carries its proof with it, which is one reason exclusive canonicalisation exists. - **Independent evidence of authorship.** The proof is about the envelope. Where the responder and the issuer of the claims are different parties, an envelope signature says nothing about who authored those claims. - **Profile conformance under HTTP POST.** A receiver following the profile is entitled to reject a posted response whose assertions are unsigned, and strict implementations do. ## Where deployments actually sit Three configurations show up in production: 1. **Assertion signed only.** Meets the POST-binding rule. The `<samlp:Response>` envelope, including its `<samlp:Status>` and `InResponseTo`, is unprotected, so a receiver must not draw conclusions from unsigned envelope fields. 2. **Response signed only.** Common, and non-conformant under HTTP POST. It is also the configuration that surprises teams when a partner tightens its receiver and logins start failing with no change on their own side. 3. **Both signed.** Two signatures, each with its own single `<ds:Reference>` and its own transforms. The cost is a second signature operation per login and a marginally larger document. A service provider can also publish the expectation: `WantAssertionsSigned` on its `<SPSSODescriptor>` is the declaration that it requires signed assertions, and a partner that ignores it produces exactly the interoperability failure above. ## The question behind the question What an interviewer is really testing is whether the candidate separates "this message arrived intact" from "this claim was made by that issuer". Those are different properties with different lifetimes: the first expires the moment the message is unpacked, the second travels with the assertion. Every deployment argument about what to sign is an argument about which of the two you need — and under HTTP POST the profile has already decided that you need the second.
- If only the assertion is signed, what should a receiver not conclude from the <samlp:Response>?Anything read from the envelope alone. `<samlp:Status>`, `Destination`, `InResponseTo` and the response's own `<saml:Issuer>` are unprotected in that configuration, so a decision turning on them is a decision based on modifiable fields. The trustworthy statements are the ones inside the signed assertion.
- Why does the HTTP-Artifact binding relax the requirement to MAY?Because the service provider does not receive the message from the browser. It receives a short reference and resolves it by calling the identity provider directly over a back-channel connection, which authenticates the source at the transport level. The untrusted relay that makes message-level signing mandatory under HTTP POST is simply not in the path.
- What does a service provider's WantAssertionsSigned declaration express?That this service provider requires the assertions it receives to be signed in their own right, rather than relying on an envelope signature. It is an expectation published to partners; a partner that does not honour it produces logins that fail at the receiver with nothing visibly wrong on the wire.
saying these in an interview costs you the question
- Says SAML assertions are always signed, regardless of binding.
- Thinks signing the <samlp:Response> satisfies the POST-binding rule.
- Treats envelope integrity and issuer-authored claims as one property.
- Trusts unsigned <samlp:Status> when only the assertion is signed.
- Assumes signing both levels is pointless duplication.