001 /** 002 * 003 * Licensed to the Apache Software Foundation (ASF) under one or more 004 * contributor license agreements. See the NOTICE file distributed with 005 * this work for additional information regarding copyright ownership. 006 * The ASF licenses this file to You under the Apache License, Version 2.0 007 * (the "License"); you may not use this file except in compliance with 008 * the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018 package org.apache.geronimo.console.ca; 019 020 import java.io.ByteArrayInputStream; 021 import java.io.IOException; 022 import java.math.BigInteger; 023 import java.security.PublicKey; 024 import java.text.DateFormat; 025 import java.text.SimpleDateFormat; 026 import java.util.Date; 027 import java.util.Map; 028 import java.util.Properties; 029 030 import javax.portlet.ActionRequest; 031 import javax.portlet.ActionResponse; 032 import javax.portlet.PortletException; 033 import javax.portlet.RenderRequest; 034 import javax.portlet.RenderResponse; 035 import javax.security.auth.x500.X500Principal; 036 037 import org.apache.commons.logging.Log; 038 import org.apache.commons.logging.LogFactory; 039 import org.apache.geronimo.console.MultiPageModel; 040 import org.apache.geronimo.management.geronimo.CertificationAuthority; 041 import org.apache.geronimo.util.CaUtils; 042 import org.apache.geronimo.util.asn1.x509.X509Name; 043 044 /** 045 * Handler for Confirm Client Certificate Issue screen. 046 * 047 * @version $Rev: 514091 $ $Date: 2007-03-03 01:26:39 -0500 (Sat, 03 Mar 2007) $ 048 */ 049 public class ConfirmClientCertHandler extends BaseCAHandler { 050 private final static Log log = LogFactory.getLog(ConfirmClientCertHandler.class); 051 public ConfirmClientCertHandler() { 052 super(CONFIRM_CLIENT_CERT_MODE, "/WEB-INF/view/ca/confirmClientCert.jsp"); 053 } 054 055 public String actionBeforeView(ActionRequest request, ActionResponse response, MultiPageModel model) throws PortletException, IOException { 056 String[] params = {ERROR_MSG, INFO_MSG, "subject", "publickey", "algorithm", "validFrom", "validTo", "sNo", "pkcs10certreq", "requestId"}; 057 for(int i = 0; i < params.length; ++i) { 058 String value = request.getParameter(params[i]); 059 if(value != null) response.setRenderParameter(params[i], value); 060 } 061 return getMode(); 062 } 063 064 public void renderView(RenderRequest request, RenderResponse response, MultiPageModel model) throws PortletException, IOException { 065 String[] params = {ERROR_MSG, INFO_MSG, "subject", "publickey", "algorithm", "validFrom", "validTo", "sNo", "pkcs10certreq", "requestId"}; 066 for(int i = 0; i < params.length; ++i) { 067 String value = request.getParameter(params[i]); 068 if(value != null) request.setAttribute(params[i], value); 069 } 070 } 071 072 public String actionAfterView(ActionRequest request, ActionResponse response, MultiPageModel model) throws PortletException, IOException { 073 String errorMsg = null; 074 try { 075 CertificationAuthority ca = getCertificationAuthority(request); 076 if(ca == null) { 077 throw new Exception("CA is not running. CA may not have been initialized!!"); 078 } 079 BigInteger sNo = new BigInteger(request.getParameter("sNo")); 080 if(ca.isCertificateIssued(sNo)) { 081 // A certificate with the serial number has already been issued. 082 // This may happen if the user clicks on "Issue Certificate" button a second time 083 log.warn("Second request to issue certificate with serial number'"+sNo+"'. A certificate has already been issued."); 084 response.setRenderParameter("sNo", sNo.toString()); 085 response.setRenderParameter(INFO_MSG, "A certificate with the serial number '"+sNo+"' has already been issued. " 086 +"You may be seeing this message since you have clicked on 'Issue Certificate' button a second time."); 087 return VIEW_CERT_MODE; 088 } 089 090 X509Name subject = null; 091 PublicKey publickey = null; 092 // Process the CSR text to get subject details 093 String pkcs10certreq = null, certreq = null; 094 String challenge = null; 095 String requestId = request.getParameter("requestId"); 096 if(requestId != null && !requestId.equals("")) { 097 // Certificate request is being processed using a previously stored request in CertificateRequestStore 098 String certreqText = getCertificateRequestStore(request).getRequest(requestId); 099 if(certreqText.startsWith(CaUtils.CERT_REQ_HEADER)) { 100 // A PKCS 10 Certificate Request 101 pkcs10certreq = certreqText; 102 } else { 103 // Possibly a CSR received through web browser 104 certreq = certreqText; 105 } 106 } else { 107 // No request id is found. Get the PKCS10 request submitted through form input 108 pkcs10certreq = request.getParameter("pkcs10certreq"); 109 } 110 111 if(pkcs10certreq != null && !"".equals(pkcs10certreq)) { 112 // Process PKCS 10 Certificate Request text to get Subject name and public-key 113 Map certReqMap = CaUtils.processPKCS10Request(pkcs10certreq); 114 subject = (X509Name) certReqMap.get(CaUtils.CERT_REQ_SUBJECT); 115 publickey = (PublicKey) certReqMap.get(CaUtils.CERT_REQ_PUBLICKEY_OBJ); 116 } else { 117 // This is a custom request containing SPKAC and X509Name attributes received through web browser 118 Properties csrProps = new Properties(); 119 csrProps.load(new ByteArrayInputStream(certreq.getBytes())); 120 String spkac = csrProps.getProperty("SPKAC"); 121 String cn = csrProps.getProperty("CN"); 122 String ou = csrProps.getProperty("OU"); 123 String o = csrProps.getProperty("O"); 124 String l = csrProps.getProperty("L"); 125 String st = csrProps.getProperty("ST"); 126 String c = csrProps.getProperty("C"); 127 subject = CaUtils.getX509Name(cn, ou, o, l, st, c); 128 Map certReqMap = CaUtils.processSPKAC(spkac); 129 publickey = (PublicKey) certReqMap.get(CaUtils.CERT_REQ_PUBLICKEY_OBJ); 130 challenge = (String) certReqMap.get(CaUtils.PKAC_CHALLENGE); 131 } 132 133 // Dates have already been validated in the previous screen 134 String validFrom = request.getParameter("validFrom"); 135 String validTo = request.getParameter("validTo"); 136 DateFormat df = new SimpleDateFormat("MM/dd/yyyy"); 137 Date validFromDate = df.parse(validFrom); 138 Date validToDate = df.parse(validTo); 139 String algorithm = request.getParameter("algorithm"); 140 // Issue certificate 141 ca.issueCertificate(new X500Principal(subject.getEncoded()), publickey, sNo, validFromDate, validToDate, algorithm); 142 // Store the challenge phrase against the issued certificate serial number 143 if(challenge != null && !challenge.equals("")) { 144 getCertificateStore(request).setCertificateChallenge(sNo, challenge); 145 } 146 147 if(requestId != null && !requestId.equals("")) { 148 // This request was processed using a requestId from CertificateRequestStore. Delete the fulfilled request. 149 getCertificateRequestStore(request).setRequestFulfilled(requestId, sNo); 150 // The confirmation page will show a link to the "Requests to be fulfilled" page. 151 response.setRenderParameter("linkToListRequests", "true"); 152 } 153 154 // Set the serial number and forward to view certificate page 155 response.setRenderParameter("sNo", sNo.toString()); 156 response.setRenderParameter(INFO_MSG, "Certificate Issued successfully. This Certificate details can also be viewed using the serial number '" 157 +sNo+"' with the 'View Issued Certificate' link provided in the CA home screen."); 158 log.info("Certificate with serial number '"+sNo+"' issued to "+subject); 159 return VIEW_CERT_MODE; 160 } catch(Exception e) { 161 errorMsg = e.toString(); 162 log.error("Errors in issuing certificate.", e); 163 } 164 // An error occurred. Go back to previous screen to let the user correct the errors. 165 response.setRenderParameter(ERROR_MSG, errorMsg); 166 return CERT_REQ_DETAILS_MODE+BEFORE_ACTION; 167 } 168 }