我将custom jndi-resource factory添加到我的tomcat(嵌入式hornetq的ConnectionFactory的jndi-resource)。我的资源需要一些配置文件;我把它们放在${catalina_home}/hornetq
文件夹中。我有一个测试网络应用程序在tomcat启动时使用此资源。在tomcat启动时,当test-web-app想要使用我的资源时,资源想要锁定配置文件但它不能,并抛出`OverlappingFileLockException:
java.nio.channels.OverlappingFileLockException
at sun.nio.ch.SharedFileLockTable.checkList(FileLockTable.java:255)
at sun.nio.ch.SharedFileLockTable.add(FileLockTable.java:152)
at sun.nio.ch.FileChannelImpl.tryLock(FileChannelImpl.java:1056)
at org.hornetq.core.server.impl.FileLockNodeManager.tryLock(FileLockNodeManager.java:266)
at org.hornetq.core.server.impl.FileLockNodeManager.isBackupLive(FileLockNodeManager.java:82)
at org.hornetq.core.server.impl.HornetQServerImpl$SharedStoreLiveActivation.run(HornetQServerImpl.java:2161)
at org.hornetq.core.server.impl.HornetQServerImpl.start(HornetQServerImpl.java:450)
at org.hornetq.jms.server.impl.JMSServerManagerImpl.start(JMSServerManagerImpl.java:485)
at org.hornetq.jms.server.embedded.EmbeddedJMS.start(EmbeddedJMS.java:115)
at ...
是否可以在tomcat或OS中禁用文件锁定(${catalina_home}/hornetq
目录中的文件)?
更新:
我在tomcat中的context.xml
文件中的jndi资源(名称为/ConnectionFactory
的连接工厂在hornetq-jms.xml
中定义):
<Resource name="jms/ConnectionFactory" auth="Container"
type="javax.jms.ConnectionFactory"
factory="com.wise.jms.hornetq.embedded.HornetqConnectionFactoryBuilder"
cf-name="/ConnectionFactory" singletone="true"/>
我的工厂类:HornetqConnectionFactoryBuilder
。我将包含此类的jar放在${catalina_home}/lib
目录中(嵌入式hornetq将在第一个getObjectInstance
方法调用中启动):
public class HornetqConnectionFactoryBuilder implements ObjectFactory{
private EmbeddedJMS embeddedJMS;
private static final String ConnectionFactoryName = "cf-name";
private static final String HornetqConfigDirectoryPath = getCatalinaHomePath() + "/conf/hornetq/";
private static final String JmsConfigFilePath = HornetqConfigDirectoryPath + "hornetq-jms.xml";
private static final String HornetqConfigFilePath = HornetqConfigDirectoryPath + "hornetq-configuration.xml";
@Override
public Object getObjectInstance(Object obj, Name name, Context nameCtx, Hashtable<?, ?> environment) throws Exception{
Properties properties = initProperties((Reference) obj);
validateProperties(properties);
initHornetq();
String connectionFactoryJndiName = (String) properties.get(ConnectionFactoryName);
return embeddedJMS.lookup(connectionFactoryJndiName);
}
private synchronized void initHornetq() throws Exception{
if (embeddedJMS == null){
embeddedJMS = new EmbeddedJMS();
embeddedJMS.setJmsConfigResourcePath(JmsConfigFilePath);
embeddedJMS.setConfigResourcePath(HornetqConfigFilePath);
embeddedJMS.start();
}
}
private Properties initProperties(Reference reference) throws IOException{
Enumeration<RefAddr> addresses = reference.getAll();
Properties properties = new Properties();
while (addresses.hasMoreElements()) {
RefAddr address = addresses.nextElement();
String type = address.getType();
String value = (String) address.getContent();
properties.put(type, value);
}
return properties;
}
private void validateProperties(Properties properties){
validateSingleProperty(properties, ConnectionFactoryName);
}
private static String getCatalinaHomePath(){
String catalinaHome = System.getenv("CATALINA_HOME");
if (catalinaHome == null){
throw new IllegalArgumentException("CATALINA_HOME environment variable should be set");
}
return "file:///" + catalinaHome.replaceAll("\\\\", "/");
}
private static void validateSingleProperty(Properties properties, String propertyName){
if (!properties.containsKey(propertyName)){
throw new IllegalArgumentException(propertyName + " property should be set.");
}
}
}
我的测试网络应用Test
课程(测试方法将在测试网络应用启动时午餐):
public class Test{
private ConnectionFactory connectionFactory;
public Test() throws NamingException{
Context initCtx = new InitialContext();
Context envCtx = (Context) initCtx.lookup("java:comp/env");
connectionFactory = (ConnectionFactory) envCtx.lookup("jms/ConnectionFactory");
}
public void test() throws JMSException{
Connection connection = connectionFactory.createConnection();
connection.start();
Session session = connection.createSession(true,Session.SESSION_TRANSACTED);
Queue queue = session.createQueue("testQueue");
MessageProducer messageProducer = session.createProducer(queue);
MessageConsumer messageConsumer = session.createConsumer(queue);
TextMessage message1 = session.createTextMessage("This is a text message1");
messageProducer.send(message1);
session.commit();
TextMessage receivedMessage = (TextMessage) messageConsumer.receive(5000);
session.commit();
System.out.println("Message1 received after receive commit: " + receivedMessage.getText());
}
public void setConnectionFactory(ConnectionFactory connectionFactory){
this.connectionFactory = connectionFactory;
}
}
注意:当我把(hornetq)配置文件放在jar类路径中时,我没有问题,一切都很好!! (tomcat:6,hornetq:2.4.0.Final,OS:windows 7)
答案 0 :(得分:0)
您是否在Tomcat中进行了其他部署? 一旦你重新启动tomcat,很有可能首先部署一些其他项目,它们使用lib文件夹中的文件。
尝试在新的tomcat安装中部署它,或从Tomcat的webapps文件夹中删除其他文件夹。