Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--org.eclipse.gemini.web.tomcat/src/main/java/org/eclipse/gemini/web/tomcat/internal/Tomcat.java160
-rw-r--r--org.eclipse.gemini.web.tomcat/template.mf3
2 files changed, 160 insertions, 3 deletions
diff --git a/org.eclipse.gemini.web.tomcat/src/main/java/org/eclipse/gemini/web/tomcat/internal/Tomcat.java b/org.eclipse.gemini.web.tomcat/src/main/java/org/eclipse/gemini/web/tomcat/internal/Tomcat.java
index e1c5b94..db1828c 100644
--- a/org.eclipse.gemini.web.tomcat/src/main/java/org/eclipse/gemini/web/tomcat/internal/Tomcat.java
+++ b/org.eclipse.gemini.web.tomcat/src/main/java/org/eclipse/gemini/web/tomcat/internal/Tomcat.java
@@ -17,8 +17,13 @@
package org.eclipse.gemini.web.tomcat.internal;
import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.jar.JarFile;
+import java.util.zip.ZipEntry;
import org.apache.catalina.Container;
import org.apache.catalina.Context;
@@ -40,6 +45,7 @@ import org.eclipse.gemini.web.core.spi.ServletContainerException;
import org.eclipse.gemini.web.tomcat.internal.loading.ChainedClassLoader;
import org.eclipse.gemini.web.tomcat.internal.support.BundleFileResolverFactory;
import org.eclipse.gemini.web.tomcat.internal.support.PackageAdminBundleDependencyDeterminer;
+import org.eclipse.virgo.util.io.IOUtils;
import org.osgi.framework.BundleContext;
import org.osgi.service.packageadmin.PackageAdmin;
import org.slf4j.Logger;
@@ -52,6 +58,20 @@ final class Tomcat extends Embedded {
private static final String ROOT_CONTEXT_PATH = "";
private static final String ROOT_PATH = "/";
+
+ private static final String ROOT_CONTEXT_FILE = "ROOT";
+
+ private static final String CONTEXT_XML = "META-INF/context.xml";
+
+ private static final String CONTEXT_PROPERTY = "Context";
+
+ private static final String XML_EXTENSION = ".xml";
+
+ private static final char SLASH_SEPARATOR = '/';
+
+ private static final char HASH_SEPARATOR = '#';
+
+ private static final String DEFAULT_CONFIG_DIRECTORY = "config";
private final static Logger LOGGER = LoggerFactory.getLogger(Tomcat.class);
@@ -59,12 +79,19 @@ final class Tomcat extends Embedded {
private final JarScanner jarScanner;
+ private Digester digester;
+
+ private BundleContext bundleContext;
+
Tomcat(BundleContext context, PackageAdmin packageAdmin) {
+ this.bundleContext = context;
JarScanner bundleDependenciesJarScanner = new BundleDependenciesJarScanner(new PackageAdminBundleDependencyDeterminer(context, packageAdmin),
BundleFileResolverFactory.createBundleFileResolver());
JarScanner defaultJarScanner = new DefaultJarScanner();
this.jarScanner = new ChainingJarScanner(bundleDependenciesJarScanner, defaultJarScanner);
+
+ digester = createDigester();
}
public void start() throws LifecycleException {
@@ -136,9 +163,10 @@ final class Tomcat extends Embedded {
if (LOGGER.isDebugEnabled()) {
LOGGER.debug("Creating context '" + path + "' with docBase '" + docBase + "'");
}
-
+
StandardContext context = new ExtendedStandardContext();
-
+ readContextXml(path, docBase, context);
+
context.setDocBase(docBase);
context.setPath(path.equals(ROOT_PATH) ? ROOT_CONTEXT_PATH : path);
@@ -211,4 +239,132 @@ final class Tomcat extends Embedded {
*/
private static class ExtendedContextConfig extends ContextConfig {
}
+
+ private Digester createDigester() {
+ Digester digester = new Digester();
+ ClassLoader[] loaders = new ClassLoader[] { Catalina.class.getClassLoader(), Tomcat.class.getClassLoader() };
+ digester.setClassLoader(ChainedClassLoader.create(loaders));
+ digester.setValidating(false);
+ digester.addSetProperties(CONTEXT_PROPERTY);
+ return (digester);
+ }
+
+ private void readContextXml(String path, String docBase, StandardContext context) {
+ // Multi-level context paths may be defined using #, e.g. foo#bar.xml
+ // for a context path of /foo/bar.
+ if (path.equals(ROOT_PATH)) {
+ path = ROOT_CONTEXT_FILE;
+ } else if (SLASH_SEPARATOR == path.charAt(0)) {
+ path = path.substring(1);
+ }
+ path = path.replace(SLASH_SEPARATOR, HASH_SEPARATOR);
+
+ // Initialize config directory location
+ File configLocation = new File(resolveConfigDir());
+ Host host = findHost();
+ Container parent = host.getParent();
+ if ((parent != null) && (parent instanceof Engine)) {
+ configLocation = new File(configLocation, parent.getName());
+ }
+ configLocation = new File(configLocation, host.getName());
+
+ // Try to find the context.xml in the Tomcat's configuration directory
+ File contextXml = new File(configLocation, path + XML_EXTENSION);
+ if (contextXml.exists()) {
+ configureWebContext(contextXml, context);
+ return;
+ }
+
+ // Try to find the context.xml in docBase
+ File docBaseFile = new File(docBase);
+ if (docBaseFile.isDirectory()) {
+ contextXml = new File(docBaseFile, CONTEXT_XML);
+ if (contextXml.exists()) {
+ File destination = new File(configLocation, path + XML_EXTENSION);
+ try {
+ copyFile(new FileInputStream(contextXml), destination);
+ } catch (IOException e) {
+ throw new ServletContainerException("Cannot copy " + contextXml.getAbsolutePath() + " to "
+ + destination.getAbsolutePath(), e);
+ }
+ configureWebContext(destination, context);
+ }
+ } else {
+ JarFile jar;
+ try {
+ jar = new JarFile(docBaseFile);
+ } catch (IOException e) {
+ throw new ServletContainerException("Cannot open for reading " + docBaseFile.getAbsolutePath(), e);
+ }
+ ZipEntry contextXmlEntry = jar.getEntry(CONTEXT_XML);
+ if (contextXmlEntry != null) {
+ File destination = new File(configLocation, path + XML_EXTENSION);
+ try {
+ copyFile(jar.getInputStream(contextXmlEntry), destination);
+ } catch (IOException e) {
+ throw new ServletContainerException("Cannot copy " + contextXml.getAbsolutePath() + " to "
+ + destination.getAbsolutePath(), e);
+ }
+ configureWebContext(destination, context);
+ }
+ }
+ }
+
+ private String resolveConfigDir() {
+ File configFile = null;
+
+ // Search for the property 'org.eclipse.gemini.web.tomcat.config.path'
+ String path = bundleContext.getProperty(TomcatConfigLocator.CONFIG_PATH_FRAMEWORK_PROPERTY);
+ if (path != null) {
+ configFile = new File(path);
+ if (configFile.exists()) {
+ return configFile.getParent();
+ }
+ }
+
+ // Search for the 'config' directory
+ configFile = new File(TomcatConfigLocator.DEFAULT_CONFIG_FILE_PATH);
+ if (configFile.exists()) {
+ return configFile.getParent();
+ } else {
+ return DEFAULT_CONFIG_DIRECTORY;
+ }
+ }
+
+ private void configureWebContext(File contextXml, StandardContext context) {
+ synchronized (digester) {
+ try {
+ digester.push(context);
+ try {
+ digester.parse(contextXml);
+ context.setConfigFile(contextXml.getAbsolutePath());
+ } catch (IOException e) {
+ throw new ServletContainerException("Cannot read " + contextXml.getAbsolutePath()
+ + " for web application.", e);
+ } catch (SAXException e) {
+ throw new ServletContainerException("Cannot parse " + contextXml.getAbsolutePath()
+ + " for web application.", e);
+ }
+ } finally {
+ digester.reset();
+ }
+ }
+ }
+
+ private void copyFile(InputStream source, File destination) throws IOException {
+ destination.getParentFile().mkdirs();
+
+ OutputStream outputStream = null;
+ try {
+ outputStream = new FileOutputStream(destination);
+ byte[] buffer = new byte[1024];
+ int read;
+ while ((read = source.read(buffer)) > 0) {
+ outputStream.write(buffer, 0, read);
+ }
+ } finally {
+ IOUtils.closeQuietly(source);
+ IOUtils.closeQuietly(outputStream);
+ }
+ }
}
diff --git a/org.eclipse.gemini.web.tomcat/template.mf b/org.eclipse.gemini.web.tomcat/template.mf
index 1024713..7a482bb 100644
--- a/org.eclipse.gemini.web.tomcat/template.mf
+++ b/org.eclipse.gemini.web.tomcat/template.mf
@@ -26,6 +26,7 @@ Import-Template: org.eclipse.gemini.web.*;version="1.0",
javax.xml.transform.*;version="0",
javax.xml.validation.*;version="0",
org.w3c.dom.*;version="0"
-Import-Package: org.apache.catalina.deploy;version="6.0.20.S2-r5956"
+Import-Package: org.apache.catalina.deploy;version="6.0.20.S2-r5956",
+ org.apache.catalina.session;version="6.0.20.S2-r5956"
Bundle-Activator: org.eclipse.gemini.web.tomcat.internal.Activator
Excluded-Exports: *.internal.*

Back to the top