IDPProxyUtil.java revision 31995e9edcce4393cdab93d80f27d5ab54ff5264
/**
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright (c) 2007 Sun Microsystems Inc. All Rights Reserved
*
* The contents of this file are subject to the terms
* of the Common Development and Distribution License
* (the License). You may not use this file except in
* compliance with the License.
*
* You can obtain a copy of the License at
* See the License for the specific language governing
* permission and limitations under the License.
*
* When distributing Covered Code, include this CDDL
* Header Notice in each file and include the License file
* at opensso/legal/CDDLv1.0.txt.
* If applicable, add the following below the CDDL Header,
* with the fields enclosed by brackets [] replaced by
* your own identifying information:
* "Portions Copyrighted [year] [name of copyright owner]"
*
* $Id: IDPProxyUtil.java,v 1.18 2009/11/20 21:41:16 exu Exp $
*
* Portions Copyrighted 2010-2015 ForgeRock AS.
*/
/**
* Utility class to be used for IDP Proxying.
*/
public class IDPProxyUtil {
// IDP proxy finder
// private static SAML2IDPFinder proxyFinder = null;
static {
try {
sm = new SAML2MetaManager();
}
}
/**
* Gets the preferred IDP Id to be proxied. This method makes use of an
* SPI to determine the preferred IDP.
* @param authnRequest original Authn Request.
* @param hostedEntityId hosted provider ID
* @param realm Realm
* @param request HttpServletRequest
* @param response HttpServletResponse
* @exception SAML2Exception for any SAML2 failure.
* @return String Provider id of the preferred IDP to be proxied.
*/
public static String getPreferredIDP(
throws SAML2Exception
{
return null;
}
}
/**
* Sends a new AuthnRequest to the authenticating provider.
* @param authnRequest original AuthnRequest sent by the service provider.
* @param preferredIDP IDP to be proxied.
* @param spSSODescriptor SPSSO Descriptor Element
* @param hostedEntityId hosted provider ID
* @param request HttpServletRequest
* @param response HttpServletResponse
* @param realm Realm
* @param relayState the Relay State
* @param originalBinding The binding used to send the original AuthnRequest.
* @exception SAML2Exception for any SAML2 failure.
* @exception IOException if there is a failure in redirection.
*/
public static void sendProxyAuthnRequest(
throws SAML2Exception, IOException {
try {
}
} catch (SAML2MetaException e) {
throw new SAML2Exception(e.getMessage());
}
AuthnRequest newAuthnRequest = getNewAuthnRequest(hostedEntityId, destination, realm, authnRequest);
// invoke SP Adapter class if registered
spAdapter.preSingleSignOnRequest(hostedEntityId, preferredIDP, realm, request, response, newAuthnRequest);
}
SAML2Utils.debug.message(classMethod + "New Authentication request:" + newAuthnRequest.toXMLString());
}
// save the AuthnRequest in the IDPCache so that it can be
// retrieved later when the user successfully authenticates
// save the original AuthnRequest
boolean signingNeeded = idpDescriptor.isWantAuthnRequestsSigned() || localDescriptor.isAuthnRequestsSigned();
// check if relayState is present and get the unique
// id which will be appended to the SSO URL before
// redirecting
authnRequest.getID());
}
if (signingNeeded) {
}
} else {
}
.append(encodedXML);
//TODO: should it be newAuthnRequest???
.append("=")
}
if (signingNeeded) {
} else {
}
}
null);
synchronized(SPCache.requestHash) {
}
if (SAML2FailoverUtils.isSAML2FailoverEnabled()) {
try {
// sessionExpireTime is counted in seconds
SAML2FailoverUtils.saveSAML2TokenWithoutSecondaryKey(requestID, new AuthnRequestInfoCopy(reqInfo), sessionExpireTime);
}
} catch(SAML2TokenRepositoryException se) {
}
}
}
private static SingleSignOnServiceElement getMatchingSSOEndpoint(List<SingleSignOnServiceElement> endpoints,
boolean isFirst = true;
if (isFirst) {
//If there is no match, we should use the first endpoint in the list
isFirst = false;
}
break;
}
}
return preferredEndpoint;
}
/**
* Constructs new authentication request by using the original request
* that is sent by the service provider to the proxying IDP.
* @param hostedEntityId hosted provider ID
* @param destination The destination where the new AuthnRequest will be sent to.
* @param realm Realm
* @param origRequest Original Authn Request
* @return AuthnRequest new authn request.
* @exception SAML2Exception for failure in creating new authn request.
* @return AuthnRequest object
*/
private static AuthnRequest getNewAuthnRequest(String hostedEntityId, String destination, String realm,
// New Authentication request should only be a single sign-on request.
try {
}
SPSSODescriptorElement localDescriptor = IDPSSOUtil.metaManager.getSPSSODescriptor(realm, hostedEntityId);
if (origNameIDPolicy != null) {
}
int proxyCount = 1;
if (proxyCountInt != null) {
}
} else {
//handling the alwaysIdpProxy case -> the incoming request
//did not contained a Scoping field
if (proxyCount <= 0) {
} else {
//since this is a remote SP configuration, we should
//decrement the proxycount by one
}
}
}
}
}
return newRequest;
"Error in creating new authn request.", ex);
throw new SAML2Exception(ex);
}
}
/**
* Checks if the identity provider is configured for proxying the
* authentication requests for a requesting service provider.
* @param authnRequest Authentication Request.
* @param realm Realm
* @return <code>true</code> if the IDP is configured for proxying.
* @exception SAML2Exception for any failure.
*/
throws SAML2Exception
{
//let's check if always IdP proxy and IdP Proxy itself is enabled
return true;
}
}
return false;
}
int proxyCount = 0;
if (proxyCountInt == null) {
//Proxy count missing, IDP Proxy allowed
proxyCount = 1;
} else {
}
if (proxyCount <= 0) {
return false;
}
spConfig =
}
if (enabledString == null) {
return false;
}
return (enabledString.booleanValue());
}
/**
* Checks if the proxying is enabled. It will be checking if the proxy
* service provider descriptor is set in the session manager for the
* specific request ID.
* @param requestID authentication request id which is created by the
* proxying IDP to the authenticating IDP.
* @return true if the proxying is enabled.
*/
}
/**
* Sends the proxy authentication response to the proxying service
* provider which has originally requested for the authentication.
* @param request HttpServletRequest
* @param response HttpServletResponse
* @param out the print writer for writing out presentation
* @param requestID request ID
* @param idpMetaAlias meta Alias
* @param newSession Session object
* @throws SAML2Exception for any SAML2 failure.
*/
private static void sendProxyResponse(
throws SAML2Exception
{
try {
"toString(): Failed.", ex);
}
}
+ ":Original requesting service provider id:"
+ proxySPEntityId);
}
// Save the SP provider id based on the token id
IDPCache.spSessionPartnerBySessionID.put(sessionProvider.getSessionID(newSession), proxySPEntityId);
//TODO: set AuthnContext
/*AuthnContext authnContextStm;
if (authnContextStmt != null) {
String authnContext = authnContextStmt.getAuthnContextClassRef();
session.setAuthnContext(authnContext);
}*/
out,
}
/**
* Sends back a NoPassive response for the original AuthnRequest.
*
* @param request The request.
* @param response The response.
* @param requestID The requestID of the proxied AuthnRequest.
* @param idpMetaAlias The IdP's metaAlias.
* @param hostEntityID The IdP's entity ID.
* @param realm The realm where the IdP belongs to.
* @throws SAML2Exception If there was an error while sending the NoPassive response.
*/
public static void sendNoPassiveProxyResponse(HttpServletRequest request, HttpServletResponse response,
}
/**
* Generates the AuthnResponse by the IDP Proxy and send to the
* service provider.
* @param request HttpServletRequest
* @param response HttpServletResponse
* @param out the print writer for writing out presentation
* @param metaAlias meta Alias
* @param respInfo ResponseInfo object
* @param newSession Session object
* @exception SAML2Exception for any SAML2 failure.
*/
public static void generateProxyResponse(
throws SAML2Exception
{
//if (isIDPProxyEnabled(requestID)) {
}
return ;
// }
}
{
return null;
}
return null;
}
return null;
}
return null;
}
return format;
}
/**
* Initiates the Single logout request by the IDP Proxy to the
* authenticating identity provider.
* @param request HttpServletRequest
* @param response HttpServletResponse
* @param partner Authenticating identity provider
* @param spMetaAlias IDP proxy's meta alias acting as SP
* @param realm Realm
*/
public static void initiateSPLogoutRequest(
)
{
try {
"nullSSOToken",
return;
}
}
}
} else {
throw new SAML2Exception(
"sloResponseServiceLocationNotfound"));
}
if (relayState != null) {
}
} catch (SAML2Exception sse) {
try {
"LogoutRequestCreationError",
"LogoutRequestCreationError"));
"initiateSPLogoutRequest: ", se);
}
return ;
} catch (Exception e) {
try {
"LogoutRequestCreationError",
"LogoutRequestCreationError"));
"initiateSPLogoutRequest: ", mme);
}
return;
}
}
/**
* Gets the SLO response service location of the authenticating
* identity provider
* @param realm Realm
* @param idpEntityID authenticating identity provider.
* @return location URL of the SLO response service, return null
* if not found.
*/
{
try {
// get IDPSSODescriptor
null);
throw new SAML2Exception(
}
null);
throw new SAML2Exception(
}
location);
}
return location;
} catch (SAML2Exception se) {
return null;
}
}
{
try {
idpSession = (IDPSession)
}
if (idpSession != null) {
}
"SESSION PARTNER's Provider ID: "
+ partner.getPartner());
}
}
}
}
return partners;
} catch (SessionException se) {
return null;
}
}
public static void sendProxyLogoutRequest(
{
try {
idpSession = (IDPSession)
}
"CURRENT PARTNER's provider ID: " +
partner.getPartner());
}
if (idpSession != null) {
}
} catch (SessionException se) {
"sendProxyLogoutRequest: ", se);
}
}
public static void sendProxyLogoutResponse(
}
}
realm = "/";
}
}
String location = IDPSingleLogout.getSingleLogoutLocation(remoteEntity, realm, SAML2Constants.HTTP_REDIRECT);
}
}
public static void sendProxyLogoutRequestSOAP(
{
"CURRENT PARTNER's provider ID: " +
partner.getPartner());
}
}
try {
"LogoutRequest");
int numSI = 0;
if (debug.messageEnabled()) {
"Number of session indices in the logout request is "
+ numSI);
}
"SessionIndex= " + sessionIndex);
}
if (idpSession == null) {
// session is in another server
return sessMap;
}
if (newIdpSession != null) {
}
"SESSION PARTNER's Provider ID: "
+ partner.getPartner());
}
}
}
}
return sessMap;
} else {
"session indices in the logout request is null");
}
return null;
}
} catch (SAML2Exception se) {
return null;
}
}
public static void sendProxyLogoutResponseBySOAP(
{ try {
// Need to call saveChanges because we're
// going to use the MimeHeaders to set HTTP
// response information. These MimeHeaders
// are generated as part of the save.
if (reply.saveRequired()) {
reply.saveChanges();
}
// Write out the message on the response stream
} catch (SOAPException se) {
} catch (IOException ie) {
}
}
public static void sendIDPInitProxyLogoutRequest(
if (logoutResponse != null) {
}
}
}
}
}
/*TODO:
if (binding.equalsIgnoreCase(SAML2Constants.SOAP)) {
if (RelayState != null) {
response.sendRedirect(RelayState);
} else {
%>
<jsp:forward
page="/saml2/jsp/default.jsp?message=idpSloSuccess" />
<%
}
}
*/
}
{
try {
}
"SP SESSION PARTNER's Provider ID: " + pid);
}
return partners;
} catch (SessionException se) {
return null;
}
}
/**
* Returns an <code>IDPProxyFinder</code>
*
* @param realm the realm name
* @param idpEntityID the entity id of the identity provider
*
* @return the <code>IDPProxyFinder</code>
* @exception SAML2Exception if the operation is not successful
*/
static SAML2IDPFinder getIDPProxyFinder(
throws SAML2Exception {
try {
}
}
if (idpProxyFinder == null) {
} else {
"got the IDPProxyFinder from cache");
}
}
"Unable to get IDP Proxy Finder.", ex);
throw new SAML2Exception(ex);
}
return idpProxyFinder;
}
private static SPSSOConfigElement getSPSSOConfigByAuthnRequest(
}
}