[124914] Implement main portion of experimental Tomcat plug-in to serve modules without publishing. Does not save contexts to separate XML files. The "loader" jars are also simple Java projects that can be rebuilt by specifying a classpath variable that points to an appropriate Tomcat installation,
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/META-INF/MANIFEST.MF b/plugins/org.eclipse.jst.server.tomcat.core/META-INF/MANIFEST.MF
index 8cd9b0f..aea71e2 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/META-INF/MANIFEST.MF
+++ b/plugins/org.eclipse.jst.server.tomcat.core/META-INF/MANIFEST.MF
@@ -19,6 +19,9 @@
org.eclipse.jdt.launching;bundle-version="[3.2.0,4.0.0)",
org.eclipse.wst.server.core;bundle-version="[1.0.204,1.1.0)",
org.eclipse.jst.server.core;bundle-version="[1.0.103,1.1.0)",
- org.eclipse.jst.common.project.facet.core;bundle-version="[1.1.0,1.2.0)"
+ org.eclipse.jst.common.project.facet.core;bundle-version="[1.1.0,1.2.0)",
+ org.eclipse.wst.common.modulecore;bundle-version="[1.1.0,1.2.0)",
+ org.eclipse.jst.j2ee;bundle-version="[1.1.0,1.2.0)",
+ org.eclipse.emf.common
Eclipse-LazyStart: true
Bundle-RequiredExecutionEnvironment: J2SE-1.4
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.50.loader.jar b/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.50.loader.jar
new file mode 100644
index 0000000..6a4a4d3
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.50.loader.jar
Binary files differ
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.55.loader.jar b/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.55.loader.jar
new file mode 100644
index 0000000..17f0382
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.55.loader.jar
Binary files differ
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.60.loader.jar b/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.60.loader.jar
new file mode 100644
index 0000000..72f19e0
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/org.eclipse.jst.server.tomcat.runtime.60.loader.jar
Binary files differ
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/CatalinaPropertiesUtil.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/CatalinaPropertiesUtil.java
new file mode 100644
index 0000000..9876742
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/CatalinaPropertiesUtil.java
@@ -0,0 +1,136 @@
+/**********************************************************************
+ * Copyright (c) 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Igor Fedorenko & Fabrizio Giustina - Initial API and implementation
+ **********************************************************************/
+package org.eclipse.jst.server.tomcat.core.internal;
+
+import java.io.BufferedReader;
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileReader;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.util.Iterator;
+import java.util.LinkedHashSet;
+import java.util.Set;
+import java.util.StringTokenizer;
+
+/**
+ * Utility methods for handling loaders in catalina.properties.
+ */
+public class CatalinaPropertiesUtil {
+
+ /**
+ * Don't instantiate
+ */
+ private CatalinaPropertiesUtil() {
+ // unused
+ }
+
+ /**
+ * Adds a list of path elements to a specific loader in catalina.properties.
+ * This method doesn't use java.util.Properties in order to keep file
+ * formatting intact.
+ *
+ * @param file catalina.properties file
+ * @param loader loader name
+ * @param elements List of classpath elements
+ * @throws IOException
+ */
+ public static void addGlobalClasspath(File file, String loader,
+ String[] elements) throws IOException {
+
+ String propertyName = loader + ".loader";
+
+ BufferedReader br = null;
+ StringBuffer buffer = new StringBuffer();
+ boolean added = false;
+
+ try {
+ br = new BufferedReader(new FileReader(file));
+ String line = br.readLine();
+ while (line != null) {
+
+ if (line.startsWith(propertyName)) {
+ added = true;
+ line = addElements(line, elements);
+ }
+
+ buffer.append(line);
+ buffer.append("\n");
+ line = br.readLine();
+ }
+ } finally {
+ if (br != null) {
+ br.close();
+ }
+ }
+ if (!added) {
+ // should never happen with an original catalina.properties,
+ // but better handle also files modified by users
+ buffer.append(propertyName);
+ buffer.append("=");
+ for (int i = 0; i < elements.length; i++) {
+ buffer.append(elements[i]);
+ }
+ buffer.append("\n");
+ }
+
+ String propertyFile = buffer.toString();
+
+ BufferedWriter bw = null;
+ try {
+ bw = new BufferedWriter(new FileWriter(file));
+ bw.write(propertyFile);
+ } finally {
+ if (br != null) {
+ bw.close();
+ }
+ }
+ }
+
+ /**
+ * Append a list of path to the property at the given line and returns the
+ * modified name.
+ * @param line line (property=value)
+ * @param elements classpath elements to add.
+ * @return modified line
+ */
+ private static String addElements(String line, String[] elements) {
+ String[] propAndValue = line.split("=");
+ String loaderProperty = "";
+
+ if (propAndValue.length > 1) {
+ loaderProperty = propAndValue[1];
+ }
+
+ Set classpath = new LinkedHashSet();
+
+ StringTokenizer st = new StringTokenizer(loaderProperty, ",");
+ while (st.hasMoreTokens()) {
+ classpath.add(st.nextToken());
+ }
+
+ for (int i = 0; i < elements.length; i++) {
+ classpath.add(elements[i]);
+ }
+
+ StringBuffer sb = new StringBuffer();
+ sb.append(propAndValue[0]);
+ sb.append("=");
+ for (Iterator it = classpath.iterator(); it.hasNext();) {
+ sb.append(it.next());
+ if (it.hasNext()) {
+ sb.append(',');
+ }
+ }
+
+ return sb.toString();
+ }
+}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServer.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServer.java
index eee5098..4e09d34 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServer.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServer.java
@@ -1,5 +1,5 @@
/**********************************************************************
- * Copyright (c) 2005 IBM Corporation and others.
+ * Copyright (c) 2005, 2006, 2007 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@@ -34,6 +34,12 @@
public static final String PROPERTY_DEPLOY_DIR = "deployDir";
/**
+ * Property which specifies if modules should be served without
+ * publishing.
+ */
+ public static final String PROPERTY_SERVE_MODULES_WITHOUT_PUBLISH = "serveModulesWithoutPublish";
+
+ /**
* Returns true if this is a test (publish and run code out of the
* workbench) environment server.
*
@@ -58,4 +64,12 @@
* @return directory where web applications are deployed
*/
public String getDeployDirectory();
+
+ /**
+ * Returns true if modules should be served directly from the project
+ * folders without publishing.
+ *
+ * @return true if modules should not be published but served directly
+ */
+ public boolean isServeModulesWithoutPublish();
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServerWorkingCopy.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServerWorkingCopy.java
index 75e169b..b6dc882 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServerWorkingCopy.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatServerWorkingCopy.java
@@ -47,4 +47,11 @@
* @param deployDir deployment directory for the server
*/
public void setDeployDirectory(String deployDir);
+
+ /**
+ * Set this server to serve modules without publishing.
+ *
+ * @param b true if modules should be served without publishing
+ */
+ public void setServeModulesWithoutPublish(boolean b);
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatVersionHandler.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatVersionHandler.java
index fc3b107..9cea32d 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatVersionHandler.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/ITomcatVersionHandler.java
@@ -100,7 +100,7 @@
*
* @param server TomcatServer instance from which to determine
* the base path.
- * @return the server base path
+ * @return path to Tomcat instance directory
*/
public IPath getRuntimeBaseDirectory(TomcatServer server);
@@ -108,7 +108,7 @@
* Prepare server runtime directory. Create catalina instance set of
* directories.
*
- * @param baseDir directory at which to prepare the runtime directory.
+ * @param baseDir Tomcat instance directory to prepare
* @return result of creation operation
*/
public IStatus prepareRuntimeDirectory(IPath baseDir);
@@ -118,7 +118,47 @@
* initialized appropriately.
*
* @param deployPath path to the deployment directory
+ * being prepared
* @return status result of the operation
*/
public IStatus prepareDeployDirectory(IPath deployPath);
+
+ /**
+ * Prepare directory for serving contexts directly if enabled.
+ * If not enabled, restore directory if necessary.
+ *
+ * @param baseDir path to Tomcat instance directory
+ * @param server TomcatServer instance from which to determine
+ * if serving directly is enabled
+ * @return status result of the operation
+ */
+ public IStatus prepareForServingDirectly(IPath baseDir, TomcatServer server);
+
+ /**
+ * Gets the name of the "shared" loader to use with serving
+ * modules without publishing. Returns null if serving modules
+ * without publishing is not supported.
+ *
+ * @param baseDir path to Tomcat instance directory
+ * @return name of shared loader
+ */
+ public String getSharedLoader(IPath baseDir);
+
+ /**
+ * Returns true if this server supports serving modules without
+ * publishing.
+ *
+ * @return true if serving modules without publishing is supported
+ */
+ public boolean supportsServeModulesWithoutPublish();
+
+ /**
+ * Returns true if this server supports a debug argument. This
+ * argument is expected to affect the level of logging. Newer
+ * versions of Tomcat use different means of controlling logging
+ * and ignore this argument.
+ *
+ * @return true if debug argument is supported
+ */
+ public boolean supportsDebugArgument();
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.java
index d2155b8..732211f 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.java
@@ -1,5 +1,5 @@
/**********************************************************************
- * Copyright (c) 2005 IBM Corporation and others.
+ * Copyright (c) 2005, 2006, 2007 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@@ -83,6 +83,13 @@
public static String errorXMLContextNotFoundPath;
public static String errorXMLContextMangerNotFound;
public static String errorXMLContextNotFoundPath32;
+ public static String errorNoPublishNotSupported;
+ public static String errorPublishContextNotFound;
+ public static String errorPublishCouldNotRemoveModule;
+ public static String errorPublishLoaderJarNotFound;
+ public static String errorPublishURLConvert;
+ public static String errorPublishCantDeleteLoaderJar;
+ public static String errorPublishCatalinaProps;
public static String configurationEditorActionModifyPort;
public static String configurationEditorActionModifyMimeMapping;
@@ -96,6 +103,7 @@
public static String serverEditorActionSetSecure;
public static String serverEditorActionSetServerDirectory;
public static String serverEditorActionSetDeployDirectory;
+ public static String serverEditorActionSetServeWithoutPublish;
public static String fixModuleContextRootDescription;
public static String fixModuleContextRoot;
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.properties b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.properties
index 305e01c..407bc59 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.properties
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Messages.properties
@@ -1,5 +1,5 @@
###############################################################################
-# Copyright (c) 2004, 2005 IBM Corporation and others.
+# Copyright (c) 2004, 2005, 2006, 2007 IBM Corporation and others.
# All rights reserved. This program and the accompanying materials
# are made available under the terms of the Eclipse Public License v1.0
# which accompanies this distribution, and is available at
@@ -100,6 +100,13 @@
errorXMLContextNotFoundPath=Context with path \"{0}\" was not found under Service \"{1}\", Engine \"{2}\", and Host \"{3}\".
errorXMLContextMangerNotFound=ContextManager element was not found.
errorXMLContextNotFoundPath32=Context with path \"{0}\" was not found under ContextManager.
+errorNoPublishNotSupported=Serving modules without publishing is not supported by this server.
+errorPublishContextNotFound=Context not found for module {0}.
+errorPublishCouldNotRemoveModule=Could not remove module {0}.
+errorPublishLoaderJarNotFound=Loader jar not found for server ID: {0}.
+errorPublishURLConvert=Exception occurred converting URL {0}: {1}.
+errorPublishCantDeleteLoaderJar=Unable to delete the custom loader jar {0} from Tomcat server.
+errorPublishCatalinaProps=Exception occurred modifying catalina.properties: {0}.
warningJRE=Tomcat requires a Java SDK in order to compile JSP files. Ensure that the JRE preference settings point to an SDK install location.
warningCantReadConfig=Cannot read the Tomcat configuration.
@@ -109,3 +116,4 @@
serverEditorActionSetDebugMode=Tomcat Debug Option Change
serverEditorActionSetServerDirectory=Tomcat Server Path Change
serverEditorActionSetDeployDirectory=Tomcat Deploy Path Change
+serverEditorActionSetServeWithoutPublish=Serve Modules Without Publish Change
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/PublishOperation2.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/PublishOperation2.java
index 3b285a7..613109e 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/PublishOperation2.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/PublishOperation2.java
@@ -28,6 +28,15 @@
protected int kind;
protected int deltaKind;
+ /**
+ * Construct the operation object to publish the specified module
+ * to the specified server.
+ *
+ * @param server server to which the module will be published
+ * @param kind kind of publish
+ * @param module module to publish
+ * @param deltaKind kind of change
+ */
public PublishOperation2(TomcatServerBehaviour server, int kind, IModule[] module, int deltaKind) {
super("Publish to server", "Publish Web module to Tomcat server");
this.server = server;
@@ -36,14 +45,23 @@
this.deltaKind = deltaKind;
}
+ /**
+ * @see PublishOperation#getOrder()
+ */
public int getOrder() {
return 0;
}
+ /**
+ * @see PublishOperation#getKind()
+ */
public int getKind() {
return REQUIRED;
}
+ /**
+ * @see PublishOperation#execute(IProgressMonitor, IAdaptable)
+ */
public void execute(IProgressMonitor monitor, IAdaptable info) throws CoreException {
List status = new ArrayList();
if (module.length == 1) { // web module
@@ -58,14 +76,17 @@
private void publishDir(IModule module2, List status, IProgressMonitor monitor) throws CoreException {
IPath path = server.getModuleDeployDirectory(module2);
- if (kind == IServer.PUBLISH_CLEAN || deltaKind == ServerBehaviourDelegate.REMOVED) { // clean and republish from scratch
+ // Remove if requested or if previously published and are now serving without publishing
+ if (kind == IServer.PUBLISH_CLEAN || deltaKind == ServerBehaviourDelegate.REMOVED
+ || server.getTomcatServer().isServeModulesWithoutPublish()) {
File f = path.toFile();
if (f.exists()) {
IStatus[] stat = PublishUtil.deleteDirectory(f, monitor);
addArrayToList(status, stat);
}
- if (deltaKind == ServerBehaviourDelegate.REMOVED)
+ if (deltaKind == ServerBehaviourDelegate.REMOVED
+ || server.getTomcatServer().isServeModulesWithoutPublish())
return;
}
@@ -90,11 +111,14 @@
path = path.append("WEB-INF").append("lib");
IPath jarPath = path.append(module[1].getName() + ".jar");
- if (kind == IServer.PUBLISH_CLEAN || deltaKind == ServerBehaviourDelegate.REMOVED) { // clean and republish from scratch
+ // Remove if requested or if previously published and are now serving without publishing
+ if (kind == IServer.PUBLISH_CLEAN || deltaKind == ServerBehaviourDelegate.REMOVED
+ || server.getTomcatServer().isServeModulesWithoutPublish()) {
if (jarPath.toFile().exists())
jarPath.toFile().delete();
- if (deltaKind == ServerBehaviourDelegate.REMOVED)
+ if (deltaKind == ServerBehaviourDelegate.REMOVED
+ || server.getTomcatServer().isServeModulesWithoutPublish())
return;
}
if (kind != IServer.PUBLISH_CLEAN && kind != IServer.PUBLISH_FULL) {
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat32Handler.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat32Handler.java
index e74c049..2e0d348 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat32Handler.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat32Handler.java
@@ -88,7 +88,7 @@
List list = new ArrayList();
list.add("-Dtomcat.home=\"" + installPath.toOSString() + "\"");
// Include a system property for the configurable deploy location
- list.add("-Dtomcat.deploy=\"" + deployPath.toOSString() + "\"");
+ list.add("-Dwtp.deploy=\"" + deployPath.toOSString() + "\"");
String[] s = new String[list.size()];
list.toArray(s);
@@ -146,4 +146,37 @@
return TomcatVersionHelper.createDeploymentDirectory(deployPath,
TomcatVersionHelper.DEFAULT_WEBXML_SERVLET22);
}
+
+ /**
+ * @see ITomcatVersionHandler#prepareForServingDirectly(IPath, TomcatServer)
+ */
+ public IStatus prepareForServingDirectly(IPath baseDir, TomcatServer server) {
+ if (server.isServeModulesWithoutPublish())
+ return new Status(IStatus.ERROR, TomcatPlugin.PLUGIN_ID, 0, Messages.errorNoPublishNotSupported, null);
+ return Status.OK_STATUS;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#getSharedLoader(IPath)
+ */
+ public String getSharedLoader(IPath baseDir) {
+ // Not supported
+ return null;
+ }
+
+ /**
+ * Returns false since Tomcat 3.2 doesn't support this feature.
+ *
+ * @return false since feature is not supported
+ */
+ public boolean supportsServeModulesWithoutPublish() {
+ return false;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#supportsDebugArgument()
+ */
+ public boolean supportsDebugArgument() {
+ return true;
+ }
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat40Handler.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat40Handler.java
index 17ac0cb..36eed35 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat40Handler.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat40Handler.java
@@ -141,4 +141,37 @@
return TomcatVersionHelper.createDeploymentDirectory(deployPath,
TomcatVersionHelper.DEFAULT_WEBXML_SERVLET23);
}
+
+ /**
+ * @see ITomcatVersionHandler#prepareForServingDirectly(IPath, TomcatServer)
+ */
+ public IStatus prepareForServingDirectly(IPath baseDir, TomcatServer server) {
+ if (server.isServeModulesWithoutPublish())
+ return new Status(IStatus.ERROR, TomcatPlugin.PLUGIN_ID, 0, Messages.errorNoPublishNotSupported, null);
+ return Status.OK_STATUS;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#getSharedLoader(IPath)
+ */
+ public String getSharedLoader(IPath baseDir) {
+ // Not supported
+ return null;
+ }
+
+ /**
+ * Returns false since Tomcat 4.0 doesn't support this feature.
+ *
+ * @return false since feature is not supported
+ */
+ public boolean supportsServeModulesWithoutPublish() {
+ return false;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#supportsDebugArgument()
+ */
+ public boolean supportsDebugArgument() {
+ return true;
+ }
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat41Handler.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat41Handler.java
index cf5f4d6..8b9ad2d 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat41Handler.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat41Handler.java
@@ -127,4 +127,37 @@
return TomcatVersionHelper.createDeploymentDirectory(deployPath,
TomcatVersionHelper.DEFAULT_WEBXML_SERVLET23);
}
+
+ /**
+ * @see ITomcatVersionHandler#prepareForServingDirectly(IPath, TomcatServer)
+ */
+ public IStatus prepareForServingDirectly(IPath baseDir, TomcatServer server) {
+ if (server.isServeModulesWithoutPublish())
+ return new Status(IStatus.ERROR, TomcatPlugin.PLUGIN_ID, 0, Messages.errorNoPublishNotSupported, null);
+ return Status.OK_STATUS;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#getSharedLoader(IPath)
+ */
+ public String getSharedLoader(IPath baseDir) {
+ // Not supported
+ return null;
+ }
+
+ /**
+ * Returns false since Tomcat 4.1 doesn't support this feature.
+ *
+ * @return false since feature is not supported
+ */
+ public boolean supportsServeModulesWithoutPublish() {
+ return false;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#supportsDebugArgument()
+ */
+ public boolean supportsDebugArgument() {
+ return true;
+ }
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Configuration.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Configuration.java
index 6d608de..8385035 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Configuration.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Configuration.java
@@ -609,7 +609,19 @@
protected IStatus publishContextConfig(IPath baseDir, IPath deployDir, IProgressMonitor monitor) {
return TomcatVersionHelper.publishCatalinaContextConfig(baseDir, deployDir, monitor);
}
-
+
+ /**
+ * Update contexts in server.xml to serve projects directly without
+ * publishing.
+ *
+ * @param baseDir path to catalina instance directory
+ * @param monitor a progress monitor or null
+ * @return result of operation
+ */
+ protected IStatus updateContextsToServeDirectly(IPath baseDir, String loader, IProgressMonitor monitor) {
+ return TomcatVersionHelper.updateContextsToServeDirectly(baseDir, loader, monitor);
+ }
+
/**
* Cleanup the server instance. This consists of deleting the work
* directory associated with Contexts that are going away in the
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Handler.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Handler.java
index d577ea5..fc60147 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Handler.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat50Handler.java
@@ -127,4 +127,54 @@
return TomcatVersionHelper.createDeploymentDirectory(deployPath,
TomcatVersionHelper.DEFAULT_WEBXML_SERVLET24);
}
+
+ /**
+ * @see ITomcatVersionHandler#prepareForServingDirectly(IPath, TomcatServer)
+ */
+ public IStatus prepareForServingDirectly(IPath baseDir, TomcatServer server) {
+ IStatus status;
+ // If serving modules without publishing, loader jar is needed
+ if (server.isServeModulesWithoutPublish()) {
+ status = TomcatVersionHelper.copyLoaderJar(
+ getRuntimeBaseDirectory(server).append("server/lib"),
+ server.getServer().getRuntime().getRuntimeType().getId());
+ // If copy successful and running a separate server instance, modify catalina.properties
+ if (status.isOK() && server.isTestEnvironment()) {
+ status = TomcatVersionHelper.updatePropertiesToServeDirectly(baseDir, "server/lib", "server");
+ }
+ }
+ // Else ensure jar is removed
+ else {
+ TomcatVersionHelper.removeLoaderJar(
+ getRuntimeBaseDirectory(server).append("server/lib"),
+ server.getServer().getRuntime().getRuntimeType().getId());
+ // TODO Decide what to do with removal warning, maybe nothing
+ status = Status.OK_STATUS;
+ }
+ return status;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#getSharedLoader(IPath)
+ */
+ public String getSharedLoader(IPath baseDir) {
+ // Use shared loader
+ return "shared";
+ }
+
+ /**
+ * Returns true since Tomcat 5.x supports this feature.
+ *
+ * @return true since feature is supported
+ */
+ public boolean supportsServeModulesWithoutPublish() {
+ return true;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#supportsDebugArgument()
+ */
+ public boolean supportsDebugArgument() {
+ return false;
+ }
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat55Configuration.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat55Configuration.java
index c19938e..61d5433 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat55Configuration.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat55Configuration.java
@@ -607,6 +607,18 @@
}
/**
+ * Update contexts in server.xml to serve projects directly without
+ * publishing.
+ *
+ * @param baseDir path to catalina instance directory
+ * @param monitor a progress monitor or null
+ * @return result of operation
+ */
+ protected IStatus updateContextsToServeDirectly(IPath baseDir, String loader, IProgressMonitor monitor) {
+ return TomcatVersionHelper.updateContextsToServeDirectly(baseDir, loader, monitor);
+ }
+
+ /**
* Cleanup the server instance. This consists of deleting the work
* directory associated with Contexts that are going away in the
* up coming publish.
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Configuration.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Configuration.java
index 24fd5d4..2e07671 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Configuration.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Configuration.java
@@ -609,6 +609,18 @@
}
/**
+ * Update contexts in server.xml to serve projects directly without
+ * publishing.
+ *
+ * @param baseDir path to catalina instance directory
+ * @param monitor a progress monitor or null
+ * @return result of operation
+ */
+ protected IStatus updateContextsToServeDirectly(IPath baseDir, String loader, IProgressMonitor monitor) {
+ return TomcatVersionHelper.updateContextsToServeDirectly(baseDir, loader, monitor);
+ }
+
+ /**
* Cleanup the server instance. This consists of deleting the work
* directory associated with Contexts that are going away in the
* up coming publish.
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Handler.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Handler.java
index c6eefbf..7ac82a2 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Handler.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/Tomcat60Handler.java
@@ -121,4 +121,54 @@
return TomcatVersionHelper.createDeploymentDirectory(deployPath,
TomcatVersionHelper.DEFAULT_WEBXML_SERVLET25);
}
+
+ /**
+ * @see ITomcatVersionHandler#prepareForServingDirectly(IPath, TomcatServer)
+ */
+ public IStatus prepareForServingDirectly(IPath baseDir, TomcatServer server) {
+ IStatus status;
+ // If serving modules without publishing, loader jar is needed
+ // TODO Need to examine catalina.properties to ensure loader jar and catalina.properties are handled appropriately
+ if (server.isServeModulesWithoutPublish()) {
+ status = TomcatVersionHelper.copyLoaderJar(
+ getRuntimeBaseDirectory(server).append("lib"),
+ server.getServer().getRuntime().getRuntimeType().getId());
+ // If copy successful and running a separate server instance, modify catalina.properties
+ if (status.isOK() && server.isTestEnvironment()) {
+ status = TomcatVersionHelper.updatePropertiesToServeDirectly(baseDir, "lib", "common");
+ }
+ }
+ // Else ensure jar is removed
+ else {
+ TomcatVersionHelper.removeLoaderJar(
+ getRuntimeBaseDirectory(server).append("lib"),
+ server.getServer().getRuntime().getRuntimeType().getId());
+ // TODO Decide what to do with removal warning, maybe nothing
+ status = Status.OK_STATUS;
+ }
+ return status;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#getSharedLoader(IPath)
+ */
+ public String getSharedLoader(IPath baseDir) {
+ return "common";
+ }
+
+ /**
+ * Returns true since Tomcat 6.x supports this feature.
+ *
+ * @return true since feature is supported
+ */
+ public boolean supportsServeModulesWithoutPublish() {
+ return true;
+ }
+
+ /**
+ * @see ITomcatVersionHandler#supportsDebugArgument()
+ */
+ public boolean supportsDebugArgument() {
+ return false;
+ }
}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatConfiguration.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatConfiguration.java
index ef9637c..15f636e 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatConfiguration.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatConfiguration.java
@@ -180,6 +180,11 @@
}
+ protected IStatus updateContextsToServeDirectly(IPath baseDir, String loader, IProgressMonitor monitor) {
+ // Default implementation assumes nothing to do
+ return Status.OK_STATUS;
+ }
+
protected IStatus cleanupServer(IPath confDir, IPath installDir, IProgressMonitor monitor) {
// Default implementation assumes nothing to clean
return Status.OK_STATUS;
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatPublishModuleVisitor.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatPublishModuleVisitor.java
new file mode 100644
index 0000000..3e5d360
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatPublishModuleVisitor.java
@@ -0,0 +1,331 @@
+/**********************************************************************
+ * Copyright (c) 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Igor Fedorenko & Fabrizio Giustina - Initial API and implementation
+ **********************************************************************/
+package org.eclipse.jst.server.tomcat.core.internal;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.LinkedHashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+import org.eclipse.jdt.core.IClasspathEntry;
+import org.eclipse.jst.server.tomcat.core.internal.wst.IModuleVisitor;
+import org.eclipse.jst.server.tomcat.core.internal.xml.Factory;
+import org.eclipse.jst.server.tomcat.core.internal.xml.server40.Context;
+import org.eclipse.jst.server.tomcat.core.internal.xml.server40.Loader;
+import org.eclipse.jst.server.tomcat.core.internal.xml.server40.ServerInstance;
+import org.eclipse.osgi.util.NLS;
+import org.eclipse.wst.common.componentcore.resources.IVirtualComponent;
+import org.eclipse.wst.common.componentcore.resources.IVirtualFile;
+import org.eclipse.wst.server.core.IModule;
+import org.eclipse.wst.server.core.ServerUtil;
+
+/**
+ * Handles "publishing" for servers that can load classes and resources directly
+ * from the workspace. Instead of creating and deploying jars to the webapp this
+ * simply update the virtual classpath in the context xml file.
+ */
+public class TomcatPublishModuleVisitor implements IModuleVisitor {
+
+ /**
+ * Server base path (Catalina base).
+ */
+ protected final IPath baseDir;
+
+ /**
+ * Server instance in which to modify the context
+ */
+ protected final ServerInstance serverInstance;
+
+ /**
+ * Catalina.properties loader to add global classpath entries
+ */
+ protected final String sharedLoader;
+
+ /**
+ * Classpath entries added by ear configurations.
+ */
+ protected final List earCommonResources = new ArrayList();
+
+ /**
+ * List of classpath elements that will be used by the custom tomcat loader.
+ * This set should include any class dir from referenced project.
+ */
+ protected Set virtualClasspathElements = new LinkedHashSet();
+
+ /**
+ * Instantiate a new TomcatPublishModuleVisitor
+ *
+ * @param catalinaBase catalina base path
+ * @param webModules list of
+ * <code>org.eclipse.jst.server.tomcat.core.internal.WebModule</code>
+ * configured for this server
+ */
+ TomcatPublishModuleVisitor(IPath catalinaBase, ServerInstance serverInstance, String sharedLoader) {
+ this.baseDir = catalinaBase;
+ this.serverInstance = serverInstance;
+ this.sharedLoader = sharedLoader;
+ }
+
+ /**
+ * @see IModuleVisitor#visitWebComponent(IVirtualComponent)
+ */
+ public void visitWebComponent(IVirtualComponent component)
+ throws CoreException {
+ // nothing to do, everything is done in endVisitWebComponent
+ }
+
+ /**
+ * @see IModuleVisitor#visitArchiveComponent(IPath, IPath)
+ */
+ public void visitArchiveComponent(IPath runtimePath, IPath workspacePath) {
+ addVirtualResource(runtimePath, workspacePath);
+ }
+
+ /**
+ * @see IModuleVisitor#visitDependentComponent(IPath, IPath)
+ */
+ public void visitDependentComponent(IPath runtimePath, IPath workspacePath) {
+ addVirtualResource(runtimePath, workspacePath);
+ }
+
+ /**
+ * @see IModuleVisitor#visitWebResource(IPath, IPath)
+ */
+ public void visitWebResource(IPath runtimePath, IPath workspacePath) {
+ addVirtualResource(runtimePath, workspacePath);
+ }
+
+ /**
+ * @see IModuleVisitor#visitEarResource(IPath, IPath)
+ */
+ public void visitEarResource(IPath runtimePath, IPath workspacePath) {
+ earCommonResources.add(workspacePath.toOSString());
+ }
+
+ /**
+ * @see IModuleVisitor#endVisitEarComponent(IVirtualComponent)
+ */
+ public void endVisitEarComponent(IVirtualComponent component)
+ throws CoreException {
+ if (earCommonResources.size() > 0) {
+ try {
+ CatalinaPropertiesUtil.addGlobalClasspath(baseDir.append(
+ "conf/catalina.properties").toFile(), sharedLoader,
+ (String[]) earCommonResources.toArray(new String[earCommonResources.size()]));
+ } catch (IOException e) {
+ Trace.trace(Trace.WARNING, "Unable to add ear path entries to catalina.properties", e);
+ } finally {
+ earCommonResources.clear();
+ }
+ }
+ }
+
+ /**
+ * @see IModuleVisitor#visitClasspathEntry(IPath, IClasspathEntry)
+ */
+ public void visitClasspathEntry(IPath rtFolder, IClasspathEntry entry) {
+ if (entry != null) {
+ addVirtualResource(rtFolder, entry.getPath());
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void endVisitWebComponent(IVirtualComponent component)
+ throws CoreException {
+
+ // track context changes, don't rewrite if not needed
+ boolean dirty = false;
+
+ IModule module = ServerUtil.getModule(component.getProject());
+
+ // we need this for the user-specified context path
+ Context context = findContext(module);
+ if (context == null) {
+ String name = module != null ? module.getName() : component.getName();
+ Trace.trace(Trace.SEVERE, "Could not find context for module " + name);
+ throw new CoreException(new Status(IStatus.ERROR, TomcatPlugin.PLUGIN_ID, 0,
+ NLS.bind(Messages.errorPublishContextNotFound, name), null));
+ }
+
+ String contextName = null;
+ boolean reloadable = true;
+
+ contextName = context.getPath();
+ reloadable = Boolean.valueOf(context.getReloadable()).booleanValue();
+
+ // now strip initial /
+ if (contextName.startsWith("/")) {
+ contextName = contextName.substring(1);
+ }
+
+ // root context is deployed with the "ROOT" name in tomcat
+ if ("".equals(contextName)) {
+ contextName = "ROOT";
+ }
+
+ // handle project context.xml
+ Context projectContext = getProjectContextXml(component);
+
+ if (projectContext != null) {
+ // copy configuration to server context
+ projectContext.copyChildrenTo(context);
+
+ Map attrs = projectContext.getAttributes();
+ Iterator iter = attrs.keySet().iterator();
+ while (iter.hasNext()) {
+ String name = (String) iter.next();
+ if (!name.equalsIgnoreCase("path")
+ && !name.equalsIgnoreCase("docBase")
+ && !name.equalsIgnoreCase("source")) {
+ String value = (String) attrs.get(name);
+ String actualValue = context.getAttributeValue(name);
+ if (!value.equals(actualValue)) {
+ context.setAttributeValue(name, value);
+ dirty = true;
+ }
+ }
+ }
+ }
+
+ // handle changes in docBase
+ String docBase = component.getRootFolder().getUnderlyingFolder()
+ .getLocation().toOSString();
+ if (!docBase.equals(context.getDocBase())) {
+ dirty = true;
+ context.setDocBase(docBase);
+ }
+
+ // handle changes in reloadable flag
+ if (reloadable != (Boolean.valueOf((context.getReloadable()))
+ .booleanValue())) {
+ dirty = true;
+ context.setReloadable(Boolean.toString(reloadable));
+ }
+
+ String path = (contextName.equals("ROOT") ? "" : "/" + contextName);
+ // handle changes in the path
+ // PATH is required for tomcat 5.0, but ignored in tomcat 5.5
+ if (!path.equals(context.getPath())) {
+ dirty = true;
+ context.setPath(path);
+ }
+
+ context.getResources().setClassName(
+ "org.eclipse.jst.server.tomcat.loader.WtpDirContext");
+
+ Loader loader = context.getLoader();
+
+ loader.setClassName("org.eclipse.jst.server.tomcat.loader.WtpWebappLoader");
+
+ // required for tomcat 5.5.20 due to the change in
+ // http://issues.apache.org/bugzilla/show_bug.cgi?id=39704
+ loader.setUseSystemClassLoaderAsParent(Boolean.FALSE.toString());
+
+ // write down the virtual classPath
+ StringBuffer buffer = new StringBuffer();
+ for (Iterator iterator = virtualClasspathElements.iterator(); iterator
+ .hasNext();) {
+ buffer.append(iterator.next());
+ if (iterator.hasNext()) {
+ buffer.append(";");
+ }
+ }
+ virtualClasspathElements.clear();
+
+ String vcp = buffer.toString();
+
+ String oldVcp = loader.getVirtualClasspath();
+
+ if (!vcp.equals(oldVcp)) {
+ // save only if needed
+ dirty = true;
+ loader.setVirtualClasspath(vcp);
+ context.getResources().setVirtualClasspath(vcp);
+ }
+
+ if (dirty) {
+ //TODO If writing to separate context XML files, save "dirty" status for later use
+ }
+ }
+
+ private void addVirtualResource(IPath runtimePath, IPath workspacePath) {
+ virtualClasspathElements.add(workspacePath.toOSString());
+ }
+
+ /**
+ * Load a META-INF/context.xml file from project, if available
+ *
+ * @param component web component containing the context.xml
+ * @return context element containing the context.xml
+ * @throws CoreException
+ */
+ protected Context getProjectContextXml(IVirtualComponent component)
+ throws CoreException {
+
+ // load or create module's context.xml document
+ IVirtualFile contextFile = (IVirtualFile) component.getRootFolder()
+ .findMember("META-INF/context.xml");
+
+ Context contextElement = null;
+
+ if (contextFile != null && contextFile.exists()) {
+
+ Factory factory = new Factory();
+ factory.setPackageName("org.eclipse.jst.server.tomcat.core.internal.xml.server40");
+
+ InputStream fis = null;
+ try {
+ fis = contextFile.getUnderlyingFile().getContents();
+ contextElement = (Context) factory.loadDocument(fis);
+ } catch (Exception e) {
+ Trace.trace(Trace.SEVERE, "Exception reading " + contextFile, e);
+ } finally {
+ try {
+ fis.close();
+ } catch (IOException e) {
+ // ignore
+ }
+ }
+ }
+ return contextElement;
+ }
+
+ /**
+ * Returns the given module from the config.
+ *
+ * @param module a web module
+ * @return a web module
+ */
+ protected Context findContext(IModule module) {
+ if (module == null) {
+ return null;
+ }
+
+ String source = module.getId();
+
+ Context [] contexts = serverInstance.getContexts();
+ for (int i = 0; i < contexts.length; i++) {
+ if (source.equals(contexts[i].getSource()))
+ return contexts[i];
+ }
+ return null;
+ }
+}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServer.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServer.java
index 3476538..6106f14 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServer.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServer.java
@@ -219,6 +219,18 @@
// Default to value used by prior WTP versions
return getAttribute(PROPERTY_DEPLOY_DIR, LEGACY_DEPLOYDIR);
}
+
+ /**
+ * Returns true if modules should be served without publishing.
+ *
+ * @return boolean
+ */
+ public boolean isServeModulesWithoutPublish() {
+ // If feature is supported, return current setting
+ if (versionHandler.supportsServeModulesWithoutPublish())
+ return getAttribute(PROPERTY_SERVE_MODULES_WITHOUT_PUBLISH, false);
+ return false;
+ }
/**
* Gets the base directory where the server instance runs. This
@@ -262,8 +274,10 @@
return buf.toString();
}
- /*
+ /**
* Returns the child module(s) of this module.
+ * @param module module from which to get child module(s)
+ * @return array of child module(s)
*/
public IModule[] getChildModules(IModule[] module) {
if (module == null)
@@ -283,8 +297,11 @@
return new IModule[0];
}
- /*
+ /**
* Returns the root module(s) of this module.
+ * @param module module from which to get the root module
+ * @return root module
+ * @throws CoreException
*/
public IModule[] getRootModules(IModule module) throws CoreException {
if ("jst.web".equals(module.getModuleType().getId())) {
@@ -397,6 +414,13 @@
else
setAttribute(PROPERTY_DEPLOY_DIR, deployDir);
}
+
+ /**
+ * @see ITomcatServerWorkingCopy#setServeModulesWithoutPublish(boolean)
+ */
+ public void setServeModulesWithoutPublish(boolean b) {
+ setAttribute(PROPERTY_SERVE_MODULES_WITHOUT_PUBLISH, b);
+ }
/**
* @see ServerDelegate#modifyModules(IModule[], IModule[], IProgressMonitor)
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServerBehaviour.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServerBehaviour.java
index b9607e1..11f8c41 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServerBehaviour.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatServerBehaviour.java
@@ -18,6 +18,7 @@
import java.util.List;
import java.util.Properties;
+import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.*;
import org.eclipse.debug.core.*;
import org.eclipse.debug.core.model.IProcess;
@@ -125,8 +126,17 @@
protected String[] getRuntimeVMArguments() {
IPath installPath = getServer().getRuntime().getLocation();
IPath configPath = getRuntimeBaseDirectory();
+ IPath deployPath;
+ // If serving modules without publishing, use workspace path as the deploy path
+ if (getTomcatServer().isServeModulesWithoutPublish()) {
+ deployPath = ResourcesPlugin.getWorkspace().getRoot().getLocation();
+ }
+ // Else normal publishing for modules
+ else {
+ deployPath = getServerDeployDirectory();
+ }
return getTomcatVersionHandler().getRuntimeVMArguments(installPath, configPath,
- getServerDeployDirectory(), getTomcatServer().isTestEnvironment());
+ deployPath, getTomcatServer().isTestEnvironment());
}
protected String getRuntimePolicyFile() {
@@ -276,16 +286,20 @@
*/
private void publishDir(int deltaKind, Properties p, IModule module[], IProgressMonitor monitor) throws CoreException {
List status = new ArrayList();
- if (deltaKind == REMOVED) {
- try {
- String publishPath = (String) p.get(module[0].getId());
- File f = new File(publishPath);
- if (f.exists()) {
- IStatus[] stat = PublishUtil.deleteDirectory(f, monitor);
- PublishOperation2.addArrayToList(status, stat);
+ // Remove if requested or if previously published and are now serving without publishing
+ if (deltaKind == REMOVED || getTomcatServer().isServeModulesWithoutPublish()) {
+ String publishPath = (String) p.get(module[0].getId());
+ if (publishPath != null) {
+ try {
+ File f = new File(publishPath);
+ if (f.exists()) {
+ IStatus[] stat = PublishUtil.deleteDirectory(f, monitor);
+ PublishOperation2.addArrayToList(status, stat);
+ }
+ } catch (Exception e) {
+ throw new CoreException(new Status(IStatus.WARNING, TomcatPlugin.PLUGIN_ID, 0,
+ NLS.bind(Messages.errorPublishCouldNotRemoveModule,module[0].getName()), e));
}
- } catch (Exception e) {
- throw new CoreException(new Status(IStatus.WARNING, TomcatPlugin.PLUGIN_ID, 0, "Could not remove module", e));
}
} else {
IPath path = getModuleDeployDirectory(module[0]);
@@ -307,7 +321,8 @@
* @throws CoreException
*/
private void publishJar(int kind, int deltaKind, Properties p, IModule[] module, IProgressMonitor monitor) throws CoreException {
- if (deltaKind == REMOVED) {
+ // Remove if requested or if previously published and are now serving without publishing
+ if (deltaKind == REMOVED || getTomcatServer().isServeModulesWithoutPublish()) {
try {
String publishPath = (String) p.get(module[1].getId());
new File(publishPath).delete();
@@ -340,9 +355,24 @@
}
protected void publishFinish(IProgressMonitor monitor) throws CoreException {
- // Publish context configuration for servers that support META-INF/context.xml
- IStatus status = getTomcatConfiguration().publishContextConfig(
- getRuntimeBaseDirectory(), getServerDeployDirectory(), monitor);
+ IStatus status;
+ IPath baseDir = getRuntimeBaseDirectory();
+ ITomcatVersionHandler tvh = getTomcatVersionHandler();
+ // Include or remove loader jar depending on state of serving directly
+ status = tvh.prepareForServingDirectly(baseDir, getTomcatServer());
+ if (status.isOK()) {
+ // If serving modules directly, update server.xml accordingly (includes project context.xmls)
+ if (getTomcatServer().isServeModulesWithoutPublish()) {
+ status = getTomcatConfiguration().updateContextsToServeDirectly(
+ baseDir, tvh.getSharedLoader(baseDir), monitor);
+ }
+ // Else serving normally. Add project context.xmls to server.xml
+ else {
+ // Publish context configuration for servers that support META-INF/context.xml
+ status = getTomcatConfiguration().publishContextConfig(
+ baseDir, getServerDeployDirectory(), monitor);
+ }
+ }
if (!status.isOK())
throw new CoreException(status);
}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatSourcePathComputerDelegate.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatSourcePathComputerDelegate.java
index 572bfc9..b9a67e2 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatSourcePathComputerDelegate.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatSourcePathComputerDelegate.java
@@ -1,5 +1,5 @@
/**********************************************************************
- * Copyright (c) 2004, 2005 IBM Corporation and others.
+ * Copyright (c) 2004, 2005, 2006, 2007 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@@ -14,85 +14,137 @@
import java.util.Arrays;
import java.util.List;
-import org.eclipse.core.resources.IFolder;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.debug.core.ILaunchConfiguration;
import org.eclipse.debug.core.sourcelookup.ISourceContainer;
import org.eclipse.debug.core.sourcelookup.ISourcePathComputerDelegate;
-import org.eclipse.debug.core.sourcelookup.containers.FolderSourceContainer;
+import org.eclipse.jdt.core.IClasspathEntry;
import org.eclipse.jdt.core.IJavaProject;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.launching.IRuntimeClasspathEntry;
import org.eclipse.jdt.launching.JavaRuntime;
+import org.eclipse.jst.server.tomcat.core.internal.wst.IModuleVisitor;
+import org.eclipse.jst.server.tomcat.core.internal.wst.ModuleTraverser;
+import org.eclipse.wst.common.componentcore.resources.IVirtualComponent;
import org.eclipse.wst.server.core.IModule;
import org.eclipse.wst.server.core.IServer;
import org.eclipse.wst.server.core.ServerUtil;
+
/**
- *
+ *
*/
-public class TomcatSourcePathComputerDelegate implements ISourcePathComputerDelegate {
- /* (non-Javadoc)
- * @see org.eclipse.debug.core.sourcelookup.ISourcePathComputerDelegate#computeSourceContainers(org.eclipse.debug.core.ILaunchConfiguration, org.eclipse.core.runtime.IProgressMonitor)
+public class TomcatSourcePathComputerDelegate implements
+ ISourcePathComputerDelegate {
+
+ /**
+ * {@inheritDoc}
*/
- public ISourceContainer[] computeSourceContainers(ILaunchConfiguration configuration, IProgressMonitor monitor) throws CoreException {
- List classpaths = new ArrayList();
- classpaths.addAll(Arrays.asList(JavaRuntime.computeUnresolvedSourceLookupPath(configuration)));
- List sourcefolderList = new ArrayList();
-
+ public ISourceContainer[] computeSourceContainers(
+ ILaunchConfiguration configuration, IProgressMonitor monitor)
+ throws CoreException {
IServer server = ServerUtil.getServer(configuration);
- if (server != null) {
- //IPath basePath = ((TomcatServerBehaviour)server.getAdapter(TomcatServerBehaviour.class)).getRuntimeBaseDirectory();
- List list = new ArrayList();
- //List pathList = new ArrayList();
- IModule[] modules = server.getModules();
- for (int i = 0; i < modules.length; i++) {
- IProject project = modules[i].getProject();
- if (project != null) {
- IFolder moduleFolder = project.getFolder(modules[i].getName());
- if (moduleFolder.exists()) {
- sourcefolderList.add(new FolderSourceContainer(moduleFolder, true));
- }
-
- try {
- if (project.hasNature(JavaCore.NATURE_ID)) {
- IJavaProject javaProject = (IJavaProject) project.getNature(JavaCore.NATURE_ID);
- if (!list.contains(javaProject))
- list.add(javaProject);
- }
- } catch (Exception e) {
- // ignore
- }
-
- //IPath path = basePath.append("work").append("Catalina").append("localhost").append(modules[i].getName());
- //pathList.add(path);
- }
+
+ SourcePathComputerVisitor visitor = new SourcePathComputerVisitor(
+ configuration);
+
+ IModule[] modules = server.getModules();
+ for (int i = 0; i < modules.length; i++) {
+ ModuleTraverser.traverse(modules[i], visitor, monitor);
+ }
+
+ return visitor.getSourceContainers();
+ }
+
+ class SourcePathComputerVisitor implements IModuleVisitor {
+
+ final ILaunchConfiguration configuration;
+
+ /**
+ * List<IRuntimeClasspathEntry> of unresolved IRuntimeClasspathEntries
+ */
+ List runtimeClasspath = new ArrayList();
+
+ SourcePathComputerVisitor(ILaunchConfiguration configuration) {
+ this.configuration = configuration;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void visitWebComponent(IVirtualComponent component)
+ throws CoreException {
+ IProject project = component.getProject();
+ if (project.hasNature(JavaCore.NATURE_ID)) {
+ IJavaProject javaProject = JavaCore.create(project);
+ runtimeClasspath.add(JavaRuntime
+ .newDefaultProjectClasspathEntry(javaProject));
}
- int size = list.size();
- IJavaProject[] projects = new IJavaProject[size];
- list.toArray(projects);
-
- for (int i = 0; i < size; i++)
- classpaths.addAll(Arrays.asList(JavaRuntime.computeUnresolvedRuntimeClasspath(projects[i])));
-
- // for (int i = 0; i < size3; i++)
- // entries2[size + size2 + i] = JavaRuntime.newArchiveRuntimeClasspathEntry((IPath) pathList.get(i));
}
- IRuntimeClasspathEntry[] entries = new IRuntimeClasspathEntry[classpaths.size()];
- classpaths.toArray(entries);
-
- IRuntimeClasspathEntry[] resolved = JavaRuntime.resolveSourceLookupPath(entries, configuration);
- ISourceContainer[] sourceContainers = JavaRuntime.getSourceContainers(resolved);
-
- if (!sourcefolderList.isEmpty()) {
- ISourceContainer[] combinedSourceContainers = new ISourceContainer[sourceContainers.length + sourcefolderList.size()];
- sourcefolderList.toArray(combinedSourceContainers);
- System.arraycopy(sourceContainers, 0, combinedSourceContainers, sourcefolderList.size(), sourceContainers.length);
- sourceContainers = combinedSourceContainers;
+ /**
+ * {@inheritDoc}
+ */
+ public void endVisitWebComponent(IVirtualComponent component)
+ throws CoreException {
+ // do nothing
}
- return sourceContainers;
+ /**
+ * {@inheritDoc}
+ */
+ public void visitArchiveComponent(IPath runtimePath, IPath workspacePath) {
+ // do nothing
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void visitDependentComponent(IPath runtimePath,
+ IPath workspacePath) {
+ // do nothing
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void visitWebResource(IPath runtimePath, IPath workspacePath) {
+ // do nothing
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void visitEarResource(IPath runtimePath, IPath workspacePath) {
+ // do nothing
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void endVisitEarComponent(IVirtualComponent component)
+ throws CoreException {
+ // do nothing
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void visitClasspathEntry(IPath rtFolder, IClasspathEntry entry) {
+ // do nothing
+ }
+
+ ISourceContainer[] getSourceContainers() throws CoreException {
+ runtimeClasspath.addAll(Arrays.asList(JavaRuntime
+ .computeUnresolvedSourceLookupPath(configuration)));
+ IRuntimeClasspathEntry[] entries = (IRuntimeClasspathEntry[]) runtimeClasspath
+ .toArray(new IRuntimeClasspathEntry[runtimeClasspath.size()]);
+ IRuntimeClasspathEntry[] resolved = JavaRuntime
+ .resolveSourceLookupPath(entries, configuration);
+ return JavaRuntime.getSourceContainers(resolved);
+ }
+
}
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatVersionHelper.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatVersionHelper.java
index 7bff3f2..1d733de 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatVersionHelper.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/TomcatVersionHelper.java
@@ -18,6 +18,7 @@
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
+import java.net.URL;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashSet;
@@ -27,6 +28,7 @@
import java.util.Set;
import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.FileLocator;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
@@ -34,11 +36,14 @@
import org.eclipse.core.runtime.Path;
import org.eclipse.core.runtime.Status;
import org.eclipse.jst.server.core.PublishUtil;
+import org.eclipse.jst.server.tomcat.core.internal.wst.ModuleTraverser;
import org.eclipse.jst.server.tomcat.core.internal.xml.Factory;
import org.eclipse.jst.server.tomcat.core.internal.xml.server40.Context;
import org.eclipse.jst.server.tomcat.core.internal.xml.server40.Server;
import org.eclipse.jst.server.tomcat.core.internal.xml.server40.ServerInstance;
import org.eclipse.osgi.util.NLS;
+import org.eclipse.wst.server.core.IModule;
+import org.eclipse.wst.server.core.ServerUtil;
import org.xml.sax.SAXException;
/**
@@ -155,7 +160,7 @@
list.add("-Dcatalina.base=\"" + installPath.toOSString() + "\"");
list.add("-Dcatalina.home=\"" + installPath.toOSString() + "\"");
// Include a system property for the configurable deploy location
- list.add("-Dcatalina.deploy=\"" + deployPath.toOSString() + "\"");
+ list.add("-Dwtp.deploy=\"" + deployPath.toOSString() + "\"");
list.add("-Djava.endorsed.dirs=\"" + installPath.append("common").append("endorsed").toOSString() + "\"");
String[] s = new String[list.size()];
@@ -598,4 +603,132 @@
}
return Status.OK_STATUS;
}
+
+ /**
+ * Copies the custom loader jar required to serve projects without
+ * publishing to the specified destination directory.
+ *
+ * @param destDir destination directory for the loader jar
+ * @param serverId ID of the server receiving the jar
+ * @return result of copy operation
+ */
+ public static IStatus copyLoaderJar(IPath destDir, String serverId) {
+ String loaderJar = "/" + serverId + ".loader.jar";
+ URL installURL = TomcatPlugin.getInstance().getBundle().getEntry(loaderJar);
+ if (installURL == null) {
+ Trace.trace(Trace.SEVERE, "Loader jar not found for server ID " + serverId);
+ return new Status(IStatus.ERROR, TomcatPlugin.PLUGIN_ID, 0, NLS.bind(Messages.errorPublishLoaderJarNotFound, serverId), null);
+ }
+
+ URL localURL;
+ try {
+ localURL = FileLocator.toFileURL(installURL);
+ } catch (IOException e) {
+ Trace.trace(Trace.SEVERE, "Could not convert " + installURL.toString() + " to file URL: " + e.getMessage());
+ return new Status(IStatus.ERROR, TomcatPlugin.PLUGIN_ID, 0, NLS.bind(Messages.errorPublishURLConvert,
+ new String[] {installURL.toString(), e.getLocalizedMessage()}), e);
+ }
+
+ destDir.toFile().mkdirs();
+ IStatus status = FileUtil.copyFile(localURL, destDir.append(loaderJar).toString());
+
+ return status;
+ }
+
+ /**
+ * Tries to delete the custom loader jar added to support serving projects directly
+ * without publishing. Returns a warning if not successful.
+ *
+ * @param destDir destination directory containing the loader jar
+ * @param serverId ID of the server from which to delete the jar
+ * @return result of copy operation
+ */
+ public static IStatus removeLoaderJar(IPath destDir, String serverId) {
+ String loaderJar = "/" + serverId + ".loader.jar";
+ File loaderFile = destDir.append(loaderJar).toFile();
+ // If loader jar exists but is not successfully deleted, return warning
+ if (loaderFile.exists() && !loaderFile.delete())
+ return new Status(IStatus.WARNING, TomcatPlugin.PLUGIN_ID, 0,
+ NLS.bind(Messages.errorPublishCantDeleteLoaderJar, loaderFile.getPath()), null);
+
+ return Status.OK_STATUS;
+ }
+ /**
+ * Updates the catalina.properties file to include a extra entry in the
+ * specified loader property to pickup the loader jar.
+ *
+ * @param baseDir directory where the Catalina instance is found
+ * @param jarLoc location of loader jar relative to baseDir
+ * @param loader loader in catalina.properties to use
+ * @return result of update operation
+ */
+ public static IStatus updatePropertiesToServeDirectly(IPath baseDir, String jarLoc, String loader) {
+ File catalinaProperties = baseDir.append(
+ "conf/catalina.properties").toFile();
+ try {
+ CatalinaPropertiesUtil.addGlobalClasspath(catalinaProperties, loader,
+ new String[] { "${catalina.base}/" + jarLoc + "/*.jar" });
+
+ } catch (IOException e) {
+ return new Status(IStatus.ERROR,TomcatPlugin.PLUGIN_ID,
+ NLS.bind(Messages.errorPublishCatalinaProps, e.getLocalizedMessage()), e);
+ }
+ return Status.OK_STATUS;
+ }
+
+ /**
+ * Update Contexts to serve web projects directly.
+ *
+ * @param baseDir directory where the Catalina instance is found
+ * @param loader name of the catalina.properties loader to use for global
+ * classpath entries
+ * @param monitor a progress monitor
+ * @return result of update operation
+ */
+ public static IStatus updateContextsToServeDirectly(IPath baseDir, String loader, IProgressMonitor monitor) {
+
+ IPath confDir = baseDir.append("conf");
+ IPath serverXml = confDir.append("server.xml");
+ try {
+ monitor = ProgressUtil.getMonitorFor(monitor);
+ monitor.beginTask(Messages.publishConfigurationTask, 300);
+
+ monitor.subTask(Messages.publishContextConfigTask);
+ Factory factory = new Factory();
+ factory.setPackageName("org.eclipse.jst.server.tomcat.core.internal.xml.server40");
+ Server publishedServer = (Server) factory.loadDocument(new FileInputStream(serverXml.toFile()));
+ ServerInstance publishedInstance = new ServerInstance(publishedServer, null, null);
+ monitor.worked(100);
+
+ boolean modified = false;
+
+ // care about top-level modules only
+ TomcatPublishModuleVisitor visitor = new TomcatPublishModuleVisitor(
+ baseDir, publishedInstance, loader);
+ Context [] contexts = publishedInstance.getContexts();
+ for (int i = 0; i < contexts.length; i++) {
+ String moduleId = contexts[i].getSource();
+ if (moduleId != null && moduleId.length() > 0) {
+ IModule module = ServerUtil.getModule(moduleId);
+ ModuleTraverser.traverse(module, visitor, monitor);
+ modified = true;
+ }
+ }
+
+ if (modified) {
+ monitor.subTask(Messages.savingContextConfigTask);
+ factory.save(serverXml.toOSString());
+ }
+ monitor.worked(100);
+ if (Trace.isTraceEnabled())
+ Trace.trace(Trace.FINER, "Context docBase settings updated in server.xml.");
+ } catch (Exception e) {
+ Trace.trace(Trace.SEVERE, "Could not modify context configurations to serve directly for Tomcat configuration " + confDir.toOSString() + ": " + e.getMessage());
+ return new Status(IStatus.ERROR, TomcatPlugin.PLUGIN_ID, 0, NLS.bind(Messages.errorPublishConfiguration, new String[] {e.getLocalizedMessage()}), e);
+ }
+ finally {
+ monitor.done();
+ }
+ return Status.OK_STATUS;
+ }
}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/command/SetServeModulesWithoutPublishCommand.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/command/SetServeModulesWithoutPublishCommand.java
new file mode 100644
index 0000000..9eff331
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/command/SetServeModulesWithoutPublishCommand.java
@@ -0,0 +1,48 @@
+/*******************************************************************************
+ * Copyright (c) 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * IBM Corporation - Initial API and implementation
+ *******************************************************************************/
+package org.eclipse.jst.server.tomcat.core.internal.command;
+
+import org.eclipse.jst.server.tomcat.core.internal.ITomcatServerWorkingCopy;
+import org.eclipse.jst.server.tomcat.core.internal.Messages;
+/**
+ * Command to enable or disable serving modules without publishing
+ */
+public class SetServeModulesWithoutPublishCommand extends ServerCommand {
+ protected boolean smwp;
+ protected boolean oldSmwp;
+
+ /**
+ * SetTestEnvironmentCommand constructor comment.
+ *
+ * @param server a Tomcat server
+ * @param smwp <code>true</code> to enable serving modules without
+ * publishing. Otherwise modules are served with standard publishing.
+ */
+ public SetServeModulesWithoutPublishCommand(ITomcatServerWorkingCopy server, boolean smwp) {
+ super(server, Messages.serverEditorActionSetServeWithoutPublish);
+ this.smwp = smwp;
+ }
+
+ /**
+ * Execute the command.
+ */
+ public void execute() {
+ oldSmwp = server.isServeModulesWithoutPublish();
+ server.setServeModulesWithoutPublish(smwp);
+ }
+
+ /**
+ * Undo the command.
+ */
+ public void undo() {
+ server.setServeModulesWithoutPublish(oldSmwp);
+ }
+}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/command/SetTestEnvironmentCommand.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/command/SetTestEnvironmentCommand.java
index 53eb6c3..394df2d 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/command/SetTestEnvironmentCommand.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/command/SetTestEnvironmentCommand.java
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2003, 2005 IBM Corporation and others.
+ * Copyright (c) 2003, 2005, 2007 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/wst/IModuleVisitor.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/wst/IModuleVisitor.java
new file mode 100644
index 0000000..b31bc25
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/wst/IModuleVisitor.java
@@ -0,0 +1,78 @@
+/**********************************************************************
+ * Copyright (c) 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Igor Fedorenko & Fabrizio Giustina - Initial API and implementation
+ **********************************************************************/
+package org.eclipse.jst.server.tomcat.core.internal.wst;
+
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.jdt.core.IClasspathEntry;
+import org.eclipse.wst.common.componentcore.resources.IVirtualComponent;
+
+/**
+ * Visitor interface to process module components
+ */
+public interface IModuleVisitor {
+
+ /**
+ * Process web component
+ * @param component web component to process
+ * @throws CoreException
+ */
+ void visitWebComponent(IVirtualComponent component) throws CoreException;
+
+ /**
+ * Post process web component
+ * @param component web componet to process
+ * @throws CoreException
+ */
+ void endVisitWebComponent(IVirtualComponent component) throws CoreException;
+
+ /**
+ * Process archive component.
+ * @param runtimePath path for component at runtime
+ * @param workspacePath path to component in workspace
+ */
+ void visitArchiveComponent(IPath runtimePath, IPath workspacePath);
+
+ /**
+ * Process dependent component.
+ * @param runtimePath path for component at runtime
+ * @param workspacePath path to component in workspace
+ */
+ void visitDependentComponent(IPath runtimePath, IPath workspacePath);
+
+ /**
+ * Process web resource.
+ * @param runtimePath path for resource at runtime
+ * @param workspacePath path to resource in workspace
+ */
+ void visitWebResource(IPath runtimePath, IPath workspacePath);
+
+ /**
+ * Process EAR resource.
+ * @param runtimePath path for resource at runtime
+ * @param workspacePath path to resource in workspace
+ */
+ void visitEarResource(IPath runtimePath, IPath workspacePath);
+
+ /**
+ * Post process EAR resource.
+ * @param component EAR componet to process
+ * @throws CoreException
+ */
+ void endVisitEarComponent(IVirtualComponent component) throws CoreException;
+
+ /**
+ * Process a classpath entry.
+ * @param rtFolder path for class folder at runtime
+ * @param entry classpath entry
+ */
+ void visitClasspathEntry(IPath rtFolder, IClasspathEntry entry);
+}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/wst/ModuleTraverser.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/wst/ModuleTraverser.java
new file mode 100644
index 0000000..02aa3f2
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/wst/ModuleTraverser.java
@@ -0,0 +1,273 @@
+/**********************************************************************
+ * Copyright (c) 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Igor Fedorenko & Fabrizio Giustina - Initial API and implementation
+ **********************************************************************/
+package org.eclipse.jst.server.tomcat.core.internal.wst;
+
+import java.util.Iterator;
+import java.util.List;
+
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.resources.ResourcesPlugin;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.emf.common.util.URI;
+import org.eclipse.jdt.core.IClasspathEntry;
+import org.eclipse.jdt.core.IJavaProject;
+import org.eclipse.jdt.core.JavaCore;
+import org.eclipse.jdt.core.JavaModelException;
+import org.eclipse.jst.j2ee.componentcore.util.EARArtifactEdit;
+import org.eclipse.jst.server.tomcat.core.internal.TomcatPlugin;
+import org.eclipse.jst.server.tomcat.core.internal.Trace;
+import org.eclipse.wst.common.componentcore.ComponentCore;
+import org.eclipse.wst.common.componentcore.UnresolveableURIException;
+import org.eclipse.wst.common.componentcore.internal.ComponentResource;
+import org.eclipse.wst.common.componentcore.internal.ReferencedComponent;
+import org.eclipse.wst.common.componentcore.internal.StructureEdit;
+import org.eclipse.wst.common.componentcore.internal.WorkbenchComponent;
+import org.eclipse.wst.common.componentcore.internal.impl.ModuleURIUtil;
+import org.eclipse.wst.common.componentcore.internal.impl.PlatformURLModuleConnection;
+import org.eclipse.wst.common.componentcore.internal.resources.VirtualArchiveComponent;
+import org.eclipse.wst.common.componentcore.internal.util.IModuleConstants;
+import org.eclipse.wst.common.componentcore.resources.IVirtualComponent;
+import org.eclipse.wst.common.componentcore.resources.IVirtualReference;
+import org.eclipse.wst.server.core.IModule;
+
+/**
+ * Temporary solution for https://bugs.eclipse.org/bugs/show_bug.cgi?id=103888
+ */
+public class ModuleTraverser {
+
+ /**
+ * Facet type for EAR modules
+ */
+ public static final String EAR_MODULE = IModuleConstants.JST_EAR_MODULE;
+
+ /**
+ * Facet type for Web modules
+ */
+ public static final String WEB_MODULE = IModuleConstants.JST_WEB_MODULE;
+
+ /**
+ * Facet type for utility modules
+ */
+ public static final String UTILITY_MODULE = IModuleConstants.JST_UTILITY_MODULE;
+
+ /**
+ * Scans the module using the specified visitor.
+ *
+ * @param module module to traverse
+ * @param visitor visitor to handle resources
+ * @param monitor a progress monitor
+ * @throws CoreException
+ */
+ public static void traverse(IModule module, IModuleVisitor visitor,
+ IProgressMonitor monitor) throws CoreException {
+ if (module == null || module.getModuleType() == null)
+ return;
+
+ String typeId = module.getModuleType().getId();
+ IVirtualComponent component = ComponentCore.createComponent(module.getProject());
+
+ if (component == null) {
+ // can happen if project has been closed
+ Trace.trace(Trace.WARNING, "Unable to create component for module "
+ + module.getName());
+ return;
+ }
+
+ if (EAR_MODULE.equals(typeId)) {
+ traverseEarComponent(component, visitor, monitor);
+ } else if (WEB_MODULE.equals(typeId)) {
+ traverseWebComponent(component, visitor, monitor);
+ }
+ }
+
+ private static void traverseEarComponent(IVirtualComponent component,
+ IModuleVisitor visitor, IProgressMonitor monitor)
+ throws CoreException {
+ EARArtifactEdit earEdit = EARArtifactEdit
+ .getEARArtifactEditForRead(component);
+ if (earEdit != null) {
+ IVirtualReference[] j2eeComponents = earEdit.getJ2EEModuleReferences();
+ for (int i = 0; i < j2eeComponents.length; i++) {
+ traverseWebComponent(
+ j2eeComponents[i].getReferencedComponent(), visitor,
+ monitor);
+ }
+ IVirtualReference[] jarComponents = earEdit.getUtilityModuleReferences();
+ for (int i = 0; i < jarComponents.length; i++) {
+ IVirtualReference jarReference = jarComponents[i];
+ IVirtualComponent jarComponent = jarReference
+ .getReferencedComponent();
+ IProject dependentProject = jarComponent.getProject();
+ if (!dependentProject.hasNature(JavaCore.NATURE_ID))
+ continue;
+ IJavaProject project = JavaCore.create(dependentProject);
+ IClasspathEntry cpe = getClasspathEntry(project, jarComponent
+ .getRootFolder().getProjectRelativePath());
+ visitor.visitEarResource(null, getOSPath(dependentProject,
+ project, cpe.getOutputLocation()));
+ }
+ }
+ visitor.endVisitEarComponent(component);
+ }
+
+ private static void traverseWebComponent(IVirtualComponent component,
+ IModuleVisitor visitor, IProgressMonitor monitor)
+ throws CoreException {
+
+ visitor.visitWebComponent(component);
+
+ IProject proj = component.getProject();
+ StructureEdit warStruct = StructureEdit.getStructureEditForRead(proj);
+ try {
+ WorkbenchComponent comp = warStruct.getComponent();
+ if (comp == null) {
+ Trace.trace(Trace.SEVERE,
+ "Error getting WorkbenchComponent from war project. IProject=\""
+ + proj + "\" StructureEdit=\"" + warStruct
+ + "\" WorkbenchComponent=\"" + comp + "\"");
+ return;
+ }
+ traverseWebComponentLocalEntries(comp, visitor, monitor);
+
+ // traverse referenced components
+ List children = comp.getReferencedComponents();
+ for (Iterator itor = children.iterator(); itor.hasNext();) {
+ ReferencedComponent childRef = (ReferencedComponent) itor.next();
+ IPath rtFolder = childRef.getRuntimePath();
+ URI refHandle = childRef.getHandle();
+
+ if (PlatformURLModuleConnection.CLASSPATH.equals(
+ refHandle.segment(ModuleURIUtil.ModuleURI.SUB_PROTOCOL_INDX))) {
+ IJavaProject jproj = JavaCore.create(proj);
+ String classpathKind = refHandle.segment(1);
+ IPath classpathRef = getSuffixPath(refHandle, 2);
+
+ visitor.visitClasspathEntry(rtFolder, getClasspathEntry(
+ jproj, classpathKind, classpathRef));
+ } else {
+ try {
+ WorkbenchComponent childCom = warStruct.findComponentByURI(refHandle);
+ if (childCom == null) {
+ continue;
+ }
+
+ traverseDependentEntries(visitor, rtFolder, childCom,
+ monitor);
+ } catch (UnresolveableURIException e) {
+ TomcatPlugin.log(e);
+ }
+ }
+ }
+ } finally {
+ warStruct.dispose();
+ }
+
+ visitor.endVisitWebComponent(component);
+ }
+
+ private static IPath getSuffixPath(URI uri, int index) {
+ StringBuffer result = new StringBuffer();
+ String[] segments = uri.segments();
+ for (int i = index; i < segments.length; i++) {
+ if (i > index)
+ result.append('/');
+ result.append(segments[i]);
+ }
+ return new Path(result.toString());
+ }
+
+ private static void traverseWebComponentLocalEntries(
+ WorkbenchComponent comp, IModuleVisitor visitor,
+ IProgressMonitor monitor) throws CoreException {
+ IProject warProject = StructureEdit.getContainingProject(comp);
+ if (warProject == null || !warProject.hasNature(JavaCore.NATURE_ID)) {
+ return;
+ }
+ IJavaProject project = JavaCore.create(warProject);
+
+ List res = comp.getResources();
+ for (Iterator itorRes = res.iterator(); itorRes.hasNext();) {
+ ComponentResource childComp = (ComponentResource) itorRes.next();
+ IClasspathEntry cpe = getClasspathEntry(project, childComp.getSourcePath());
+ if (cpe == null)
+ continue;
+ visitor.visitWebResource(childComp.getRuntimePath(), getOSPath(
+ warProject, project, cpe.getOutputLocation()));
+ }
+ }
+
+ private static void traverseDependentEntries(IModuleVisitor visitor,
+ IPath runtimeFolder, WorkbenchComponent component,
+ IProgressMonitor monitor) throws CoreException {
+ IProject dependentProject = StructureEdit.getContainingProject(component);
+ if (!dependentProject.hasNature(JavaCore.NATURE_ID))
+ return;
+ IJavaProject project = JavaCore.create(dependentProject);
+
+ String name = component.getName(); // assume it is the same as URI
+
+ // go thru all entries
+ List res = component.getResources();
+ for (Iterator itorRes = res.iterator(); itorRes.hasNext();) {
+ ComponentResource childComp = (ComponentResource) itorRes.next();
+ IPath rtPath = childComp.getRuntimePath();
+ IClasspathEntry cpe = getClasspathEntry(project, childComp.getSourcePath());
+ if (cpe == null)
+ continue;
+ visitor.visitDependentComponent(runtimeFolder.append(rtPath)
+ .append(name + ".jar"), getOSPath(dependentProject,
+ project, cpe.getOutputLocation()));
+ }
+ }
+
+ private static IClasspathEntry getClasspathEntry(IJavaProject project,
+ IPath sourcePath) throws JavaModelException {
+ sourcePath = project.getPath().append(sourcePath);
+ IClasspathEntry[] cp = project.getRawClasspath();
+ for (int i = 0; i < cp.length; i++) {
+ if (sourcePath.equals(cp[i].getPath()))
+ return JavaCore.getResolvedClasspathEntry(cp[i]);
+ }
+ return null;
+ }
+
+ private static IClasspathEntry getClasspathEntry(IJavaProject project,
+ String classpathKind, IPath classpathRef) throws JavaModelException {
+ int entryKind;
+ if (VirtualArchiveComponent.LIBARCHIVETYPE.equals(classpathKind)) {
+ entryKind = IClasspathEntry.CPE_LIBRARY;
+ } else if (VirtualArchiveComponent.VARARCHIVETYPE.equals(classpathKind)) {
+ entryKind = IClasspathEntry.CPE_VARIABLE;
+ } else {
+ return null;
+ }
+ IClasspathEntry[] cp = project.getRawClasspath();
+ for (int i = 0; i < cp.length; i++) {
+ if (entryKind == cp[i].getEntryKind()
+ && classpathRef.equals(cp[i].getPath())) {
+ return JavaCore.getResolvedClasspathEntry(cp[i]);
+ }
+ }
+ return null;
+ }
+
+ private static IPath getOSPath(IProject project, IJavaProject javaProject,
+ IPath outputPath) throws JavaModelException {
+ if (outputPath == null)
+ outputPath = javaProject.getOutputLocation();
+ return ResourcesPlugin.getWorkspace().getRoot().getFolder(outputPath)
+ .getLocation();
+ }
+
+}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Context.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Context.java
index b597c89..9197dd8 100644
--- a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Context.java
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Context.java
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2003, 2005 IBM Corporation and others.
+ * Copyright (c) 2003, 2005, 2007 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@@ -15,47 +15,112 @@
*
*/
public class Context extends XMLElement {
+ /**
+ * Default constructor
+ */
public Context() {
// do nothing
}
+ /**
+ * Get debug attribute.
+ * @return debug attribute value
+ */
public String getDebug() {
return getAttributeValue("debug");
}
+ /**
+ * Get docBase attribute.
+ * @return docBase attribute value
+ */
public String getDocBase() {
return getAttributeValue("docBase");
}
+ /**
+ * Get path attribute.
+ * @return path attribute value
+ */
public String getPath() {
return getAttributeValue("path");
}
+ /**
+ * Get reloadable attribute.
+ * @return reloadable attribute value
+ */
public String getReloadable() {
return getAttributeValue("reloadable");
}
+ /**
+ * Get WTP source attribute. Links the context
+ * to a project module.
+ * @return source attribute value
+ */
public String getSource() {
return getAttributeValue("source");
}
+ /**
+ * Get context Resources element. Will create
+ * the element if it does not already exist.
+ * @return resources element.
+ */
+ public Resources getResources() {
+ return (Resources) findElement("Resources");
+ }
+
+ /**
+ * Get context Loader element. Will create
+ * the element if it does not already exist.
+ * @return loader element.
+ */
+ public Loader getLoader() {
+ return (Loader) findElement("Loader");
+ }
+
+ /**
+ * Set debug attribute
+ * @param debug value to set
+ */
public void setDebug(String debug) {
setAttributeValue("debug", debug);
}
+ /**
+ * Set docBase attribute.
+ * @param docBase value to set
+ */
public void setDocBase(String docBase) {
setAttributeValue("docBase", docBase);
}
+ /**
+ * Set path attribute.
+ * @param path value to set
+ */
public void setPath(String path) {
setAttributeValue("path", path);
}
+ /**
+ * Set reloadable attribute.
+ * @param reloadable value to set
+ */
public void setReloadable(String reloadable) {
setAttributeValue("reloadable", reloadable);
}
+ /**
+ * Set WTP source attribute. Links the context
+ * to a project module.
+ * @param source value to set
+ */
public void setSource(String source) {
setAttributeValue("source", source);
}
+
+
}
\ No newline at end of file
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Loader.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Loader.java
new file mode 100644
index 0000000..55b7ccb
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Loader.java
@@ -0,0 +1,70 @@
+/**********************************************************************
+ * Copyright (c) 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Fabrizio Giustina - Initial API and implementation
+ **********************************************************************/
+package org.eclipse.jst.server.tomcat.core.internal.xml.server40;
+
+import org.eclipse.jst.server.tomcat.core.internal.xml.XMLElement;
+
+/**
+ * Loader element, optional in Context.
+ */
+public class Loader extends XMLElement {
+
+ /**
+ * Get className attribute.
+ * @return className attribute value
+ */
+ public String getClassName() {
+ return getAttributeValue("className");
+ }
+
+ /**
+ * Set className attribute.
+ * @param className value to set
+ */
+ public void setClassName(String className) {
+ setAttributeValue("className", className);
+ }
+
+ /**
+ * Get WTP virtualClasspath attribute.
+ * @return virtualClasspath value
+ */
+ public String getVirtualClasspath() {
+ return getAttributeValue("virtualClasspath");
+ }
+
+ /**
+ * Set WTP virtualClasspath attribute.
+ * @param virtualClasspath value to set
+ */
+ public void setVirtualClasspath(String virtualClasspath) {
+ setAttributeValue("virtualClasspath", virtualClasspath);
+ }
+
+ /**
+ * Get useSystemClassLoaderAsParent attribute
+ * @return useSystemClassLoaderAsParent value
+ */
+ public String getUseSystemClassLoaderAsParent() {
+ return getAttributeValue("useSystemClassLoaderAsParent");
+ }
+
+ /**
+ * Set useSystemClassLoaderAsParent attribute.
+ * @param useSystemClassLoaderAsParent value to set
+ */
+ public void setUseSystemClassLoaderAsParent(
+ String useSystemClassLoaderAsParent) {
+ setAttributeValue("useSystemClassLoaderAsParent",
+ useSystemClassLoaderAsParent);
+ }
+
+}
diff --git a/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Resources.java b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Resources.java
new file mode 100644
index 0000000..6163e62
--- /dev/null
+++ b/plugins/org.eclipse.jst.server.tomcat.core/tomcatcore/org/eclipse/jst/server/tomcat/core/internal/xml/server40/Resources.java
@@ -0,0 +1,51 @@
+/**********************************************************************
+ * Copyright (c) 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * Fabrizio Giustina - Initial API and implementation
+ **********************************************************************/
+package org.eclipse.jst.server.tomcat.core.internal.xml.server40;
+
+import org.eclipse.jst.server.tomcat.core.internal.xml.XMLElement;
+
+/**
+ * Resources element, optional in Context.
+ */
+public class Resources extends XMLElement {
+
+ /**
+ * Get className attribute
+ * @return className attribute value
+ */
+ public String getClassName() {
+ return getAttributeValue("className");
+ }
+
+ /**
+ * Get virtualClasspath attribute.
+ * @return virtualClasspath attribute value
+ */
+ public String getVirtualClasspath() {
+ return getAttributeValue("virtualClasspath");
+ }
+
+ /**
+ * Set className attribute.
+ * @param className value to set
+ */
+ public void setClassName(String className) {
+ setAttributeValue("className", className);
+ }
+
+ /**
+ * Set virtualClasspath attribute.
+ * @param virtualClasspath value to set
+ */
+ public void setVirtualClasspath(String virtualClasspath) {
+ setAttributeValue("virtualClasspath", virtualClasspath);
+ }
+}
diff --git a/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.java b/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.java
index 0dceefc..72805ce 100644
--- a/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.java
+++ b/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.java
@@ -66,8 +66,11 @@
public static String serverEditorServerDir;
public static String serverEditorDeployDir;
public static String serverEditorTestEnvironment;
+ public static String serverEditorNoPublish;
public static String serverEditorSecure;
public static String serverEditorDebugMode;
+ public static String serverEditorNotSupported;
+ public static String errorNoPublishServerMustBeStopped;
public static String errorServerDirIsRoot;
public static String errorServerDirUnderRoot;
public static String errorDeployDirNotSpecified;
diff --git a/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.properties b/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.properties
index e6225a4..69d3219 100644
--- a/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.properties
+++ b/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/Messages.properties
@@ -91,9 +91,12 @@
serverEditorSecure=Enable security
serverEditorDebugMode=Enable Tomcat debug mode (v4.x and above only)
serverEditorTestEnvironment=Run modules directly from the workspace (do not modify the Tomcat installation)
+serverEditorNoPublish=Serve modules without publishing {0}
errorServerDirIsRoot=The server path may not be set to the the root of your workspace.
errorServerDirUnderRoot=The server path may not be under the \"{0}\" folder of your workspace unless it is the internally supplied path.
errorDeployDirNotSpecified=A deploy path must be specified.
+serverEditorNotSupported= (not supported by this Tomcat version)
+errorNoPublishServerMustBeStopped=The server must be stopped before a change to the \"{0}\" setting can be saved.
# Browse for Server dialog
serverEditorBrowseServerMessage=Select a server directory.
diff --git a/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/editor/ServerGeneralEditorSection.java b/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/editor/ServerGeneralEditorSection.java
index a063d0d..cc62e0f 100644
--- a/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/editor/ServerGeneralEditorSection.java
+++ b/plugins/org.eclipse.jst.server.tomcat.ui/tomcatui/org/eclipse/jst/server/tomcat/ui/internal/editor/ServerGeneralEditorSection.java
@@ -13,11 +13,17 @@
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
+import org.eclipse.jst.server.tomcat.core.internal.ITomcatServer;
import org.eclipse.jst.server.tomcat.core.internal.TomcatServer;
import org.eclipse.jst.server.tomcat.core.internal.command.SetDebugModeCommand;
import org.eclipse.jst.server.tomcat.core.internal.command.SetSecureCommand;
+import org.eclipse.jst.server.tomcat.core.internal.command.SetServeModulesWithoutPublishCommand;
import org.eclipse.jst.server.tomcat.ui.internal.ContextIds;
import org.eclipse.jst.server.tomcat.ui.internal.Messages;
+import org.eclipse.jst.server.tomcat.ui.internal.TomcatUIPlugin;
+import org.eclipse.osgi.util.NLS;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
@@ -32,8 +38,9 @@
import org.eclipse.ui.forms.widgets.FormToolkit;
import org.eclipse.ui.forms.widgets.Section;
import org.eclipse.ui.help.IWorkbenchHelpSystem;
-
-import org.eclipse.wst.server.ui.editor.*;
+import org.eclipse.wst.server.core.IServer;
+import org.eclipse.wst.server.core.internal.PublishServerJob;
+import org.eclipse.wst.server.ui.editor.ServerEditorSection;
/**
* Tomcat server general editor page.
*/
@@ -42,9 +49,12 @@
protected Button secure;
protected Button debug;
+ protected Button noPublish;
protected boolean updating;
protected PropertyChangeListener listener;
+
+ protected boolean noPublishChanged;
/**
* ServerGeneralEditorPart constructor comment.
@@ -68,6 +78,11 @@
} else if (TomcatServer.PROPERTY_DEBUG.equals(event.getPropertyName())) {
Boolean b = (Boolean) event.getNewValue();
ServerGeneralEditorSection.this.debug.setSelection(b.booleanValue());
+ } else if (ITomcatServer.PROPERTY_SERVE_MODULES_WITHOUT_PUBLISH.equals(event.getPropertyName())) {
+ Boolean b = (Boolean) event.getNewValue();
+ ServerGeneralEditorSection.this.noPublish.setSelection(b.booleanValue());
+ // Indicate this setting has changed
+ noPublishChanged = true;
}
updating = false;
}
@@ -104,9 +119,28 @@
toolkit.paintBordersFor(composite);
section.setClient(composite);
+ // serve modules without publish
+ noPublish = toolkit.createButton(composite, NLS.bind(Messages.serverEditorNoPublish, ""), SWT.CHECK);
+ GridData data = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
+ data.horizontalSpan = 3;
+ noPublish.setLayoutData(data);
+ noPublish.addSelectionListener(new SelectionAdapter() {
+ public void widgetSelected(SelectionEvent se) {
+ if (updating)
+ return;
+ updating = true;
+ execute(new SetServeModulesWithoutPublishCommand(tomcatServer, noPublish.getSelection()));
+ // Indicate this setting has changed
+ noPublishChanged = true;
+ updating = false;
+ }
+ });
+ // TODO Address help
+// whs.setHelp(noPublish, ContextIds.SERVER_EDITOR_SECURE);
+
// security
secure = toolkit.createButton(composite, Messages.serverEditorSecure, SWT.CHECK);
- GridData data = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
+ data = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
data.horizontalSpan = 3;
secure.setLayoutData(data);
secure.addSelectionListener(new SelectionAdapter() {
@@ -167,6 +201,16 @@
if (secure == null || tomcatServer == null)
return;
updating = true;
+
+ boolean supported = tomcatServer.getTomcatVersionHandler().supportsServeModulesWithoutPublish();
+ String noPublishLabel = NLS.bind(Messages.serverEditorNoPublish,
+ supported ? "" : Messages.serverEditorNotSupported);
+ noPublish.setText(noPublishLabel);
+ noPublish.setSelection(tomcatServer.isServeModulesWithoutPublish());
+ if (readOnly || !supported)
+ noPublish.setEnabled(false);
+ else
+ noPublish.setEnabled(true);
secure.setSelection(tomcatServer.isSecure());
if (server.getRuntime() != null && server.getRuntime().getRuntimeType().getId().indexOf("32") >= 0 || readOnly)
@@ -183,4 +227,27 @@
updating = false;
}
+
+ /**
+ * @see ServerEditorSection#getSaveStatus()
+ */
+ public IStatus[] getSaveStatus() {
+ // If serve modules without publishing has changed, request clean publish to be safe
+ if (noPublishChanged) {
+ // If server is running, abort the save since clean publish won't succeed
+ if (tomcatServer.getServer().getServerState() != IServer.STATE_STOPPED) {
+ return new IStatus [] {
+ new Status(IStatus.ERROR, TomcatUIPlugin.PLUGIN_ID,
+ NLS.bind(Messages.errorNoPublishServerMustBeStopped,
+ NLS.bind(Messages.serverEditorNoPublish, "").trim()))
+ };
+ }
+ // Force a clean publish
+ PublishServerJob publishJob = new PublishServerJob(tomcatServer.getServer(), IServer.PUBLISH_CLEAN, false);
+ publishJob.schedule();
+ noPublishChanged = false;
+ }
+ // use default implementation to return success
+ return super.getSaveStatus();
+ }
}
\ No newline at end of file