In this document we describe some of the scenarios in which PicketLink STS could be used to enable secure propagation of the client identity (and related attributes) between containers. In other words, we are looking into how PicketLink STS could be used to establish a trust relationship between the client and all the different containers that may be involved in the processing of a complex business logic.
Scenario - client initiated token request
In this scenario, the client authenticates to the STS and acquires a security token before sending a request to the server. The server extracts the security token from the request (or from the request's security context) and invokes the STS to have the token validated. If validation succeeds, the server considers the client authenticated.
In complex processes, an application deployed on one server may need to collaborate with an application deployed on a different server in order to fulfill the client request. If this second server is also part of the trust chain (and thus trusts the STS), then the client's identity can easily be verified by validating the security token with the STS.
How does the client acquire the token?
The client can request a security token by creating and sending a WS-Trust token request message to the STS using the STSClient class. If using JAAS, the client can simplify the whole process by configuring the STSIssuingLoginModule.
How is the token propagated from client to server and between servers?
This depends on the server being used and on the component being called. Web Services requests include the security token in the SOAP header. EJB requests on JBoss can include the token in the security context of the EJB request.
If all servers are JBoss instances, client-side interceptors could be configured to include the security token in the request messages. The servers involved in the request processing would need to configure a STSValidatingLoginModule to have the security token validated.
Besides interceptors and login modules, we may also need a custom Principal. Consider the following scenario: a client uses a SAML assertion to autheticate to Server A and call an EJB on that server. Now, the EJB must call a Web Service on Server B and must programmatically include the client assertion in the SOAP request. How does it obtain the client assertion? If we have a custom Principal that contains the SAML assertion, the code would look like this:
// get the assertion SAMLPrincipal principal = (SAMLPrincipal) this.context.getCallerPrincipal(); Element assertion = principal.getAssertionElement(); // insert the assertion in the request ...
Scenario - server initiated token request
In this scenario, the client authenticates to the server (username/pass, X509, etc) and the server acquires a token on behalf of the client when it needs to invoke operations on other servers. In other words, the client is unaware of the STS and is not part of the trust chain.
As we can see in the figure above, when Server 1 needs to call a component on Server 2, it requests a token on behalf of the client to the STS. The STS trusts the server to have authenticated the client and issues a token for the client. Server 1 then includes the token in the request before invoking an operation on Server 2.
How does Server 1 acquire the token?
In this case, Server 1 is acting as the client of the WS-Trust issue request, so it can either use the API (STSClient) or the STSIssuingLoginModule to obtain the security token. It is important to note that the WS-Trust request MUST contain a OnBehalfOf element that specifies the client principal. This will tell the STS to issue a token for the specified principal (as opposed to the caller, which is Server 1).
How is the token propagated between servers?
Same as the first scenario: depends on the component being called (protocol). Interceptors and custom Principals can be used to insert the token in the request. Validation of the token can be performed via JAAS using the STSValidatingLoginModule.
What needs to be implemented to enable this scenario?
- As of now, PicketLink STS doesn't support OnBehalfOf requests, so this needs to be implemented.
- Interceptors to include the security token in the request.
- Custom Principals to wrap the security tokens and make them accessible to components.