diff options
Diffstat (limited to 'id/server/idserverlib/src/main/java/at/gv/egovernment/moa/id/protocols/stork2/ConsentEvaluator.java')
-rw-r--r-- | id/server/idserverlib/src/main/java/at/gv/egovernment/moa/id/protocols/stork2/ConsentEvaluator.java | 208 |
1 files changed, 208 insertions, 0 deletions
diff --git a/id/server/idserverlib/src/main/java/at/gv/egovernment/moa/id/protocols/stork2/ConsentEvaluator.java b/id/server/idserverlib/src/main/java/at/gv/egovernment/moa/id/protocols/stork2/ConsentEvaluator.java new file mode 100644 index 000000000..9a3376e4c --- /dev/null +++ b/id/server/idserverlib/src/main/java/at/gv/egovernment/moa/id/protocols/stork2/ConsentEvaluator.java @@ -0,0 +1,208 @@ +package at.gv.egovernment.moa.id.protocols.stork2; + +import java.io.StringWriter; +import java.util.ArrayList; +import java.util.HashMap; +import at.gv.egovernment.moa.id.auth.data.AuthenticationSession; +import at.gv.egovernment.moa.id.auth.exception.MOAIDException; +import at.gv.egovernment.moa.id.commons.db.ex.MOADatabaseException; +import at.gv.egovernment.moa.id.config.auth.AuthConfigurationProvider; +import at.gv.egovernment.moa.id.config.auth.OAAuthParameter; +import at.gv.egovernment.moa.id.moduls.IAction; +import at.gv.egovernment.moa.id.moduls.IRequest; +import at.gv.egovernment.moa.id.storage.AssertionStorage; +import at.gv.egovernment.moa.id.util.VelocityProvider; +import at.gv.egovernment.moa.logging.Logger; +import eu.stork.peps.auth.commons.PEPSUtil; +import eu.stork.peps.auth.commons.PersonalAttribute; +import eu.stork.peps.auth.commons.STORKAuthnResponse; +import eu.stork.peps.auth.engine.STORKSAMLEngine; +import eu.stork.peps.exceptions.STORKSAMLEngineException; +import org.apache.velocity.Template; +import org.apache.velocity.VelocityContext; +import org.apache.velocity.app.VelocityEngine; +import org.joda.time.DateTime; +import org.opensaml.common.impl.SecureRandomIdentifierGenerator; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +/** + * The ConsentEvaluator assists with fetching user consent on the list of attributes to be sent to the asking S-PEPS. + */ +public class ConsentEvaluator implements IAction { + + /** + * The Constant ARTIFACT_ID. + */ + private static final String ARTIFACT_ID = "artifactId"; + + /* (non-Javadoc) + * @see at.gv.egovernment.moa.id.moduls.IAction#processRequest(at.gv.egovernment.moa.id.moduls.IRequest, javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse, at.gv.egovernment.moa.id.auth.data.AuthenticationSession) + */ + public String processRequest(IRequest req, HttpServletRequest httpReq, HttpServletResponse httpResp, AuthenticationSession moasession) throws MOAIDException { + + // - fetch the container + String artifactId = (String) httpReq.getParameter(ARTIFACT_ID); + DataContainer container; + try { + container = AssertionStorage.getInstance().get(artifactId, DataContainer.class); + } catch (MOADatabaseException e) { + Logger.error("Error fetching incomplete Stork response from temporary storage. Most likely a timeout occured.", e); + throw new MOAIDException("stork.17", null); + } + + // evaluate response + for(PersonalAttribute current : container.getResponse().getPersonalAttributeList()) { + if(null == httpReq.getParameter(current.getName())) { + current.setStatus("notAvailable"); + current.setValue(new ArrayList<String>()); + current.setComplexValue(new HashMap<String, String>()); + } + } + + // build and send response + generateSTORKResponse(httpResp, container); + + return "12345"; // AssertionId + } + + /** + * Fills the given HttpResponse with the required web page. + * + * @param container the container + * @param response the response + * @param oaParam the oa param + * @return the string + * @throws MOAIDException the mOAID exception + */ + public String requestConsent(DataContainer container, HttpServletResponse response, OAAuthParameter oaParam) throws MOAIDException { + // prepare redirect + String newArtifactId; + try { + + // memorize the container again + Logger.debug("prepare putting the container into temporary storage..."); + + // - generate new key + newArtifactId = new SecureRandomIdentifierGenerator().generateIdentifier(); + + // - put container in temporary store. + AssertionStorage.getInstance().put(newArtifactId, container); + + Logger.debug("...successful"); + + } catch (Exception e1) { + // TODO should we return the response as is to the PEPS? + e1.printStackTrace(); + Logger.error("Error putting incomplete Stork response into temporary storage", e1); + throw new MOAIDException("stork.17", null); + } + + // ask for consent + try { + VelocityEngine velocityEngine = VelocityProvider.getClassPathVelocityEngine(); + Template template = velocityEngine.getTemplate("/resources/templates/stork2_consent.html"); + VelocityContext context = new VelocityContext(); + + context.put("action", AuthConfigurationProvider.getInstance().getPublicURLPrefix() + "/stork2/CompleteAuthentication?" + ARTIFACT_ID + "=" + newArtifactId); + + // assemble table + String table = ""; + for (PersonalAttribute current : container.getResponse().getPersonalAttributeList()) + if ("Available".equals(current.getStatus())) + table += "<tr><td><input type=\"checkbox\" checked=\"yes\" name=\"" + current.getName() + "\"></td><td>" + current.getName() + "</td></tr>\n"; + + context.put("tablecontent", table); + + StringWriter writer = new StringWriter(); + template.merge(context, writer); + response.getOutputStream().write(writer.getBuffer().toString().getBytes()); + + } catch (Exception e) { + Logger.error("Velocity error: " + e.getMessage()); + throw new MOAIDException("stork.17", null); + } + + return "12345"; // AssertionId + } + + /** + * generates binary response from given response class and fill the given HttpResponse with a SAML Post Binding template. + * + * @param httpResp the http resp + * @param container the container + * @throws MOAIDException the mOAID exception + */ + public void generateSTORKResponse(HttpServletResponse httpResp, DataContainer container) throws MOAIDException { + MOASTORKRequest request = container.getRequest(); + MOASTORKResponse response = container.getResponse(); + + Logger.info("generating stork response..."); + + try { + //Get SAMLEngine instance + STORKSAMLEngine engine = STORKSAMLEngine.getInstance("VIDP"); + Logger.debug("Starting generation of SAML response"); + if(response.isAuthnResponse()) + response.setSTORKAuthnResponse(engine.generateSTORKAuthnResponse(request.getStorkAuthnRequest(), response.getStorkAuthnResponse(), container.getRemoteAddress(), false)); + else + response.setSTORKAttrResponse(engine.generateSTORKAttrQueryResponse(request.getStorkAttrQueryRequest(), response.getStorkAttrQueryResponse(), container.getRemoteAddress(), "", false)); + + + //generateSAML Token + Logger.info("SAML response succesfully generated!"); + } catch (STORKSAMLEngineException e) { + Logger.error("Failed to generate STORK SAML Response", e); + throw new MOAIDException("stork.05", null); + } + + // preparing redirection for the client + try { + VelocityEngine velocityEngine = VelocityProvider.getClassPathVelocityEngine(); + Template template = velocityEngine.getTemplate("/resources/templates/stork2_postbinding_template.html"); + VelocityContext context = new VelocityContext(); + + byte[] blob; + if(request.isAttrRequest()) + blob = response.getStorkAttrQueryResponse().getTokenSaml(); + else + blob = response.getStorkAuthnResponse().getTokenSaml(); + + context.put("SAMLResponse", PEPSUtil.encodeSAMLToken(blob)); + Logger.debug("SAMLResponse original: " + new String(blob)); + + Logger.debug("Putting assertion consumer url as action: " + request.getAssertionConsumerServiceURL()); + context.put("action", request.getAssertionConsumerServiceURL()); + Logger.debug("Starting template merge"); + StringWriter writer = new StringWriter(); + + Logger.debug("Doing template merge"); + template.merge(context, writer); + Logger.debug("Template merge done"); + + Logger.debug("Sending html content: " + writer.getBuffer().toString()); + Logger.debug("Sending html content2 : " + new String(writer.getBuffer())); + + httpResp.getOutputStream().write(writer.getBuffer().toString().getBytes()); + + } catch (Exception e) { + Logger.error("Velocity error: " + e.getMessage()); + } + } + + /* (non-Javadoc) + * @see at.gv.egovernment.moa.id.moduls.IAction#needAuthentication(at.gv.egovernment.moa.id.moduls.IRequest, javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse) + */ + public boolean needAuthentication(IRequest req, HttpServletRequest httpReq, HttpServletResponse httpResp) { + // this action does not need any authentication. The authentication is already done by the preceding AuthenticationRequest-Action. + return false; + } + + /* (non-Javadoc) + * @see at.gv.egovernment.moa.id.moduls.IAction#getDefaultActionName() + */ + public String getDefaultActionName() { + return STORKProtocol.CONSENT_EVALUATOR; + } +} |