001/** 002 * Copyright 2005-2018 The Kuali Foundation 003 * 004 * Licensed under the Educational Community License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.opensource.org/licenses/ecl2.php 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.kuali.rice.edl.impl; 017 018import java.io.ByteArrayInputStream; 019import java.io.IOException; 020 021import javax.servlet.RequestDispatcher; 022import javax.servlet.ServletException; 023import javax.servlet.http.HttpServlet; 024import javax.servlet.http.HttpServletRequest; 025import javax.servlet.http.HttpServletResponse; 026import javax.xml.parsers.DocumentBuilder; 027import javax.xml.parsers.DocumentBuilderFactory; 028import javax.xml.parsers.ParserConfigurationException; 029 030import org.apache.commons.lang.StringUtils; 031import org.apache.log4j.Logger; 032import org.kuali.rice.edl.impl.service.EdlServiceLocator; 033import org.kuali.rice.kew.api.WorkflowRuntimeException; 034import org.kuali.rice.kns.util.IncidentReportUtils; 035import org.kuali.rice.krad.UserSession; 036import org.kuali.rice.krad.exception.AuthenticationException; 037import org.kuali.rice.krad.util.GlobalVariables; 038import org.kuali.rice.krad.util.KRADConstants; 039import org.kuali.rice.krad.util.KRADUtils; 040import org.w3c.dom.Document; 041import org.w3c.dom.Element; 042import org.xml.sax.SAXException; 043 044 045/** 046 * Takes edl web requests. 047 * 048 * @author Kuali Rice Team (rice.collab@kuali.org) 049 * 050 */ 051public class EDLServlet extends HttpServlet { 052 053 private static final long serialVersionUID = -6344765194278430690L; 054 055 private static final Logger LOG = Logger.getLogger(EDLServlet.class); 056 057 @Override 058 public void init() throws ServletException { 059 try { 060 EdlServiceLocator.getEDocLiteService().initEDLGlobalConfig(); 061 } catch (Exception e) { 062 LOG.error("Error initializing EDL", e); 063 } 064 065 } 066 067 @Override 068 protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { 069 String documentId = null; 070 try { 071 UserSession userSession = KRADUtils.getUserSessionFromRequest(request); 072 if (userSession == null) { 073 throw new AuthenticationException("Failed to locate a user session for request."); 074 } 075 GlobalVariables.setUserSession(userSession); 076 077 RequestParser requestParser = new RequestParser(request); 078 String inputCommand = requestParser.getParameterValue("command"); 079 if (StringUtils.equals(inputCommand, "initiate")){ 080 requestParser.setParameterValue("userAction","initiate"); 081 } 082 String edlName = requestParser.getParameterValue("edlName"); 083 if (edlName == null) { 084 edlName = requestParser.getParameterValue("docTypeName");//this is for 'WorkflowQuicklinks' 085 } 086 EDLController edlController = null; 087 088 if (edlName == null) { 089 documentId = requestParser.getParameterValue("docId"); 090 if (documentId == null) { 091 String docFormKey = requestParser.getParameterValue(KRADConstants.DOC_FORM_KEY); 092 if (docFormKey != null) { 093 Element documentState = EDLXmlUtils.getDocumentStateElement(getDocumentFromSession(docFormKey)); 094 documentId = EDLXmlUtils.getChildElementTextValue(documentState, "docId"); 095 requestParser.setAttribute(KRADConstants.DOC_FORM_KEY, docFormKey); 096 } 097 if (documentId == null) { 098 throw new WorkflowRuntimeException("No edl name or document id detected"); 099 } 100 } 101 requestParser.setAttribute("docId", documentId); 102 edlController = EdlServiceLocator.getEDocLiteService().getEDLControllerUsingDocumentId(documentId); 103 } else { 104 edlController = EdlServiceLocator.getEDocLiteService().getEDLControllerUsingEdlName(edlName); 105 } 106 107 //TODO Fix this in a better way (reworking the command structure maybe?) 108 //fix for KULRICE-4057 to make sure we don't destory docContent on empty command params 109 if(inputCommand == null && requestParser.getParameterValue("docId") != null && !"POST".equals(request.getMethod())){ 110 //make sure these are the only params on the request (paging passed undefined input command as well... 111 if(!(request.getParameterMap().size() > 2)){//ensures ONLY documentId was passed 112 requestParser.setParameterValue("command", "displayDocSearchView"); 113 LOG.info("command parameter was not passed with the request, and only document ID was. Defaulted command to 'displayDocSearchView' to ensure docContent remains."); 114 } 115 } 116 117 EDLControllerChain controllerChain = new EDLControllerChain(); 118 controllerChain.addEdlController(edlController); 119 //TODO Do we not want to set the content type for the response? 120 controllerChain.renderEDL(requestParser, response); 121 122 } catch (Exception e) { 123 LOG.error("Error processing EDL", e); 124 outputError(request, response, e, documentId); 125 } finally { 126 GlobalVariables.setUserSession(null); 127 } 128 } 129 130 private void outputError(HttpServletRequest request, HttpServletResponse response, Exception exception, String documentId) throws ServletException, IOException { 131 IncidentReportUtils.populateRequestForIncidentReport(exception, "" + documentId, "eDoc Lite", request); 132 RequestDispatcher rd = getServletContext().getRequestDispatcher(request.getServletPath() + "/../../kr/kualiExceptionIncidentReport.do"); 133 rd.forward(request, response); 134 } 135 136 private Document getDocumentFromSession(String docFormKey) { 137 try { 138 String serializedDocument = (String)GlobalVariables.getUserSession().retrieveObject(docFormKey); 139 DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); 140 141 factory.setNamespaceAware(true); 142 DocumentBuilder builder = factory.newDocumentBuilder(); 143 return builder.parse(new ByteArrayInputStream(serializedDocument.getBytes())); 144 } catch (SAXException | IOException | ParserConfigurationException e) { 145 throw new WorkflowRuntimeException("Caught exception while deserializing document from session", e); 146 } 147 } 148 149}