/** * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You under the Apache License, Version 2.0 * (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.apache.camel.component.jmx; import java.lang.management.ManagementFactory; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Date; import javax.management.InstanceNotFoundException; import javax.management.MBeanRegistrationException; import javax.management.MBeanServer; import javax.management.MBeanServerInvocationHandler; import javax.management.MalformedObjectNameException; import javax.management.ObjectName; import org.apache.camel.builder.RouteBuilder; import org.apache.camel.component.jmx.beans.ISimpleMXBean; import org.apache.camel.component.jmx.beans.SimpleBean; import org.apache.camel.component.mock.MockEndpoint; import org.apache.camel.impl.DefaultCamelContext; import org.apache.camel.impl.SimpleRegistry; import org.junit.After; import org.junit.Before; /** * MBean that is registered for the unit tests. The fixture will register a bean * and provide access to the mxbean so tests can invoke methods on the mxbean * to trigger notifications. */ public class SimpleBeanFixture { /** * domain to use for the mbean */ protected static final String DOMAIN = "TestDomain"; /** * key for the object name */ protected static final String NAME = "name"; protected MBeanServer server; /** * camel context to stand up for the test */ private DefaultCamelContext mContext = new DefaultCamelContext(); /** * registry to store referenced beans (i.e. objectProperties or NotificationFilter) */ private SimpleRegistry mRegistry = new SimpleRegistry(); /** * destination for the simple route created. */ private MockEndpointFixture mMockEndpoint; @Before public void setUp() throws Exception { initServer(); initBean(); initRegistry(); initContext(); startContext(); } protected void startContext() throws Exception { mContext.start(); } @After public void tearDown() throws Exception { if (!mContext.isStopped()) { mContext.stop(); } unregisterBean(makeObjectName("simpleBean")); } protected void initServer() throws Exception { server = ManagementFactory.getPlatformMBeanServer(); } /** * Registers the bean on the platform mbean server */ protected void registerBean(Object aBean, ObjectName aObjectName) throws Exception { server.registerMBean(aBean, aObjectName); } /** * Unregisters the bean */ protected void unregisterBean(ObjectName aObjectName) throws MBeanRegistrationException, InstanceNotFoundException { server.unregisterMBean(aObjectName); } /** * Gets the mxbean for our remote object using the specified name */ protected ISimpleMXBean getMXBean(ObjectName aObjectName) { return MBeanServerInvocationHandler.newProxyInstance( server, aObjectName, ISimpleMXBean.class, false); // revert the above change to the below when we move to JDK 1.6 // ISimpleMXBean simpleBean = JMX.newMXBeanProxy(server, aObjectName, ISimpleMXBean.class); // return simpleBean; } /** * Gets the mxbean for our remote object using the default name "simpleBean" */ protected ISimpleMXBean getSimpleMXBean() throws MalformedObjectNameException { return getMXBean(makeObjectName("simpleBean")); } /** * Makes an ObjectName for the given domain using our domain and the name attribute. */ protected ObjectName makeObjectName(String aName) throws MalformedObjectNameException { ObjectName objectName = new ObjectName(DOMAIN, NAME, aName); return objectName; } /** * Creates the bean and registers it within the mbean server. * Note that we're using a fixed timestamp here to simplify the assertions in the tests */ protected void initBean() throws Exception { registerBean(createSimpleBean(), makeObjectName("simpleBean")); } protected SimpleBean createSimpleBean() throws ParseException { SimpleBean simpleBean = new SimpleBean(); SimpleDateFormat sdf = new SimpleDateFormat("yyyy-dd-MM'T'HH:mm:ss"); Date date = sdf.parse("2010-07-01T10:30:15"); simpleBean.setTimestamp(date.getTime()); return simpleBean; } /** * Initializes the camel context by creating a simple route from our mbean * to the mock endpoint. */ @SuppressWarnings("deprecation") protected void initContext() throws Exception { mContext.setLazyLoadTypeConverters(true); final MockEndpoint mock = mContext.getEndpoint("mock:sink", MockEndpoint.class); mock.setExpectedMessageCount(1); mMockEndpoint = new MockEndpointFixture(mock); mContext.setRegistry(getRegistry()); mContext.addRoutes(new RouteBuilder() { @Override public void configure() throws Exception { from(buildFromURI().toString()).to(mock); } }); } /** * Override this to control the properties that make up the endpoint */ protected JMXUriBuilder buildFromURI() { JMXUriBuilder uri = new JMXUriBuilder().withObjectDomain(DOMAIN) .withObjectName("simpleBean"); return uri; } /** * Override this to put stuff into the registry so it's available to be * referenced. (i.e. NotificationFilter or Hashtable<String,String> for ObjectProperties */ protected void initRegistry() { } protected DefaultCamelContext getContext() { return mContext; } protected void setContext(DefaultCamelContext aContext) { mContext = aContext; } protected SimpleRegistry getRegistry() { return mRegistry; } protected void setRegistry(SimpleRegistry aRegistry) { mRegistry = aRegistry; } protected MockEndpointFixture getMockFixture() { return mMockEndpoint; } }