Как вы используете глобальные ресурсы URL-адресов JNDI в Tomcat 8?

Я пытаюсь настроить сервер под управлением Tomcat 8, чтобы ресурсы URL-адреса JNDI были доступны большому количеству приложений, работающих на этом сервере. Приложения представляют собой простой jsp/сервлет с Maven (без Spring).

У меня есть 2 примера глобальных ресурсов, которые я пытаюсь использовать, один из них — DataSource, который работает правильно, а другой — URL-адрес, который не работает.

Источник данных

В Tomcats context.xml внутри элемента GlobalNamingResources

<Resource name="APPNAME" auth="Container" type="javax.sql.DataSource"
   maxTotal="100" maxIdle="30" maxWaitMillis="10000" username="appuser"
   password="password" driverClassName="oracle.jdbc.driver.OracleDriver"
   url="aUrl" />

В Tomcats web.xml элемент верхнего уровня

<resource-ref>
   <res-ref-name>APPNAME</res-ref-name>
   <res-type>javax.sql.DataSource</res-type>
   <res-auth>Container</res-auth>
   <res-sharing-scope>Unshareable</res-sharing-scope>
</resource-ref>

Это все для DataSource, и он действительно работает

Для ресурса URL это есть в файле server.xml.

<Resource name="url/LOGIN_MODULE_CONFIGURATION_SERVICE" auth="Container"
   type="java.net.URL" factory="com.mycompany.objectfactory.JndiUrlObjectFactory"
   url="AValidUrl" />

Моя фабрика объектов была создана так же, как в этом ответе: Tomcat: использовать FTP-соединение через JNDI За исключением того, что я добавил несколько операторов println, чтобы доказать, что он используется и имеет правильный URL-адрес, который он делает.

У меня есть следующий Tomcats web.xml

<resource-ref>
   <res-ref-name>url/LOGIN_MODULE_CONFIGURATION_SERVICE</res-ref-name>
   <res-type>java.net.URL</res-type>
   <res-auth>Container</res-auth>
</resource-ref>

Наконец, код, который обращается к this. Этот код был результатом декомпиляции jar, это не сторонний jar, но у меня нет исходного кода. Исключение возникает в строке jndiReference = ic.lookup(serviceName);. serviceName — это имя ресурса, а jndiRoot всегда имеет значение null (код, вызывающий этот метод, проходит в null). Метод getInitialContext() просто создает новый экземпляр javax.naming.InitialContext, если он еще не создан.

public static URL getUrl(final String serviceName, final String jndiRoot) {
    URL result = null;
    if (!isEmpty((Object) serviceName)) {
        final InitialContext ic = getInitialContext();
        Object jndiReference = null;
        try {
            jndiReference = ic.lookup(serviceName);
        } catch (NamingException ex) {
            ex.printStackTrace();
            if (!isEmpty((Object) jndiRoot)) {
                final String name = String.valueOf(jndiRoot) + serviceName;
                try {
                    jndiReference = ic.lookup(name);
                } catch (NamingException ex2) {
                    ex.printStackTrace();
                }
            }
        }
        if (jndiReference instanceof URL) {
            result = (URL) jndiReference;
        } else if (jndiReference instanceof Reference) {
            final Reference reference = (Reference) jndiReference;
            final RefAddr refAddr = reference.get("spec");
            try {
                result = new URL(getString(refAddr.getContent()));
            } catch (MalformedURLException e) {
                e.printStackTrace();
            }
        }
    }
    return result;
}

Строка из файла свойств, которая сопоставляется с ресурсом propertyserviceurl=url/LOGIN_MODULE_CONFIGURATION_SERVICE

Я также попытался добавить ResourceLink в Tomcats context.xml. Я попытался сделать имя ResourceLink уникальным, а значение global таким же, как у фактического ресурса. Также попытался изменить файл свойств для сопоставления с именем ResourceLink вместо ресурса, но я всегда получаю одни и те же результаты.

<ResourceLink name="url/LOGIN_MODULE_CONFIGURATION_SERVICE" 
    global="url/LOGIN_MODULE_CONFIGURATION_SERVICE" type="java.net.URL" />

Исключение

javax.naming.NameNotFoundException: Name [url/LOGIN_MODULE_CONFIGURATION_SERVICE] is not bound in this Context. Unable to find [url].
at org.apache.naming.NamingContext.lookup(NamingContext.java:816)
at org.apache.naming.NamingContext.lookup(NamingContext.java:173)
at org.apache.naming.SelectorContext.lookup(SelectorContext.java:163)
at javax.naming.InitialContext.lookup(InitialContext.java:417)
at com.mycompany.common.supplement.web.WebHelper.getUrl(WebHelper.java:739)

Я потратил несколько дней на это, и мне трудно понять, какая конфигурация мне нужна, чтобы заставить это работать. Я думаю, что самым большим препятствием является то, что я не могу изменить код Java, который пытается получить доступ к ресурсу.


person Tim    schedule 24.01.2017    source источник


Ответы (1)


Я заставил его работать. Я действительно не понимаю, как работает ResourceLink, поскольку его имя нигде не упоминается. Но если что-то отличается, это не сработает. В основном мне нужно было добавить java:/comp/env/ в начало имени ресурса, так как я не могу обновить код, который вызывает это.

Обновлен ресурс в Tomcats server.xml до

<Resource name="java:/comp/env/url/LOGIN_MODULE_CONFIGURATION_SERVICE" auth="Container"
    type="java.net.URL" factory="com.mycompany.objectfactory.JndiUrlObjectFactory"
    url="AValidUrl" />

Обновлен ResourceLink в Tomcats context.xml до

<ResourceLink name="url/LOGIN_MODULE_CONFIGURATION_SERVICE" 
    global="java:/comp/env/url/LOGIN_MODULE_CONFIGURATION_SERVICE" type="java.net.URL" />

Обновлена ​​запись файла свойств на

propertyserviceurl=java:/comp/env/url/LOGIN_MODULE_CONFIGURATION_SERVICE
person Tim    schedule 24.01.2017