/* * Copyright (c) 1998-2011 Caucho Technology -- all rights reserved * * This file is part of Resin(R) Open Source * * Each copy or derived work must preserve the copyright notice and this * notice unmodified. * * Resin Open Source is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * Resin Open Source is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or any warranty * of NON-INFRINGEMENT. See the GNU General Public License for more * details. * * You should have received a copy of the GNU General Public License * along with Resin Open Source; if not, write to the * * Free Software Foundation, Inc. * 59 Temple Place, Suite 330 * Boston, MA 02111-1307 USA * * @author Scott Ferguson */ package com.caucho.server.webapp; import java.util.ArrayList; import java.util.HashMap; import java.util.Set; import java.util.logging.Level; import java.util.logging.Logger; import com.caucho.config.ConfigException; import com.caucho.env.deploy.DeployContainer; import com.caucho.env.deploy.DeployControllerType; import com.caucho.env.deploy.DeployMode; import com.caucho.env.deploy.ExpandDeployGenerator; import com.caucho.env.deploy.ExpandVersion; import com.caucho.loader.Environment; import com.caucho.loader.EnvironmentListener; import com.caucho.vfs.Path; /** * The generator for the web-app deploy */ public class WebAppExpandDeployGenerator extends ExpandDeployGenerator<WebAppController> implements EnvironmentListener { private static final Logger log = Logger.getLogger(WebAppExpandDeployGenerator.class.getName()); private final WebAppExpandDeployGeneratorAdmin _admin; private WebAppContainer _container; private WebAppController _parent; private String _urlPrefix = ""; private ArrayList<WebAppConfig> _webAppDefaults = new ArrayList<WebAppConfig>(); private HashMap<Path,WebAppConfig> _webAppConfigMap = new HashMap<Path,WebAppConfig>(); // Maps from the context-path to the webapps directory private HashMap<String,Path> _contextPathMap = new HashMap<String,Path>(); private HashMap<String,String> _nameToKeyMap = new HashMap<String,String>(); private ClassLoader _parentLoader; /** * Creates the new expand deploy. */ public WebAppExpandDeployGenerator(String id, DeployContainer<WebAppController> container, WebAppContainer webAppContainer) { super(id, container, webAppContainer.getRootDirectory()); _container = webAppContainer; _parentLoader = webAppContainer.getClassLoader(); try { setExtension(".war"); } catch (Exception e) { log.log(Level.WARNING, e.toString(), e); } setEntryNamePrefix("/"); _admin = new WebAppExpandDeployGeneratorAdmin(this); } @Override public String getId() { return super.getId() + _urlPrefix; } /** * Gets the webApp container. */ public WebAppContainer getContainer() { return _container; } /** * Sets the parent webApp. */ public void setParent(WebAppController parent) { _parent = parent; } /** * Sets the parent loader. */ public void setParentClassLoader(ClassLoader loader) { _parentLoader = loader; } /** * Sets the url prefix. */ public void setURLPrefix(String prefix) { if (prefix.equals("")) { } while (prefix.endsWith("/")) prefix = prefix.substring(0, prefix.length() - 1); _urlPrefix = prefix; } /** * Gets the url prefix. */ public String getURLPrefix() { return _urlPrefix; } /** * Sets true for a lazy-init. */ public void setLazyInit(boolean lazyInit) throws ConfigException { log.config("lazy-init is deprecated. Use <startup>lazy</startup> instead."); if (lazyInit) setStartupMode(DeployMode.LAZY); else setStartupMode(DeployMode.AUTOMATIC); } /** * Adds an overriding web-app */ public void addWebApp(WebAppConfig config) { String docDir = config.getRootDirectory(); Path appDir = getExpandDirectory().lookup(docDir); _webAppConfigMap.put(appDir, config); if (config.getContextPath() != null) { _contextPathMap.put(config.getContextPath(), appDir); String tail = appDir.getTail(); _nameToKeyMap.put(config.getContextPath(), tail); } } /** * Adds a default. */ public void addWebAppDefault(WebAppConfig config) { _webAppDefaults.add(config); } /** * Returns the log. */ @Override protected Logger getLog() { return log; } /** * Returns the deployed keys. */ @Override protected void fillDeployedNames(Set<String> keys) { super.fillDeployedNames(keys); for (WebAppConfig cfg : _webAppConfigMap.values()) { if (cfg.getContextPath() != null) keys.add(cfg.getContextPath()); } } /** * Start the deploy. */ @Override protected void startImpl() { super.startImpl(); Environment.addEnvironmentListener(this, _parentLoader); _admin.register(); } /** * Returns the new controller. */ @Override protected WebAppController createController(ExpandVersion version) { String key = version.getKey(); String baseKey = version.getBaseKey(); String contextPath = keyToName(baseKey); Path rootDirectory = getExpandPath(key); if (rootDirectory == null) throw new NullPointerException(); if (isVersioning()) { WebAppVersioningController controller = new WebAppVersioningController(getId() + "/" + baseKey, baseKey, contextPath, this, _container); controller.setControllerType(DeployControllerType.VERSIONING); return controller; } else return createVersionController(version); } /** * Returns the new controller. */ public WebAppController createVersionController(ExpandVersion version) { String key = version.getKey(); String baseKey = version.getBaseKey(); String contextPath = keyToName(baseKey); Path rootDirectory = getExpandPath(key); Path archivePath = getArchivePath(key); String id = getId() + "/" + key; WebAppController controller = new WebAppController(id, rootDirectory, _container, contextPath); controller.setArchivePath(archivePath); controller.setWarName(key); controller.setParentWebApp(_parent); controller.setDynamicDeploy(true); controller.setSourceType("expand"); controller.setControllerType(DeployControllerType.DYNAMIC); controller.setStartupMode(getStartupMode()); controller.setRedeployMode(getRedeployMode()); controller.setVersion(version.getVersion()); // server/1h82 vs server/1h20 // controller.init(); return controller; } @Override protected void afterUpdate() { _container.clearCache(); } /** * Returns the current array of webApp entries. */ @Override protected void mergeController(WebAppController controller, String key) { try { Path expandDirectory = getExpandDirectory(); Path rootDirectory = controller.getRootDirectory(); if (! expandDirectory.equals(rootDirectory.getParent())) { return; } super.mergeController(controller, key); if (controller.getArchivePath() == null) { String archiveName = rootDirectory.getTail() + ".war"; Path jarPath = getArchiveDirectory().lookup(archiveName); if (! jarPath.isDirectory()) { controller.setArchivePath(jarPath); controller.addDepend(jarPath); } } controller.setStartupMode(getStartupMode()); // controller.setRedeployMode(getRedeployMode()); for (int i = 0; i < _webAppDefaults.size(); i++) controller.addConfigDefault(_webAppDefaults.get(i)); WebAppConfig cfg = _webAppConfigMap.get(rootDirectory); if (cfg != null) { // server/1h11 if (cfg.getContextPath() != null) controller.setContextPath(cfg.getContextPath()); controller.addConfigDefault(cfg); } } catch (ConfigException e) { log.warning(e.toString()); log.log(Level.FINEST, e.toString(), e); controller.setConfigException(e); } catch (Throwable e) { log.log(Level.WARNING, e.toString(), e); controller.setConfigException(e); } } @Override protected String keyToName(String key) { if (key.equalsIgnoreCase("root")) return _urlPrefix; else return _urlPrefix + "/" + key; } @Override protected String nameToKey(String name) { if (! name.startsWith(_urlPrefix)) return null; // server/1h86 String key = _nameToKeyMap.get(name); if (key != null) return key; String tail = name.substring(_urlPrefix.length()); if (tail.startsWith("/")) tail = tail.substring(1); if (tail.equals("")) key = "ROOT"; else key = tail; return key; } /** * Destroy the deployment. */ @Override protected void destroyImpl() { _admin.unregister(); _container.removeWebAppDeploy(this); Environment.removeEnvironmentListener(this, _parentLoader); super.destroyImpl(); } }