/* * Copyright 2000-2013 Enonic AS * http://www.enonic.com/license */ package com.enonic.vertical.adminweb; import java.io.IOException; import java.io.StringWriter; import java.util.HashMap; import java.util.List; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpSession; import org.jdom.JDOMException; import org.w3c.dom.Document; import org.w3c.dom.Element; import com.enonic.esl.containers.ExtendedMap; import com.enonic.esl.containers.MultiValueMap; import com.enonic.esl.xml.XMLTool; import com.enonic.vertical.engine.VerticalEngineException; import com.enonic.cms.framework.util.JDOMUtil; import com.enonic.cms.framework.xml.XMLDocument; import com.enonic.cms.core.content.contenttype.ContentHandlerEntity; import com.enonic.cms.core.content.contenttype.ContentHandlerKey; import com.enonic.cms.core.content.contenttype.ContentHandlerName; import com.enonic.cms.core.content.contenttype.ContentTypeConfig; import com.enonic.cms.core.content.contenttype.ContentTypeConfigParser; import com.enonic.cms.core.content.contenttype.ContentTypeEntity; import com.enonic.cms.core.content.contenttype.ContentTypeXmlCreator; import com.enonic.cms.core.content.contenttype.InvalidContentTypeConfigException; import com.enonic.cms.core.resource.ResourceFile; import com.enonic.cms.core.resource.ResourceKey; import com.enonic.cms.core.security.user.User; import com.enonic.cms.core.service.AdminService; public class ContentTypeHandlerServlet extends AdminHandlerBaseServlet { public String buildContentTypeXML( ExtendedMap formItems, boolean reload ) { StringWriter sw = new StringWriter(); try { Document doc = XMLTool.createDocument(); // Create unit element Element contentType = XMLTool.createRootElement( doc, "contenttype" ); if ( formItems.containsKey( "key" ) ) { contentType.setAttribute( "key", formItems.getString( "key" ) ); } if ( formItems.containsKey( "sitekey" ) ) { contentType.setAttribute( "sitekey", formItems.getString( "sitekey" ) ); } if ( formItems.containsKey( "contenthandlerkey" ) ) { contentType.setAttribute( "contenthandlerkey", formItems.getString( "contenthandlerkey" ) ); } if ( formItems.containsKey( "csskey" ) ) { contentType.setAttribute( "csskey", formItems.getString( "csskey" ) ); } XMLTool.createElement( doc, contentType, "name", formItems.getString( "name", "" ) ); XMLTool.createElement( doc, contentType, "description", formItems.getString( "description", "" ) ); // Module XML String moduleXML = formItems.getString( "module", "" ); if ( moduleXML == null || moduleXML.length() == 0 ) { XMLTool.createElement( doc, contentType, "moduledata" ); } else { if ( !reload ) { try { Document modDocTemp = XMLTool.domparse( moduleXML, "contenttype" ); Document modDoc = XMLTool.createDocument( "moduledata" ); XMLTool.mergeDocuments( modDoc, modDocTemp, false ); contentType.appendChild( doc.importNode( modDoc.getDocumentElement(), true ) ); } catch ( Exception e ) { addError( 2, "module", moduleXML ); } } } XMLTool.printDocument( sw, doc ); } catch ( Exception e ) { System.err.println( "[Error] Something failed:\n" + e.toString() ); } return sw.toString(); } /** * Insert the method's description here. */ public void handlerBrowse( HttpServletRequest request, HttpServletResponse response, HttpSession session, AdminService admin, ExtendedMap formItems ) throws VerticalAdminException { User loggedInUser = securityService.getLoggedInAdminConsoleUser(); List<ContentTypeEntity> allContentTypes = contentTypeDao.getAll(); ContentTypeXmlCreator xmlCreator = new ContentTypeXmlCreator(); XMLDocument contentTypesDoc = xmlCreator.createContentTypesDocument( allContentTypes ); Document doc = contentTypesDoc.getAsDOMDocument(); // Parameters ExtendedMap parameters = new ExtendedMap(); parameters.put( "page", String.valueOf( request.getParameter( "page" ) ) ); addSortParamteres( "name", "ascending", formItems, session, parameters ); addAccessLevelParameters(loggedInUser, parameters); transformXML( request, response, doc, "contenttype_browse.xsl", parameters ); } public void handlerCreate( HttpServletRequest request, HttpServletResponse response, HttpSession session, AdminService admin, ExtendedMap formItems ) throws VerticalAdminException, VerticalEngineException { User user = securityService.getLoggedInAdminConsoleUser(); // Enforce unique names String name = formItems.getString( "name" ); if ( admin.getContentTypeKeyByName( name ) > -1 ) { addError( 7, "name", name ); } String xmlData = buildContentTypeXML( formItems, false ); ContentHandlerKey contentHandlerKey = new ContentHandlerKey( formItems.getString( "contenthandlerkey" ) ); ContentHandlerEntity contentHandler = contentHandlerDao.findByKey( contentHandlerKey ); ContentHandlerName contentHandlerName = ContentHandlerName.parse( contentHandler.getClassName() ); String errorInConfig = validateConfig( contentHandlerName, xmlData ); if ( this.hasErrors() || errorInConfig != null ) { if ( errorInConfig != null ) { String moduleXML = formItems.getString( "module", "" ); addError( 2, "module", moduleXML ); formItems.put( "errorInConfig", errorInConfig ); } handlerForm( request, response, session, admin, formItems ); return; } admin.createContentType( user, xmlData ); MultiValueMap queryParams = new MultiValueMap(); queryParams.put( "page", formItems.get( "page" ) ); queryParams.put( "op", "browse" ); redirectClientToAdminPath( "adminpage", queryParams, request, response ); } public void handlerForm( HttpServletRequest request, HttpServletResponse response, HttpSession session, AdminService admin, ExtendedMap formItems ) throws VerticalAdminException { boolean createContent = formItems.containsKey( "create" ); boolean reloading = formItems.getString( "reload", "" ).equals( "true" ); boolean usehandlerindexing = false; HashMap<String, String> parameters = new HashMap<String, String>(); Element contentTypeElem; Document xmlData; Document doc; String referer = request.getHeader( "referer" ); int contentTypeKey = -1; String generateKey = formItems.getString( "generatectykey", "" ); if ( generateKey.equals( "true" ) ) { parameters.put( "generatectykey", "true" ); } else { String keyStr = request.getParameter( "key" ); if ( keyStr != null && keyStr.length() > 0 ) { contentTypeKey = Integer.parseInt( keyStr ); } } int contentHandlerKey = formItems.getInt( "contenthandlerkey", 0 ); if ( reloading || hasErrors() ) { if ( reloading ) { usehandlerindexing = true; } doc = XMLTool.createDocument( "contenttypes" ); Document contentTypeDoc = XMLTool.domparse( buildContentTypeXML( formItems, reloading ) ); contentTypeElem = contentTypeDoc.getDocumentElement(); if ( formItems.containsKey( "key" ) ) { int key = formItems.getInt( "key" ); int contentCount = admin.getContentCountByContentType( key ); contentTypeElem.setAttribute( "contentcount", String.valueOf( contentCount ) ); } doc.getDocumentElement().appendChild( doc.importNode( contentTypeElem, true ) ); referer = formItems.getString( "referer" ); } else if ( contentTypeKey == -1 ) { // Blank form, make dummy document doc = XMLTool.createDocument( "contenttypes" ); usehandlerindexing = true; // Create content type element contentTypeElem = XMLTool.createElement( doc, doc.getDocumentElement(), "contenttype" ); createContent = true; } else { // Edit content type xmlData = admin.getContentType( contentTypeKey, true ).getAsDOMDocument(); doc = xmlData; contentTypeElem = XMLTool.getElement( doc.getDocumentElement(), "contenttype" ); String contentHandlerString = contentTypeElem.getAttribute( "contenthandlerkey" ); if ( contentHandlerString.length() > 0 ) { contentHandlerKey = Integer.parseInt( contentHandlerString ); } String cssString = contentTypeElem.getAttribute( "csskey" ); if ( cssString.length() > 0 ) { ResourceKey cssKey = ResourceKey.from( cssString ); parameters.put( "cssname", cssKey.toString() ); ResourceFile contentTypeStylesheet = this.resourceService.getResourceFile( cssKey ); if ( contentTypeStylesheet == null ) { parameters.put( "cssexist", "false" ); } else { parameters.put( "cssexist", "true" ); } } } Document contentHandlersDoc = admin.getContentHandlers().getAsDOMDocument(); doc.getDocumentElement().appendChild( doc.importNode( contentHandlersDoc.getDocumentElement(), true ) ); addErrorsXML( doc ); if ( createContent ) { parameters.put( "create", "1" ); } else { parameters.put( "create", "0" ); } parameters.put( "referer", referer ); if ( contentHandlerKey > -1 ) { parameters.put( "contenthandlerkey", Integer.toString( contentHandlerKey ) ); } parameters.put( "usehandlerindexing", String.valueOf( usehandlerindexing ) ); parameters.put( "page", String.valueOf( request.getParameter( "page" ).toString() ) ); parameters.put( "errorInConfig", formItems.getString( "errorInConfig", "" ) ); transformXML( request, response, doc, "contenttype_form.xsl", parameters ); } /** * Uses the form input to remove one selected content type from the system. */ public void handlerRemove( HttpServletRequest request, HttpServletResponse response, HttpSession session, AdminService admin, ExtendedMap formItems, int key ) throws VerticalAdminException, VerticalEngineException { User user = securityService.getLoggedInAdminConsoleUser(); admin.removeContentType( user, key ); redirectClientToReferer( request, response ); } /** * Provides a list of all the content types in the system. */ public boolean handlerSelect( HttpServletRequest request, HttpServletResponse response, HttpSession session, AdminService admin, ExtendedMap formItems ) throws VerticalAdminException { String returnKey = null; String returnView = null; int returnRow = -1; if ( !( request.getParameter( "returnkey" ) == null || request.getParameter( "returnkey" ).equals( "" ) ) ) { returnKey = request.getParameter( "returnkey" ); } else { String message = "Parameter not found: returnkey"; VerticalAdminLogger.errorAdmin( message ); } if ( !( request.getParameter( "returnview" ) == null || request.getParameter( "returnview" ).equals( "" ) ) ) { returnView = request.getParameter( "returnview" ); } else { String message = "Parameter not found: returnview"; VerticalAdminLogger.errorAdmin( message ); } if ( !( request.getParameter( "returnrow" ) == null || request.getParameter( "returnrow" ).equals( "" ) ) ) { returnRow = Integer.parseInt( request.getParameter( "returnrow" ) ); } Document doc = admin.getContentTypes().getAsDOMDocument(); HashMap<String, String> parameters = new HashMap<String, String>(); parameters.put( "returnview", returnView ); parameters.put( "returnkey", returnKey ); if ( returnRow != -1 ) { parameters.put( "returnrow", String.valueOf( returnRow ) ); } transformXML( request, response, doc, "contenttype_selector.xsl", parameters ); return true; } /** * Uses the form input to update a content type. */ public void handlerUpdate( HttpServletRequest request, HttpServletResponse response, HttpSession session, AdminService admin, ExtendedMap formItems ) throws VerticalAdminException, VerticalEngineException { User user = securityService.getLoggedInAdminConsoleUser(); // Build site XML and create the protal String xmlData = buildContentTypeXML( formItems, false ); ContentHandlerKey contentHandlerKey = new ContentHandlerKey( formItems.getString( "contenthandlerkey" ) ); ContentHandlerEntity contentHandler = contentHandlerDao.findByKey( contentHandlerKey ); ContentHandlerName contentHandlerName = ContentHandlerName.parse( contentHandler.getClassName() ); String errorInConfig = validateConfig( contentHandlerName, xmlData ); if ( this.hasErrors() || errorInConfig != null ) { if ( errorInConfig != null ) { String moduleXML = formItems.getString( "module", "" ); addError( 2, "module", moduleXML ); formItems.put( "errorInConfig", errorInConfig ); } handlerForm( request, response, session, admin, formItems ); return; } admin.updateContentType( user, xmlData ); MultiValueMap queryParams = new MultiValueMap(); queryParams.put( "page", formItems.get( "page" ) ); queryParams.put( "op", "browse" ); redirectClientToAdminPath( "adminpage", queryParams, request, response ); } public void handlerCustom( HttpServletRequest request, HttpServletResponse response, HttpSession session, AdminService admin, ExtendedMap formItems, String operation ) throws VerticalAdminException, VerticalEngineException { if ( operation.equals( "selectsite" ) ) { String returnKey = null; String returnView = null; int returnRow = -1; if ( !( request.getParameter( "returnkey" ) == null || request.getParameter( "returnkey" ).equals( "" ) ) ) { returnKey = request.getParameter( "returnkey" ); } else { String message = "Parameter not found: returnkey"; VerticalAdminLogger.errorAdmin( message ); } if ( !( request.getParameter( "returnview" ) == null || request.getParameter( "returnview" ).equals( "" ) ) ) { returnView = request.getParameter( "returnview" ); } else { String message = "Parameter not found: returnview"; VerticalAdminLogger.errorAdmin( message ); } if ( !( request.getParameter( "returnrow" ) == null || request.getParameter( "returnrow" ).equals( "" ) ) ) { returnRow = Integer.parseInt( request.getParameter( "returnrow" ) ); } Document doc = admin.getContentTypes( false ).getAsDOMDocument(); HashMap<String, String> parameters = new HashMap<String, String>(); parameters.put( "returnview", returnView ); parameters.put( "returnkey", returnKey ); if ( returnRow != -1 ) { parameters.put( "returnrow", String.valueOf( returnRow ) ); } transformXML( request, response, doc, "contenttype_selector.xsl", parameters ); } else if ( "regenerateindex".equals( operation ) ) { int contentTypeKey = formItems.getInt( "contenttypekey" ); // ( "regenerate index for content type key: " + contentTypeKey ); admin.regenerateIndexForContentType( contentTypeKey ); redirectClientToReferer( request, response ); } } private String validateConfig( ContentHandlerName contentHandlerName, String xmlData ) { org.jdom.Element configEl; try { org.jdom.Element contentTypeEl = JDOMUtil.parseDocument( xmlData ).getRootElement(); org.jdom.Element moduleDataEl = contentTypeEl.getChild( "moduledata" ); if ( moduleDataEl == null ) { configEl = contentTypeEl.getChild( "config" ); } else { configEl = moduleDataEl.getChild( "config" ); } } catch ( IOException e ) { throw new RuntimeException( "Failed to validate content type config", e ); } catch ( JDOMException e ) { throw new RuntimeException( "Failed to validate content type config", e ); } if ( configEl != null ) { // Parse the content type config... the parser will throw exceptions if anything is not correctly written try { if ( contentHandlerName.equals( ContentHandlerName.CUSTOM ) ) { final ContentTypeConfig contentTypeConfig = ContentTypeConfigParser.parse( contentHandlerName, configEl ); contentTypeConfig.validate(); } } catch ( InvalidContentTypeConfigException e ) { return e.getMessage(); } } return null; } }