Author: pferraro
Date: 2009-04-22 14:22:05 -0400 (Wed, 22 Apr 2009)
New Revision: 2400
Modified:
trunk/mod_cluster/src/main/java/org/jboss/modcluster/AbstractModClusterService.java
trunk/mod_cluster/src/main/java/org/jboss/modcluster/LocalStrings.properties
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ModClusterServiceMBean.java
trunk/mod_cluster/src/main/java/org/jboss/modcluster/Utils.java
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ha/HAModClusterService.java
trunk/mod_cluster/src/main/java/org/jboss/modcluster/mbeans-descriptors.xml
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ModClusterServiceTestCase.java
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ha/HAModClusterServiceTestCase.java
Log:
[MODCLUSTER-68] Add ability to disable/enable individual webapp via JMX
Modified:
trunk/mod_cluster/src/main/java/org/jboss/modcluster/AbstractModClusterService.java
===================================================================
---
trunk/mod_cluster/src/main/java/org/jboss/modcluster/AbstractModClusterService.java 2009-04-22
11:23:17 UTC (rev 2399)
+++
trunk/mod_cluster/src/main/java/org/jboss/modcluster/AbstractModClusterService.java 2009-04-22
18:22:05 UTC (rev 2400)
@@ -178,4 +178,34 @@
return this.mcmpHandler.isProxyHealthOK();
}
+
+ /**
+ * @{inheritDoc}
+ * @see org.jboss.modcluster.ModClusterServiceMBean#disable(java.lang.String,
java.lang.String)
+ */
+ public boolean disable(String host, String path)
+ {
+ Context context = Utils.getContext(Utils.getHost(this.serverProvider.getServer(),
host), path);
+
+ // Send DISABLE-APP /... request
+ MCMPRequest request = this.requestFactory.createDisableRequest(context);
+ this.mcmpHandler.sendRequest(request);
+
+ return this.mcmpHandler.isProxyHealthOK();
+ }
+
+ /**
+ * @{inheritDoc}
+ * @see org.jboss.modcluster.ModClusterServiceMBean#enable(java.lang.String,
java.lang.String)
+ */
+ public boolean enable(String host, String path)
+ {
+ Context context = Utils.getContext(Utils.getHost(this.serverProvider.getServer(),
host), path);
+
+ // Send ENABLE-APP /... request
+ MCMPRequest request = this.requestFactory.createEnableRequest(context);
+ this.mcmpHandler.sendRequest(request);
+
+ return this.mcmpHandler.isProxyHealthOK();
+ }
}
\ No newline at end of file
Modified: trunk/mod_cluster/src/main/java/org/jboss/modcluster/LocalStrings.properties
===================================================================
---
trunk/mod_cluster/src/main/java/org/jboss/modcluster/LocalStrings.properties 2009-04-22
11:23:17 UTC (rev 2399)
+++
trunk/mod_cluster/src/main/java/org/jboss/modcluster/LocalStrings.properties 2009-04-22
18:22:05 UTC (rev 2400)
@@ -1,8 +1,8 @@
# Regular messages
-modcluster.context.disable=Undeploy context [{0}] to Host [{1}]
-modcluster.context.enable=Deploy context [{0}] to Host [{1}]
-modcluster.context.start=Start context [{0}] in Host [{1}]
-modcluster.context.stop=Stop context [{0}] in Host [{1}]
+modcluster.context.disable=Undeploy context [{0}] to host [{1}]
+modcluster.context.enable=Deploy context [{0}] to host [{1}]
+modcluster.context.start=Start context [{0}] in host [{1}]
+modcluster.context.stop=Stop context [{0}] in host [{1}]
modcluster.engine.config=Sending configuration for engine [{0}]
modcluster.engine.status=Check status for engine [{0}]
modcluster.engine.stop=Stop all web applications for engine [{0}]
@@ -13,10 +13,12 @@
# Error messages
modcluster.error.addressJvmRoute=Error connecting to proxy to determine Engine.JVMRoute
or Connector.address
+modcluster.error.context.notfound=Host [{0}] does not contain a context with path [{1}]
modcluster.error.discovery.add=Failure notifying master of added proxy [{0}]:[{1}]
modcluster.error.discovery.remove=Failure notifying master of removed proxy [{0}]:[{1}]
modcluster.error.drm="Error updating DRM
-modcluster.error.invalidHost=Invalid host specified: {0}
+modcluster.error.host.invalid=[{0}] is not a valid host
+modcluster.error.host.notfound=Server does not contain host [{0}]
modcluster.error.io=IO error sending command {0} to proxy {1}
modcluster.error.jmxRegister=Error during JMX registration
modcluster.error.jmxUnregister=Error during JMX unregistration
Modified:
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ModClusterServiceMBean.java
===================================================================
---
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ModClusterServiceMBean.java 2009-04-22
11:23:17 UTC (rev 2399)
+++
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ModClusterServiceMBean.java 2009-04-22
18:22:05 UTC (rev 2400)
@@ -49,7 +49,7 @@
void removeProxy(String host, int port);
/**
- * Retrieves the full proxy configuration. To be used through JMX or similar.
+ * Retrieves the full proxy configuration.
*
* response: HTTP/1.1 200 OK
* response:
@@ -75,22 +75,36 @@
/**
* Reset a DOWN connection to the proxy up to ERROR, where the configuration will
- * be refreshed. To be used through JMX or similar.
+ * be refreshed.
*/
public void reset();
/**
- * Refresh configuration. To be used through JMX or similar.
+ * Refresh configuration.
*/
public void refresh();
/**
- * Disable all webapps for all engines. To be used through JMX or similar.
+ * Disable all webapps for all engines.
*/
public boolean disable();
/**
- * Enable all webapps for all engines. To be used through JMX or similar.
+ * Enable all webapps for all engines.
*/
public boolean enable();
+
+ /**
+ * Disables the webapp with the specified host and context path.
+ * @param hostName host name of the target webapp
+ * @param contextPath context path of the target webapp
+ */
+ public boolean disable(String hostName, String contextPath);
+
+ /**
+ * Enables the webapp with the specified host and context path.
+ * @param hostName host name of the target webapp
+ * @param contextPath context path of the target webapp
+ */
+ public boolean enable(String hostName, String contextPath);
}
Modified: trunk/mod_cluster/src/main/java/org/jboss/modcluster/Utils.java
===================================================================
--- trunk/mod_cluster/src/main/java/org/jboss/modcluster/Utils.java 2009-04-22 11:23:17
UTC (rev 2399)
+++ trunk/mod_cluster/src/main/java/org/jboss/modcluster/Utils.java 2009-04-22 18:22:05
UTC (rev 2400)
@@ -15,9 +15,12 @@
import java.util.Map;
import java.util.Set;
+import org.apache.catalina.Container;
import org.apache.catalina.Context;
import org.apache.catalina.Engine;
import org.apache.catalina.Host;
+import org.apache.catalina.Server;
+import org.apache.catalina.Service;
import org.apache.catalina.connector.Connector;
import org.apache.catalina.util.StringManager;
import org.apache.coyote.ProtocolHandler;
@@ -273,7 +276,7 @@
}
catch (UnknownHostException e)
{
- log.error(sm.getString("modcluster.error.invalidHost", token), e);
+ log.error(sm.getString("modcluster.error.host.invalid", token),
e);
}
}
@@ -338,6 +341,47 @@
return map;
}
+ public static Host findHost(Server server, String hostName)
+ {
+ String name = (hostName != null) ? hostName : DEFAULT_HOST;
+
+ for (Service service: server.findServices())
+ {
+ Container host = service.getContainer().findChild(name);
+
+ if (host != null)
+ {
+ return (Host) host;
+ }
+ }
+
+ return null;
+ }
+
+ public static Host getHost(Server server, String hostName)
+ {
+ Host host = findHost(server, hostName);
+
+ if (host == null)
+ {
+ throw new
IllegalArgumentException(sm.getString("modcluster.error.host.notfound",
hostName));
+ }
+
+ return host;
+ }
+
+ public static Context getContext(Host host, String path)
+ {
+ Container context = host.findChild(path);
+
+ if (context == null)
+ {
+ throw new
IllegalArgumentException(sm.getString("modcluster.error.context.notfound",
host.getName(), path));
+ }
+
+ return (Context) context;
+ }
+
private Utils()
{
}
Modified:
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ha/HAModClusterService.java
===================================================================
---
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ha/HAModClusterService.java 2009-04-22
11:23:17 UTC (rev 2399)
+++
trunk/mod_cluster/src/main/java/org/jboss/modcluster/ha/HAModClusterService.java 2009-04-22
18:22:05 UTC (rev 2400)
@@ -342,6 +342,36 @@
return this.clusteredHandler.isProxyHealthOK();
}
+
+ /**
+ * @{inheritDoc}
+ * @see org.jboss.modcluster.ModClusterServiceMBean#disable(java.lang.String,
java.lang.String)
+ */
+ public boolean disable(String host, String path)
+ {
+ Context context = Utils.getContext(Utils.getHost(this.serverProvider.getServer(),
host), path);
+
+ // Send DISABLE-APP /... request
+ MCMPRequest request = this.requestFactory.createDisableRequest(context);
+ this.clusteredHandler.sendRequest(request);
+
+ return this.clusteredHandler.isProxyHealthOK();
+ }
+
+ /**
+ * @{inheritDoc}
+ * @see org.jboss.modcluster.ModClusterServiceMBean#enable(java.lang.String,
java.lang.String)
+ */
+ public boolean enable(String host, String path)
+ {
+ Context context = Utils.getContext(Utils.getHost(this.serverProvider.getServer(),
host), path);
+
+ // Send ENABLE-APP /... request
+ MCMPRequest request = this.requestFactory.createEnableRequest(context);
+ this.clusteredHandler.sendRequest(request);
+
+ return this.clusteredHandler.isProxyHealthOK();
+ }
// ------------------------------------------------------------- Properties
Modified: trunk/mod_cluster/src/main/java/org/jboss/modcluster/mbeans-descriptors.xml
===================================================================
--- trunk/mod_cluster/src/main/java/org/jboss/modcluster/mbeans-descriptors.xml 2009-04-22
11:23:17 UTC (rev 2399)
+++ trunk/mod_cluster/src/main/java/org/jboss/modcluster/mbeans-descriptors.xml 2009-04-22
18:22:05 UTC (rev 2400)
@@ -105,6 +105,30 @@
returnType="boolean"/>
<operation name="enable"
+ description="Enable a single webapp"
+ impact="ACTION"
+ returnType="boolean">
+ <parameter name="hostName"
+ description="Host name of the target webapp"
+ type="java.lang.String"/>
+ <parameter name="contextPath"
+ description="Context path of the webapp"
+ type="java.lang.String"/>
+ </operation>
+
+ <operation name="disable"
+ description="Disable a single webapp"
+ impact="ACTION"
+ returnType="boolean">
+ <parameter name="hostName"
+ description="Host name of the target webapp"
+ type="java.lang.String"/>
+ <parameter name="contextPath"
+ description="Context path of the webapp"
+ type="java.lang.String"/>
+ </operation>
+
+ <operation name="enable"
description="Enable all webapps for all engines"
impact="ACTION"
returnType="boolean"/>
Modified:
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ModClusterServiceTestCase.java
===================================================================
---
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ModClusterServiceTestCase.java 2009-04-22
11:23:17 UTC (rev 2399)
+++
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ModClusterServiceTestCase.java 2009-04-22
18:22:05 UTC (rev 2400)
@@ -21,7 +21,9 @@
*/
package org.jboss.modcluster;
+import org.apache.catalina.Context;
import org.apache.catalina.Engine;
+import org.apache.catalina.Host;
import org.apache.catalina.Lifecycle;
import org.apache.catalina.LifecycleEvent;
import org.apache.catalina.LifecycleListener;
@@ -212,4 +214,74 @@
Assert.assertTrue(result);
}
+
+ @SuppressWarnings("boxing")
+ @Test
+ public void enableContext()
+ {
+ String hostName = "host1";
+ String path = "/";
+
+ Server server = EasyMock.createStrictMock(Server.class);
+ Service service = EasyMock.createStrictMock(Service.class);
+ Engine engine = EasyMock.createStrictMock(Engine.class);
+ Host host = EasyMock.createStrictMock(Host.class);
+ Context context = EasyMock.createStrictMock(Context.class);
+ MCMPRequest request = EasyMock.createMock(MCMPRequest.class);
+
+ EasyMock.expect(this.serverProvider.getServer()).andReturn(server);
+ EasyMock.expect(server.findServices()).andReturn(new Service[] { service });
+ EasyMock.expect(service.getContainer()).andReturn(engine);
+ EasyMock.expect(engine.findChild(hostName)).andReturn(host);
+ EasyMock.expect(host.findChild(path)).andReturn(context);
+
+
EasyMock.expect(this.requestFactory.createEnableRequest(context)).andReturn(request);
+
+ EasyMock.expect(this.mcmpHandler.sendRequest(request)).andReturn(null);
+
+ EasyMock.expect(this.mcmpHandler.isProxyHealthOK()).andReturn(true);
+
+ EasyMock.replay(this.serverProvider, this.requestFactory, this.mcmpHandler, server,
service, engine, host, context);
+
+ boolean result = this.listener.enable(hostName, path);
+
+ EasyMock.verify(this.serverProvider, this.requestFactory, this.mcmpHandler, server,
service, engine, host, context);
+
+ Assert.assertTrue(result);
+ }
+
+ @SuppressWarnings("boxing")
+ @Test
+ public void disableContext()
+ {
+ String hostName = "host1";
+ String path = "/";
+
+ Server server = EasyMock.createStrictMock(Server.class);
+ Service service = EasyMock.createStrictMock(Service.class);
+ Engine engine = EasyMock.createStrictMock(Engine.class);
+ Host host = EasyMock.createStrictMock(Host.class);
+ Context context = EasyMock.createStrictMock(Context.class);
+ MCMPRequest request = EasyMock.createMock(MCMPRequest.class);
+
+ EasyMock.expect(this.serverProvider.getServer()).andReturn(server);
+ EasyMock.expect(server.findServices()).andReturn(new Service[] { service });
+ EasyMock.expect(service.getContainer()).andReturn(engine);
+ EasyMock.expect(engine.findChild(hostName)).andReturn(host);
+ EasyMock.expect(host.findChild(path)).andReturn(context);
+
+
EasyMock.expect(this.requestFactory.createDisableRequest(context)).andReturn(request);
+
+ EasyMock.expect(this.mcmpHandler.sendRequest(request)).andReturn(null);
+
+ EasyMock.expect(this.mcmpHandler.isProxyHealthOK()).andReturn(true);
+
+ EasyMock.replay(this.serverProvider, this.requestFactory, this.mcmpHandler, server,
service, engine, host, context);
+
+ boolean result = this.listener.disable(hostName, path);
+
+ EasyMock.verify(this.serverProvider, this.requestFactory, this.mcmpHandler, server,
service, engine, host, context);
+
+ Assert.assertTrue(result);
+ }
}
Modified:
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ha/HAModClusterServiceTestCase.java
===================================================================
---
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ha/HAModClusterServiceTestCase.java 2009-04-22
11:23:17 UTC (rev 2399)
+++
trunk/mod_cluster/src/test/java/org/jboss/modcluster/ha/HAModClusterServiceTestCase.java 2009-04-22
18:22:05 UTC (rev 2400)
@@ -24,7 +24,9 @@
import java.util.Collections;
import java.util.Map;
+import org.apache.catalina.Context;
import org.apache.catalina.Engine;
+import org.apache.catalina.Host;
import org.apache.catalina.Lifecycle;
import org.apache.catalina.LifecycleEvent;
import org.apache.catalina.LifecycleListener;
@@ -257,6 +259,76 @@
}
@Test
+ public void enableContext()
+ {
+ String hostName = "host1";
+ String path = "/context";
+
+ Server server = EasyMock.createStrictMock(Server.class);
+ Service service = EasyMock.createStrictMock(Service.class);
+ Engine engine = EasyMock.createStrictMock(Engine.class);
+ Host host = EasyMock.createStrictMock(Host.class);
+ Context context = EasyMock.createStrictMock(Context.class);
+ MCMPRequest request = EasyMock.createMock(MCMPRequest.class);
+ Map<MCMPServerState, String> emptyMap = Collections.emptyMap();
+
+ EasyMock.expect(this.serverProvider.getServer()).andReturn(server);
+ EasyMock.expect(server.findServices()).andReturn(new Service[] { service });
+ EasyMock.expect(service.getContainer()).andReturn(engine);
+ EasyMock.expect(engine.findChild(hostName)).andReturn(host);
+ EasyMock.expect(host.findChild(path)).andReturn(context);
+
+
EasyMock.expect(this.requestFactory.createEnableRequest(context)).andReturn(request);
+
+
EasyMock.expect(this.clusteredMCMPHandler.sendRequest(request)).andReturn(emptyMap);
+
+ EasyMock.expect(this.clusteredMCMPHandler.isProxyHealthOK()).andReturn(true);
+
+ EasyMock.replay(this.serverProvider, this.requestFactory,
this.clusteredMCMPHandler, server, service, engine, host, context);
+
+ boolean result = this.service.enable(hostName, path);
+
+ EasyMock.verify(this.serverProvider, this.requestFactory,
this.clusteredMCMPHandler, server, service, engine, host, context);
+
+ Assert.assertTrue(result);
+ }
+
+ @Test
+ public void disableContext()
+ {
+ String hostName = "host1";
+ String path = "/context";
+
+ Server server = EasyMock.createStrictMock(Server.class);
+ Service service = EasyMock.createStrictMock(Service.class);
+ Engine engine = EasyMock.createStrictMock(Engine.class);
+ Host host = EasyMock.createStrictMock(Host.class);
+ Context context = EasyMock.createStrictMock(Context.class);
+ MCMPRequest request = EasyMock.createMock(MCMPRequest.class);
+ Map<MCMPServerState, String> emptyMap = Collections.emptyMap();
+
+ EasyMock.expect(this.serverProvider.getServer()).andReturn(server);
+ EasyMock.expect(server.findServices()).andReturn(new Service[] { service });
+ EasyMock.expect(service.getContainer()).andReturn(engine);
+ EasyMock.expect(engine.findChild(hostName)).andReturn(host);
+ EasyMock.expect(host.findChild(path)).andReturn(context);
+
+
EasyMock.expect(this.requestFactory.createDisableRequest(context)).andReturn(request);
+
+
EasyMock.expect(this.clusteredMCMPHandler.sendRequest(request)).andReturn(emptyMap);
+
+ EasyMock.expect(this.clusteredMCMPHandler.isProxyHealthOK()).andReturn(true);
+
+ EasyMock.replay(this.serverProvider, this.requestFactory,
this.clusteredMCMPHandler, server, service, engine, host, context);
+
+ boolean result = this.service.disable(hostName, path);
+
+ EasyMock.verify(this.serverProvider, this.requestFactory,
this.clusteredMCMPHandler, server, service, engine, host, context);
+
+ Assert.assertTrue(result);
+ }
+
+ @Test
public void lifecycleEvent()
{
LifecycleEvent event = new LifecycleEvent(EasyMock.createMock(Lifecycle.class),
Lifecycle.INIT_EVENT);