SAML2LogoutAPIAuthenticatorCmd: check logout response and redirect to UI

Signed-off-by: Rohit Yadav <rohit.ya...@shapeblue.com>


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/15fdc174
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/15fdc174
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/15fdc174

Branch: refs/heads/master
Commit: 15fdc1744c42c0e70b3cde31ca4b163c7983bec2
Parents: 3bf387c
Author: Rohit Yadav <rohit.ya...@shapeblue.com>
Authored: Mon Aug 25 02:41:26 2014 +0200
Committer: Rohit Yadav <rohit.ya...@shapeblue.com>
Committed: Thu Aug 28 19:45:26 2014 +0200

----------------------------------------------------------------------
 .../command/SAML2LogoutAPIAuthenticatorCmd.java | 40 +++++++++++++++++++-
 1 file changed, 38 insertions(+), 2 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/15fdc174/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LogoutAPIAuthenticatorCmd.java
----------------------------------------------------------------------
diff --git 
a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LogoutAPIAuthenticatorCmd.java
 
b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LogoutAPIAuthenticatorCmd.java
index 9910074..1c96f0b 100644
--- 
a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LogoutAPIAuthenticatorCmd.java
+++ 
b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LogoutAPIAuthenticatorCmd.java
@@ -17,6 +17,7 @@
 package org.apache.cloudstack.api.command;
 
 import com.cloud.api.response.ApiResponseSerializer;
+import com.cloud.configuration.Config;
 import com.cloud.user.Account;
 import org.apache.cloudstack.api.APICommand;
 import org.apache.cloudstack.api.ApiErrorCode;
@@ -27,18 +28,24 @@ import org.apache.cloudstack.api.auth.APIAuthenticationType;
 import org.apache.cloudstack.api.auth.APIAuthenticator;
 import org.apache.cloudstack.api.auth.PluggableAPIAuthenticator;
 import org.apache.cloudstack.api.response.LogoutCmdResponse;
+import org.apache.cloudstack.framework.config.dao.ConfigurationDao;
 import org.apache.cloudstack.saml.SAML2AuthManager;
 import org.apache.cloudstack.utils.auth.SAMLUtils;
 import org.apache.log4j.Logger;
 import org.opensaml.DefaultBootstrap;
 import org.opensaml.saml2.core.LogoutRequest;
 import org.opensaml.saml2.core.NameID;
+import org.opensaml.saml2.core.Response;
+import org.opensaml.saml2.core.StatusCode;
 import org.opensaml.xml.ConfigurationException;
 import org.opensaml.xml.io.MarshallingException;
+import org.opensaml.xml.io.UnmarshallingException;
+import org.xml.sax.SAXException;
 
 import javax.inject.Inject;
 import javax.servlet.http.HttpServletResponse;
 import javax.servlet.http.HttpSession;
+import javax.xml.parsers.ParserConfigurationException;
 import javax.xml.stream.FactoryConfigurationError;
 import java.io.IOException;
 import java.util.List;
@@ -51,6 +58,8 @@ public class SAML2LogoutAPIAuthenticatorCmd extends BaseCmd 
implements APIAuthen
 
     @Inject
     ApiServerService _apiServer;
+    @Inject
+    ConfigurationDao _configDao;
     SAML2AuthManager _samlAuthManager;
 
     /////////////////////////////////////////////////////
@@ -79,6 +88,7 @@ public class SAML2LogoutAPIAuthenticatorCmd extends BaseCmd 
implements APIAuthen
         LogoutCmdResponse response = new LogoutCmdResponse();
         response.setDescription("success");
         response.setResponseName(getCommandName());
+        String responseString = 
ApiResponseSerializer.toSerializedString(response, responseType);
 
         try {
             DefaultBootstrap.bootstrap();
@@ -89,8 +99,35 @@ public class SAML2LogoutAPIAuthenticatorCmd extends BaseCmd 
implements APIAuthen
                     params, responseType));
         }
 
+        if (params.containsKey("SAMLResponse")) {
+            try {
+                final String samlResponse = 
((String[])params.get(SAMLUtils.SAML_RESPONSE))[0];
+                Response processedSAMLResponse = 
SAMLUtils.decodeSAMLResponse(samlResponse);
+                String statusCode = 
processedSAMLResponse.getStatus().getStatusCode().getValue();
+                if (!statusCode.equals(StatusCode.SUCCESS_URI)) {
+                    throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, 
_apiServer.getSerializedApiError(ApiErrorCode.INTERNAL_ERROR.getHttpCode(),
+                            "SAML SLO LogoutResponse status is not Success",
+                            params, responseType));
+                }
+            } catch (ConfigurationException | FactoryConfigurationError | 
ParserConfigurationException | SAXException | IOException | 
UnmarshallingException e) {
+                s_logger.error("SAMLResponse processing error: " + 
e.getMessage());
+            }
+            try {
+                
resp.sendRedirect(_configDao.getValue(Config.SAMLCloudStackRedirectionUrl.key()));
+            } catch (IOException ignored) {
+            }
+            return responseString;
+        }
+
         NameID nameId = (NameID) session.getAttribute(SAMLUtils.SAML_NAMEID);
         String sessionIndex = (String) 
session.getAttribute(SAMLUtils.SAML_SESSION);
+        if (nameId == null || sessionIndex == null) {
+            try {
+                
resp.sendRedirect(_configDao.getValue(Config.SAMLCloudStackRedirectionUrl.key()));
+            } catch (IOException ignored) {
+            }
+            return responseString;
+        }
         LogoutRequest logoutRequest = 
SAMLUtils.buildLogoutRequest(_samlAuthManager.getIdpSingleLogOutUrl(), 
_samlAuthManager.getServiceProviderId(), nameId, sessionIndex);
 
         try {
@@ -102,8 +139,7 @@ public class SAML2LogoutAPIAuthenticatorCmd extends BaseCmd 
implements APIAuthen
                     "SAML Single Logout Error",
                     params, responseType));
         }
-
-        return ApiResponseSerializer.toSerializedString(response, 
responseType);
+        return responseString;
     }
 
     @Override

Reply via email to