The state_id parameter in the STSUniversalUser
module is used as a key to store or retrieve state information for
each invocation of the trust chain of an OAuth flow.
Advance Access Control provides sample mapping rules. These sample mapping rules use state
management API and are applicable to OAuth 2.0 protocols. We can get the
sample mapping rules from the File downloads
section.
OAuth 2.0
OAuth 2.0 tokens, such as grants,
access tokens, and refresh tokens, have a state_id parameter
used in Security Token Service mapping rules. The state_id parameter
maintains state between associated Security Token Service calls in
an OAuth 2.0 flow.
The OAuth 2.0 mapping rule uses the state_id as
the key to issue an authorization grant. The key is used to add the
token storage time to a cache. The storage time is then retrieved
from the cache during a request for a protected resource.
Figure 1 shows a section of the
sample JavaScript mapping
rule for OAuth 2.0.Figure 1. OAuth
2.0 JavaScript sample
code with state management
...
var request_type = null;
var grant_type = null;
// The request type - if none available assume 'resource'
temp_attr = stsuu.getContextAttributes().getAttributeValuesByNameAndType("request_type", "urn:ibm:names:ITFIM:oauth:request");
if (temp_attr != null && temp_attr.length > 0) {
request_type = temp_attr[0];
} else {
request_type = "resource";
}// The grant type
temp_attr = stsuu.getContextAttributes().getAttributeValuesByNameAndType("grant_type", "urn:ibm:names:ITFIM:oauth:body:param");
if (temp_attr != null && temp_attr.length > 0) {
grant_type = temp_attr[0];
}/* The following demonstrates the use of the state management API.
*
* request_type = 'authorization' ==> Store the UTC time of the request into a cache
with state_id as key [authorization_code, implicit]
* request_type = 'access_token' && grant_type = 'client_credentials' ==> Store the UTC time of the request
into a cache with state_id as key [client_credentials]
* request_type = 'access_token' && grant_type = 'password' ==> Store the UTC time of the request into a cache
with state_id as key [password]
* request_type = 'resource' ==> Retrieve the stored time and put it into an attribute named recovered_state
*
* It also stores the flow type we are in be used later to detect if this is a client_credentials two-legged flow or not.
*/
if (request_type == "authorization" || (request_type == "access_token" &&
( grant_type == "client_credentials" || grant_type == "password" ))) {
var curr_utc_time = "State storage time was: " + IDMappingExtUtils.getCurrentTimeStringUTC();
IDMappingExtUtils.getIDMappingExtCache().put(state_id, curr_utc_time, 1000);
} else if (request_type == "resource") {
var recovered_state = IDMappingExtUtils.getIDMappingExtCache().get(state_id);
if (recovered_state != null) {
var state_arr = java.lang.reflect.Array.newInstance(java.lang.String, 1);
state_arr[0] = recovered_state;
stsuu.addContextAttribute(new Attribute("recovered_state",
"urn:ibm:names:ITFIM:oauth:response:attribute", state_arr));
}}...