/** * Initiates <code>SAML</code> web browser POST profile. This method takes in a TARGET in the * request, creates a SAMLResponse, then redirects user to the destination site. * * @param request <code>HttpServletRequest</code> instance * @param response <code>HttpServletResponse</code> instance * @throws ServletException if there is an error. * @throws IOException if there is an error. */ public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { if ((request == null) || (response == null)) { String[] data = {SAMLUtils.bundle.getString("nullInputParameter")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.NULL_PARAMETER, data); SAMLUtils.sendError( request, response, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "nullInputParameter", SAMLUtils.bundle.getString("nullInputParameter")); return; } SAMLUtils.checkHTTPContentLength(request); // get Session Object token = getSession(request); if (token == null) { response.sendRedirect(SAMLUtils.getLoginRedirectURL(request)); return; } // obtain TARGET String target = request.getParameter(SAMLConstants.POST_TARGET_PARAM); if (target == null || target.length() == 0) { String[] data = {SAMLUtils.bundle.getString("missingTargetSite")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.MISSING_TARGET, data, token); SAMLUtils.sendError( request, response, HttpServletResponse.SC_BAD_REQUEST, "missingTargetSite", SAMLUtils.bundle.getString("missingTargetSite")); return; } // Get the Destination site Entry // find the destSite POST URL, which is the Receipient SAMLServiceManager.SiteEntry destSite = getDestSite(target); String destSiteUrl = null; if ((destSite == null) || ((destSiteUrl = destSite.getPOSTUrl()) == null)) { String[] data = {SAMLUtils.bundle.getString("targetForbidden"), target}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.TARGET_FORBIDDEN, data, token); SAMLUtils.sendError( request, response, response.SC_BAD_REQUEST, "targetForbidden", SAMLUtils.bundle.getString("targetForbidden") + " " + target); return; } Response samlResponse = null; try { String version = destSite.getVersion(); int majorVersion = SAMLConstants.PROTOCOL_MAJOR_VERSION; int minorVersion = SAMLConstants.PROTOCOL_MINOR_VERSION; if (version != null) { StringTokenizer st = new StringTokenizer(version, "."); if (st.countTokens() == 2) { majorVersion = Integer.parseInt(st.nextToken().trim()); minorVersion = Integer.parseInt(st.nextToken().trim()); } } // create assertion AssertionManager am = AssertionManager.getInstance(); SessionProvider sessionProvider = SessionManager.getProvider(); Assertion assertion = am.createSSOAssertion( sessionProvider.getSessionID(token), null, request, response, destSite.getSourceID(), target, majorVersion + "." + minorVersion); // create SAMLResponse StatusCode statusCode = new StatusCode(SAMLConstants.STATUS_CODE_SUCCESS); Status status = new Status(statusCode); List contents = new ArrayList(); contents.add(assertion); samlResponse = new Response(null, status, destSiteUrl, contents); samlResponse.setMajorVersion(majorVersion); samlResponse.setMinorVersion(minorVersion); } catch (SessionException sse) { SAMLUtils.debug.error( "SAMLPOSTProfileServlet.doGet: Exception " + "Couldn't get SessionProvider:", sse); SAMLUtils.sendError( request, response, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "couldNotCreateResponse", sse.getMessage()); return; } catch (NumberFormatException ne) { SAMLUtils.debug.error( "SAMLPOSTProfileServlet.doGet: Exception " + "when creating Response: ", ne); SAMLUtils.sendError( request, response, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "couldNotCreateResponse", ne.getMessage()); return; } catch (SAMLException se) { SAMLUtils.debug.error( "SAMLPOSTProfileServlet.doGet: Exception " + "when creating Response: ", se); SAMLUtils.sendError( request, response, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "couldNotCreateResponse", se.getMessage()); return; } // sign the samlResponse byte signedBytes[] = null; try { samlResponse.signXML(); if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message( "SAMLPOSTProfileServlet.doGet: " + "signed samlResponse is" + samlResponse.toString(true, true, true)); } signedBytes = SAMLUtils.getResponseBytes(samlResponse); } catch (Exception e) { SAMLUtils.debug.error( "SAMLPOSTProfileServlet.doGet: Exception " + "when signing the response:", e); SAMLUtils.sendError( request, response, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "errorSigningResponse", SAMLUtils.bundle.getString("errorSigningResponse")); return; } // base64 encode the signed samlResponse String encodedResponse = null; try { encodedResponse = Base64.encode(signedBytes, true).trim(); } catch (Exception e) { SAMLUtils.debug.error( "SAMLPOSTProfileServlet.doGet: Exception " + "when encoding the response:", e); SAMLUtils.sendError( request, response, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "errorEncodeResponse", SAMLUtils.bundle.getString("errorEncodeResponse")); return; } if (LogUtils.isAccessLoggable(java.util.logging.Level.FINE)) { String[] data = { SAMLUtils.bundle.getString("redirectTo"), target, destSiteUrl, new String(signedBytes, "UTF-8") }; LogUtils.access(java.util.logging.Level.FINE, LogUtils.REDIRECT_TO_URL, data, token); } else { String[] data = {SAMLUtils.bundle.getString("redirectTo"), target, destSiteUrl}; LogUtils.access(java.util.logging.Level.INFO, LogUtils.REDIRECT_TO_URL, data, token); } response.setContentType("text/html; charset=UTF-8"); PrintWriter out = response.getWriter(); out.println("<HTML>"); out.println("<BODY Onload=\"document.forms[0].submit()\">"); out.println("<FORM METHOD=\"POST\" ACTION=\"" + destSiteUrl + "\">"); out.println("<INPUT TYPE=\"HIDDEN\" NAME=\"" + SAMLConstants.POST_SAML_RESPONSE_PARAM + "\" "); out.println("VALUE=\"" + encodedResponse + "\">"); out.println( "<INPUT TYPE=\"HIDDEN\" NAME=\"" + SAMLConstants.POST_TARGET_PARAM + "\" VALUE=\"" + target + "\"> </FORM>"); out.println("</BODY></HTML>"); out.close(); }
/** * This method processes TARGET and SAMLResponse info from the request, validates the * response/assertion(s), then redirects user to the TARGET resource if all are valid. * * @param request <code>HttpServletRequest</code> instance * @param response <code>HttpServletResponse</code> instance * @throws ServletException if there is an error. * @throws IOException if there is an error. */ public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { response.setContentType("text/html; charset=UTF-8"); if ((request == null) || (response == null)) { String[] data = {SAMLUtils.bundle.getString("nullInputParameter")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.NULL_PARAMETER, data); SAMLUtils.sendError( request, response, HttpServletResponse.SC_BAD_REQUEST, "nullInputParameter", SAMLUtils.bundle.getString("nullInputParameter")); return; } SAMLUtils.checkHTTPContentLength(request); // obtain TARGET String target = request.getParameter(SAMLConstants.POST_TARGET_PARAM); if (target == null || target.length() == 0) { String[] data = {SAMLUtils.bundle.getString("missingTargetSite")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.MISSING_TARGET, data); SAMLUtils.sendError( request, response, HttpServletResponse.SC_BAD_REQUEST, "missingTargetSite", SAMLUtils.bundle.getString("missingTargetSite")); return; } // obtain SAMLResponse String samlResponse = request.getParameter(SAMLConstants.POST_SAML_RESPONSE_PARAM); if (samlResponse == null) { String[] data = {SAMLUtils.bundle.getString("missingSAMLResponse")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.MISSING_RESPONSE, data); SAMLUtils.sendError( request, response, HttpServletResponse.SC_BAD_REQUEST, "missingSAMLResponse", SAMLUtils.bundle.getString("missingSAMLResponse")); return; } // decode the Response byte raw[] = null; try { raw = Base64.decode(samlResponse); } catch (Exception e) { SAMLUtils.debug.error( "SAMLPOSTProfileServlet.doPost: Exception " + "when decoding SAMLResponse:", e); SAMLUtils.sendError( request, response, response.SC_INTERNAL_SERVER_ERROR, "errorDecodeResponse", SAMLUtils.bundle.getString("errorDecodeResponse")); return; } // Get Response back Response sResponse = SAMLUtils.getResponse(raw); if (sResponse == null) { String[] data = {SAMLUtils.bundle.getString("errorObtainResponse")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.RESPONSE_MESSAGE_ERROR, data); SAMLUtils.sendError( request, response, HttpServletResponse.SC_BAD_REQUEST, "errorObtainResponse", SAMLUtils.bundle.getString("errorObtainResponse")); return; } if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("SAMLPOSTProfileServlet.doPost: Received " + sResponse.toString()); } // verify that Response is correct StringBuffer requestUrl = request.getRequestURL(); if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("SAMLPOSTProfileServlet.doPost: " + "requestUrl=" + requestUrl); } boolean valid = SAMLUtils.verifyResponse(sResponse, requestUrl.toString(), request); if (!valid) { String[] data = {SAMLUtils.bundle.getString("invalidResponse")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.INVALID_RESPONSE, data); SAMLUtils.sendError( request, response, HttpServletResponse.SC_BAD_REQUEST, "invalidResponse", SAMLUtils.bundle.getString("invalidResponse")); return; } Map attrMap = null; List assertions = null; javax.security.auth.Subject authSubject = null; try { Map sessionAttr = SAMLUtils.processResponse(sResponse, target); Object token = SAMLUtils.generateSession(request, response, sessionAttr); } catch (Exception ex) { SAMLUtils.debug.error("generateSession: ", ex); String[] data = {SAMLUtils.bundle.getString("failedCreateSSOToken")}; LogUtils.error(java.util.logging.Level.INFO, LogUtils.FAILED_TO_CREATE_SSO_TOKEN, data); SAMLUtils.sendError( request, response, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "failedCreateSSOToken", ex.getMessage()); ; return; } if (LogUtils.isAccessLoggable(java.util.logging.Level.FINE)) { String[] data = {SAMLUtils.bundle.getString("accessGranted"), new String(raw, "UTF-8")}; LogUtils.access(java.util.logging.Level.FINE, LogUtils.ACCESS_GRANTED, data); } else { String[] data = {SAMLUtils.bundle.getString("accessGranted")}; LogUtils.access(java.util.logging.Level.INFO, LogUtils.ACCESS_GRANTED, data); } if (SAMLUtils.postYN(target)) { if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("POST to target:" + target); } SAMLUtils.postToTarget(response, assertions, target, attrMap); } else { response.setHeader("Location", target); response.sendRedirect(target); } }