001 /** 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017 package org.apache.activemq.camel.component; 018 019 import java.lang.reflect.Constructor; 020 021 import javax.jms.ConnectionFactory; 022 023 import org.apache.activemq.Service; 024 import org.apache.activemq.spring.ActiveMQConnectionFactory; 025 import org.apache.camel.component.jms.JmsConfiguration; 026 import org.springframework.jms.connection.SingleConnectionFactory; 027 import org.springframework.jms.connection.JmsTransactionManager; 028 import org.springframework.jms.core.JmsTemplate; 029 import org.springframework.transaction.PlatformTransactionManager; 030 031 /** 032 * @version $Revision: 910986 $ 033 */ 034 public class ActiveMQConfiguration extends JmsConfiguration { 035 private String brokerURL = ActiveMQConnectionFactory.DEFAULT_BROKER_URL; 036 private boolean useSingleConnection = false; 037 private boolean usePooledConnection = true; 038 private String userName; 039 private String password; 040 private ActiveMQComponent activeMQComponent; 041 042 public ActiveMQConfiguration() { 043 } 044 045 public String getBrokerURL() { 046 return brokerURL; 047 } 048 049 /** 050 * Sets the broker URL to use to connect to ActiveMQ using the 051 * <a href="http://activemq.apache.org/configuring-transports.html">ActiveMQ URI format</a> 052 * 053 * @param brokerURL the URL of the broker. 054 */ 055 public void setBrokerURL(String brokerURL) { 056 this.brokerURL = brokerURL; 057 } 058 059 public boolean isUseSingleConnection() { 060 return useSingleConnection; 061 } 062 063 public String getUserName() { 064 return userName; 065 } 066 067 /** 068 * Sets the username to be used to login to ActiveMQ 069 * @param userName 070 */ 071 public void setUserName(String userName) { 072 this.userName = userName; 073 } 074 075 public String getPassword() { 076 return password; 077 } 078 079 /** 080 * Sets the password/passcode used to login to ActiveMQ 081 * 082 * @param password 083 */ 084 public void setPassword(String password) { 085 this.password = password; 086 } 087 088 /** 089 * Enables or disables whether a Spring {@link SingleConnectionFactory} will be used so that when 090 * messages are sent to ActiveMQ from outside of a message consuming thread, pooling will be used rather 091 * than the default with the Spring {@link JmsTemplate} which will create a new connection, session, producer 092 * for each message then close them all down again. 093 * <p/> 094 * The default value is true so that a single connection is used by default. 095 * 096 * @param useSingleConnection 097 */ 098 public void setUseSingleConnection(boolean useSingleConnection) { 099 this.useSingleConnection = useSingleConnection; 100 } 101 102 public boolean isUsePooledConnection() { 103 return usePooledConnection; 104 } 105 106 /** 107 * Enables or disables whether a PooledConnectionFactory will be used so that when 108 * messages are sent to ActiveMQ from outside of a message consuming thread, pooling will be used rather 109 * than the default with the Spring {@link JmsTemplate} which will create a new connection, session, producer 110 * for each message then close them all down again. 111 * <p/> 112 * The default value is false by default as it requires an extra dependency on commons-pool. 113 */ 114 public void setUsePooledConnection(boolean usePooledConnection) { 115 this.usePooledConnection = usePooledConnection; 116 } 117 118 @Override 119 public PlatformTransactionManager getTransactionManager() { 120 PlatformTransactionManager answer = super.getTransactionManager(); 121 if (isTransacted() && answer == null) { 122 // lets auto-default the transaction manager if its not specified 123 answer = createTransactionManager(); 124 setTransactionManager(answer); 125 answer = getTransactionManager(); 126 } 127 return answer; 128 } 129 130 /** 131 * Factory method to create a default transaction manager if one is not specified 132 */ 133 protected PlatformTransactionManager createTransactionManager() { 134 JmsTransactionManager answer = new JmsTransactionManager(getConnectionFactory()); 135 answer.afterPropertiesSet(); 136 return answer; 137 } 138 139 protected void setActiveMQComponent(ActiveMQComponent activeMQComponent) { 140 this.activeMQComponent = activeMQComponent; 141 } 142 143 @Override 144 protected ConnectionFactory createConnectionFactory() { 145 ActiveMQConnectionFactory answer = new ActiveMQConnectionFactory(); 146 if (userName != null) { 147 answer.setUserName(userName); 148 } 149 if (password != null) { 150 answer.setPassword(password); 151 } 152 if (answer.getBeanName() == null) { 153 answer.setBeanName("Camel"); 154 } 155 answer.setBrokerURL(getBrokerURL()); 156 if (isUseSingleConnection()) { 157 SingleConnectionFactory scf = new SingleConnectionFactory(answer); 158 if (activeMQComponent != null) { 159 activeMQComponent.addSingleConnectionFactory(scf); 160 } 161 return scf; 162 } 163 else if (isUsePooledConnection()) { 164 ConnectionFactory pcf = createPooledConnectionFactory(answer); 165 if (activeMQComponent != null) { 166 activeMQComponent.addPooledConnectionFactoryService((Service) pcf); 167 } 168 return pcf; 169 } 170 else { 171 return answer; 172 } 173 } 174 175 protected ConnectionFactory createPooledConnectionFactory(ActiveMQConnectionFactory connectionFactory) { 176 // lets not use classes directly to avoid a runtime dependency on commons-pool 177 // for folks not using this option 178 try { 179 Class type = loadClass("org.apache.activemq.pool.PooledConnectionFactory", getClass().getClassLoader()); 180 Constructor constructor = type.getConstructor(org.apache.activemq.ActiveMQConnectionFactory.class); 181 return (ConnectionFactory) constructor.newInstance(connectionFactory); 182 } 183 catch (Exception e) { 184 throw new RuntimeException("Failed to instantiate PooledConnectionFactory: " + e, e); 185 } 186 } 187 188 public static Class<?> loadClass(String name, ClassLoader loader) throws ClassNotFoundException { 189 ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader(); 190 if (contextClassLoader != null) { 191 try { 192 return contextClassLoader.loadClass(name); 193 } 194 catch (ClassNotFoundException e) { 195 try { 196 return loader.loadClass(name); 197 } 198 catch (ClassNotFoundException e1) { 199 throw e1; 200 } 201 } 202 } else { 203 return loader.loadClass(name); 204 } 205 } 206 }