/*
* JBoss, Home of Professional Open Source.
* Copyright 2008, Red Hat Middleware LLC, and individual contributors
* as indicated by the @author tags. See the copyright.txt file in the
* distribution for a full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/
package test.implementation.util;
import java.util.Set;
import java.lang.reflect.Method;
import javax.management.Attribute;
import javax.management.AttributeNotFoundException;
import javax.management.DynamicMBean;
import javax.management.InstanceNotFoundException;
import javax.management.MBeanServer;
import javax.management.MBeanServerFactory;
import javax.management.ObjectInstance;
import javax.management.ObjectName;
import javax.management.modelmbean.ModelMBean;
import javax.management.modelmbean.RequiredModelMBean;
import test.implementation.util.support.Trivial;
import test.implementation.util.support.TrivialMBean;
import test.implementation.util.support.Trivial2;
import test.implementation.util.support.Trivial2MBean;
import test.implementation.util.support.ExtendedResource;
import test.implementation.util.support.MyInterface;
import test.implementation.util.support.MyInterface2;
import test.implementation.util.support.Resource;
import test.implementation.util.support.ResourceOverride;
import test.implementation.util.support.ResourceIncorrectInfo;
import junit.framework.TestCase;
import org.jboss.mx.util.AgentID;
import org.jboss.mx.util.DefaultExceptionHandler;
import org.jboss.mx.util.MBeanProxy;
import org.jboss.mx.util.ProxyContext;
import org.jboss.mx.modelmbean.XMBean;
/**
* Tests for mbean proxy
*
* @author <a href="mailto:juha@jboss.org">Juha Lindfors</a>.
* @version $Revision: 81022 $
*/
public class MBeanProxyTEST extends TestCase
{
public MBeanProxyTEST(String s)
{
super(s);
}
public void testGetWithServer() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:name=test");
server.registerMBean(new Trivial(), oname);
TrivialMBean mbean = (TrivialMBean)MBeanProxy.get(
TrivialMBean.class, oname, server);
mbean.doOperation();
}
public void testGetWithAgentID() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
String agentID = AgentID.get(server);
ObjectName oname = new ObjectName("test:name=test");
server.registerMBean(new Trivial(), oname);
TrivialMBean mbean = (TrivialMBean)MBeanProxy.get(
TrivialMBean.class, oname, agentID);
mbean.doOperation();
}
public void testCreateWithServer() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
TrivialMBean mbean = (TrivialMBean)MBeanProxy.create(
Trivial.class, TrivialMBean.class, oname, server);
mbean.doOperation();
}
public void testCreateWithAgentID() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
String agentID = AgentID.get(server);
TrivialMBean mbean = (TrivialMBean)MBeanProxy.create(
Trivial.class, TrivialMBean.class, oname, agentID);
mbean.doOperation();
}
public void testProxyInvocations() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:name=test");
server.registerMBean(new Trivial(), oname);
TrivialMBean mbean = (TrivialMBean)MBeanProxy.get(
TrivialMBean.class, oname, AgentID.get(server));
mbean.doOperation();
mbean.setSomething("JBossMX");
assertEquals("JBossMX", mbean.getSomething());
}
public void testProxyInvocationWithConflictingMBeanAndContextMethods() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
server.registerMBean(new Trivial(), oname);
TrivialMBean mbean = (TrivialMBean)MBeanProxy.get(
TrivialMBean.class, oname, AgentID.get(server));
mbean.getMBeanServer();
assertTrue(mbean.isGMSInvoked());
}
public void testContextAccess() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
Trivial2MBean mbean = (Trivial2MBean)MBeanProxy.create(
Trivial2.class, Trivial2MBean.class, oname, server
);
ProxyContext ctx = (ProxyContext)mbean;
ctx.getMBeanServer();
}
public void testProxyInvocationBetweenServers() throws Exception
{
MBeanServer server1 = MBeanServerFactory.createMBeanServer();
MBeanServer server2 = MBeanServerFactory.createMBeanServer();
ObjectName oname1 = new ObjectName("test:name=target");
ObjectName oname2 = new ObjectName("test:name=proxy");
// createMBean on server1 and retrieve a proxy to it
Trivial2MBean mbean = (Trivial2MBean)MBeanProxy.create(
Trivial2.class, Trivial2MBean.class, oname1, server1
);
//bind the proxy to server2
server2.registerMBean(mbean, oname2);
// invoke on server2
server2.invoke(oname2, "doOperation", null, null);
// check that server1 received the invocation
assertTrue(((Boolean)server1.getAttribute(oname1, "OperationInvoked")).booleanValue());
}
public void testSimultaneousTypedAndDetypedInvocations() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
Trivial2MBean mbean = (Trivial2MBean)MBeanProxy.create(
Trivial2.class, Trivial2MBean.class, oname,server
);
// typed proxy interface
mbean.setSomething("Kissa");
assertTrue(mbean.getSomething().equals("Kissa"));
// detyped proxy interface
DynamicMBean mbean2 = (DynamicMBean)mbean;
mbean2.setAttribute(new Attribute("Something", "Koira"));
assertTrue(mbean2.getAttribute("Something").equals("Koira"));
// direct local server invocation
server.setAttribute(oname, new Attribute("Something", "Kissa"));
assertTrue(server.getAttribute(oname, "Something").equals("Kissa"));
// typed proxy interface invocation
mbean.doOperation();
assertTrue(mbean.isOperationInvoked());
mbean.reset();
// detyped proxy invocation
mbean2.invoke("doOperation", null, null);
assertTrue(((Boolean)mbean2.getAttribute("OperationInvoked")).booleanValue());
mbean2.invoke("reset", null, null);
// direct local server invocation
server.invoke(oname, "doOperation", null, null);
assertTrue(((Boolean)server.getAttribute(oname, "OperationInvoked")).booleanValue());
}
public void testContextAccessToMBeanServer() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
Trivial2MBean mbean = (Trivial2MBean)MBeanProxy.create(
Trivial2.class, Trivial2MBean.class, oname, server
);
// query the server this mbean is registered to
ProxyContext ctx = (ProxyContext)mbean;
MBeanServer srvr = ctx.getMBeanServer();
Set mbeans = srvr.queryMBeans(new ObjectName("test:*"), null);
ObjectInstance oi = (ObjectInstance)mbeans.iterator().next();
assertTrue(oi.getObjectName().equals(oname));
assertTrue(srvr.getAttribute(
new ObjectName("JMImplementation:type=MBeanServerDelegate"),
"ImplementationName"
).equals("JBossMX"));
}
public void testArbitraryInterfaceWithProxy() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
RequiredModelMBean rmm = new RequiredModelMBean();
Resource resource = new Resource();
rmm.setManagedResource(resource, "ObjectReference");
rmm.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(rmm, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
mbean.setAttributeName("foo");
mbean.setAttributeName2("bar");
assertTrue(mbean.getAttributeName2().equals("bar"));
assertTrue(mbean.doOperation().equals("tamppi"));
}
/**
* This test shows how to override the default exception handling for
* proxy invocations. The default handling for exceptions that are not
* declared as part of the proxy typed interface (such as InstanceNotFound
* or AttributeNotFound exceptions) are rethrown as unchecked
* RuntimeProxyExceptions. See org.jboss.mx.proxy.DefaultExceptionHandler
* for details. This behavior can be changed at runtime through the proxy
* context interface setExceptionHandler() method.
*/
public void testCustomExceptionHandler() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
ObjectName oname2 = new ObjectName("test:test=test2");
RequiredModelMBean rmm = new RequiredModelMBean();
Resource resource = new Resource();
rmm.setManagedResource(resource, "ObjectReference");
rmm.setModelMBeanInfo(resource.getMBeanInfo());
// create two identical mbeans
server.registerMBean(rmm, oname);
server.registerMBean(rmm, oname2);
ProxyContext ctx = (ProxyContext)MBeanProxy.get(
MyInterface.class, oname, server
);
// override InstanceNotFound exception to redirect from test=test instance
// to test=test2 instance
ctx.setExceptionHandler(new DefaultExceptionHandler()
{
public Object handleInstanceNotFound(ProxyContext proxyCtx, InstanceNotFoundException e, Method m, Object[] args) throws Exception
{
return proxyCtx.getMBeanServer().invoke(new ObjectName("test:test=test2"), m.getName(), args, null);
}
});
// unregister mbean 1
server.unregisterMBean(oname);
// invocation attempt to mbean1 should now redirect to mbean2
MyInterface mbean = (MyInterface)ctx;
assertTrue(mbean.doOperation().equals("tamppi"));
}
public void testObjectToStringOnProxy() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
RequiredModelMBean rmm = new RequiredModelMBean();
Resource resource = new Resource();
rmm.setManagedResource(resource, "ObjectReference");
rmm.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(rmm, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
mbean.toString();
Object o = (Object)mbean;
o.toString();
}
public void testObjectToStringOverride() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
RequiredModelMBean rmm = new RequiredModelMBean();
ResourceOverride resource = new ResourceOverride();
rmm.setManagedResource(resource, "ObjectReference");
rmm.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(rmm, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
assertTrue(mbean.toString().equals("Resource"));
Object o = (Object)mbean;
assertTrue(o.toString().equals("Resource"));
}
public void testObjectHashCodeOnProxy() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
RequiredModelMBean rmm = new RequiredModelMBean();
Resource resource = new Resource();
rmm.setManagedResource(resource, "ObjectReference");
rmm.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(rmm, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
mbean.hashCode();
Object o = (Object)mbean;
o.toString();
}
public void testObjectHashCodeOverride() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
RequiredModelMBean rmm = new RequiredModelMBean();
ResourceOverride resource = new ResourceOverride();
rmm.setManagedResource(resource, "ObjectReference");
rmm.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(rmm, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
assertTrue(mbean.hashCode() == 10);
Object o = (Object)mbean;
assertTrue(o.hashCode() == 10);
}
public void testObjectEqualsOnProxy() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
ModelMBean mmbean = new XMBean();
Resource resource = new Resource();
mmbean.setManagedResource(resource, "ObjectReference");
mmbean.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(mmbean, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
MyInterface mbean2 = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
assertTrue(mbean.equals(mbean));
assertTrue(!mbean.equals(mbean2));
assertTrue(!mbean2.equals(mbean));
}
public void testObjectEqualsOverride() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
ModelMBean rmm = new RequiredModelMBean();
ResourceOverride resource = new ResourceOverride("state");
rmm.setManagedResource(resource, "ObjectReference");
rmm.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(rmm, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
assertTrue(mbean.equals(mbean));
}
public void testAttributeNotFoundOnTypedProxy() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
ModelMBean mmbean = new XMBean();
ResourceIncorrectInfo resource = new ResourceIncorrectInfo();
mmbean.setManagedResource(resource, "ObjectReference");
mmbean.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(mmbean, oname);
MyInterface mbean = (MyInterface)MBeanProxy.get(
MyInterface.class, oname, server
);
ProxyContext ctx = (ProxyContext)mbean;
ctx.setExceptionHandler(new DefaultExceptionHandler());
try
{
mbean.setAttributeName2("some name");
}
catch (IllegalArgumentException e)
{
// expected
// by default, if no such attribute 'AttributeName2' exists in the
// MBean metadata (as is the case with ResourceIncorrectInfo), the
// MBeanProxy invocation handler falls back attempting to execute
// MBeanServer.invoke() which fails with IAE.
}
}
public void testAttributeNotFoundOnDeTypedProxy() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
ModelMBean mmbean = new XMBean();
ResourceIncorrectInfo resource = new ResourceIncorrectInfo();
mmbean.setManagedResource(resource, "ObjectReference");
mmbean.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(mmbean, oname);
DynamicMBean mbean = (DynamicMBean)MBeanProxy.get(oname, server);
ProxyContext ctx = (ProxyContext)mbean;
ctx.setExceptionHandler(new DefaultExceptionHandler());
try
{
mbean.setAttribute(new Attribute("AttributeName2", "some name"));
}
catch (AttributeNotFoundException e)
{
// expected
}
}
public void testInheritanceInTypedProxyArgs() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
XMBean mmbean = new XMBean();
ExtendedResource resource = new ExtendedResource();
mmbean.setManagedResource(resource, "ObjectReference");
mmbean.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(mmbean, oname);
MyInterface2 mbean = (MyInterface2)MBeanProxy.get(
MyInterface2.class, oname, server);
assertTrue(mbean.doOperation().equals("doOperation"));
try
{
assertTrue(mbean.executeThis("executeThis").equals("executeThis"));
}
catch (ClassCastException e) {
fail("KNOWN ISSUE: proxy generates incorrect JMX invocation " +
"signature in case argument subclasses are used.");
}
}
public void testInheritanceInProxyAttribute() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
XMBean mmbean = new XMBean();
ExtendedResource resource = new ExtendedResource();
mmbean.setManagedResource(resource, "ObjectReference");
mmbean.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(mmbean, oname);
MyInterface2 mbean = (MyInterface2)MBeanProxy.get(
MyInterface2.class, oname, server);
mbean.setAttribute3("Attribute3");
assertTrue(mbean.getAttribute3().equals("Attribute3"));
}
public void testInheritanceInProxyReturnType() throws Exception
{
MBeanServer server = MBeanServerFactory.createMBeanServer();
ObjectName oname = new ObjectName("test:test=test");
XMBean mmbean = new XMBean();
ExtendedResource resource = new ExtendedResource();
mmbean.setManagedResource(resource, "ObjectReference");
mmbean.setModelMBeanInfo(resource.getMBeanInfo());
server.registerMBean(mmbean, oname);
MyInterface2 mbean = (MyInterface2)MBeanProxy.get(
MyInterface2.class, oname, server);
assertTrue(mbean.runMe("runMe").equals("runMe"));
}
}