【问题标题】:Trying to work with different remote data sources. Failing - jndi resolve exception尝试使用不同的远程数据源。失败 - jndi 解决异常
【发布时间】:2019-06-09 13:42:33
【问题描述】:

我在 tomcat 上部署了一个应用程序,它尝试使用外部系统 A 和 B 的远程 JMS 队列。外部系统部署在 Weblogic 上,因此为了与它们通信,我还提供了 wlthint3client。

这是我的代码:

public void myMethod () {
   // Sending message to first ext system
   // jndi queue name - topic1.extsys1.tosend.messages
   magicMethod(Params of External system A);

   // Sending message to second ext system
   // jndi queue name - topic1.extsys2.tosend.messages
   magicMethod(Params of External system B);

   // AGAIN Sending message to FIRST ext system
   // jndi queue name - topic1.extsys1.tosend.messages
   magicMethod(Params of External system A);  
}

private void magicMethod(String factoryName, String url, String connectionFactoryJNDI, String queueName) throws Exception {

    javax.jms.QueueConnectionFactory queueConnectionFactory = null;
    javax.jms.QueueSession queueSession = null;
    javax.jms.Queue queue = null;
    javax.jms.QueueSender queueSender = null;
    javax.jms.QueueConnection queueConnection = null;
    InitialContext ic = null;

    try {
        final Properties initialContextProperties = new Properties();
        initialContextProperties.put(Context.INITIAL_CONTEXT_FACTORY, factoryName);
        initialContextProperties.put(Context.PROVIDER_URL, url);
        initialContextProperties.put(Context.SECURITY_PRINCIPAL, "");
        initialContextProperties.put(Context.SECURITY_CREDENTIALS, "");
        ic = new InitialContext(initialContextProperties);
        queueConnectionFactory = (QueueConnectionFactory) ic.lookup(connectionFactoryJNDI);
        queue = (javax.jms.Queue) ic.lookup(queueName);
    } catch (NamingException e) {
        System.out.println("Could not create JNDI context: " + e.getMessage());
    }

    try {
        queueConnection = queueConnectionFactory.createQueueConnection();
        queueSession = queueConnection.createQueueSession(false, Session.AUTO_ACKNOWLEDGE);
        queueSender = queueSession.createSender(queue);
        ObjectMessage objectMessage = queueSession.createObjectMessage("message");
        queueSender.send(objectMessage);
    } catch (JMSException e) {
        System.out.println(e.getMessage());
    } finally {
        ic.close();
        queueConnection.close();
        queueSession.close();
        queueSender.close();
    }
}

当我向分机系统 A 发送消息时 - 一切正常。 向分机系统 B 发送消息 - 仍然发送消息,一切正常。

当再次尝试向分机系统 A 发送消息时 - 我失败了。

无法创建 JNDI 上下文:尝试查找“topic1.extsys1.tosend.messages”时未找到子上下文“extsys1”。已解决'topic1'

所以我正在尝试理解:

  1. 我做错了什么?
  2. 为什么在我成功发送到外部系统 B 后,它没有向系统 A 发送消息?
  3. 这些内部 java 对象(InitialContext、JNDI 对象等)是否在某处具有某种状态?也许我需要清洁一些东西?
  4. 我觉得 JNDI 名称有点乱...
  5. 也许我需要更改名称? (实际上我已经尝试过使用完全不同的 jndi 队列名称但没有效果,但是我没有重新启动外部系统,不确定是否需要)。

任何想法,移动方向???请

ps - jms 服务器和 jms 模块在 A 和 B 外部系统中具有相同的名称。提供者 URL 是 - ext1.xxx.corp.com, ext2.xxx.corp.com

【问题讨论】:

    标签: java jms weblogic jndi initial-context


    【解决方案1】:

    我不确定 JNDI 查找失败的原因。 JNDI 对象没有任何状态,至少不符合规范,但您的特定实现可能有一些非规范行为。这也可能只是您的 JNDI 实现中的一个错误。

    但是,我可以说您的代码在这里采用了一种重要的反模式,因为它对您发送的每条消息执行以下操作:

    • JNDI 查找(可能需要网络往返)
    • 创建 JMS 连接(当然需要网络往返)
    • 创建 JMS 会话(几乎可以肯定需要网络往返)
    • 创建 JMS 生产者

    这是对资源的极大浪费。至少您应该缓存 JNDI 查找的结果(这可能会解决您的问题)以及您的 JMS 连接工厂。理想情况下,您会为 JMS 连接使用池。

    【讨论】:

      【解决方案2】:

      这是虚拟代码,只是为了描述情况。

      答案在这里 - JMSTemplate with multiple brokers. Destination resolving exception

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2016-06-23
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2022-01-24
        • 1970-01-01
        相关资源
        最近更新 更多