简体   繁体   English

使用Jet的JNDI查找失败与MySQL建立JDBC连接池?

[英]JNDI lookup failing with Jetty for JDBC connection pooling with MySQL?

I'm using Jetty 9.2 (embedded) with the standard MySQL connector API and I'm very confused by how this is supposed to be setup. 我正在使用带有标准MySQL连接器API的Jetty 9.2(嵌入式),我对如何设置它感到困惑。 Currently, I have this in my web.xml file: 目前,我在我的web.xml文件中有这个:

<webapp ...

    <resource-ref>
        <description>JDBC Data Source</description>
        <res-ref-name>jdbc/DataSource</res-ref-name>
        <res-type>javax.sql.DataSource</res-type>
        <res-auth>Container</res-auth>
    </resource-ref>
</webapp>

...and this in my jetty-env.xml: ...这在我的jetty-env.xml中:

<Configure class="org.eclipse.jetty.webapp.WebAppContext">

   <New id="DatabaseConnector" class="org.eclipse.jetty.plus.jndi.Resource">
        <Arg></Arg>
        <Arg>jdbc/DataSource</Arg>
        <Arg>
            <New class="com.mysql.jdbc.jdbc2.optional.MysqlConnectionPoolDataSource">
                <Set name="Url">jdbc:mysql://localhost:3306/DBName</Set>
                <Set name="User">user</Set>
                <Set name="Password">pass</Set>
            </New>
        </Arg>
    </New>

 </Configure>

...and this code to initialize: ...以及此代码初始化:

Context envCtx = (Context) new InitialContext().lookup("java:comp/env");
DataSource datasource = (DataSource) envCtx.lookup("jdbc/DataSource");

When I try to fire up the server, I get the error javax.naming.NameNotFoundException; remaining name 'jdbc/DataSource' 当我尝试启动服务器时,我收到错误javax.naming.NameNotFoundException; remaining name 'jdbc/DataSource' javax.naming.NameNotFoundException; remaining name 'jdbc/DataSource' . javax.naming.NameNotFoundException; remaining name 'jdbc/DataSource' I've tried lots of different variations of the strings in the code initialization, like removing the lookup call on the InitialContext object, but I just keep getting variations of the same error with a different name value; 我已经在代码初始化中尝试了很多不同的字符串变体,比如删除了InitialContext对象上的lookup调用,但我只是不断地使用不同的name值来获取相同错误的变体。

Both of the xml files are located in my /WAR/WEB-INF directory. 这两个xml文件都位于我的/WAR/WEB-INF目录中。 I've looked at loads of previous questions and tutorials, blogs etc. but I'm getting nowhere. 我看过很多以前的问题和教程,博客等,但我无处可去。

It was a combination of problems specific to embedded Jetty. 这是嵌入式Jetty特有的问题组合。

First, my launcher code that was configuring and launching the web server was doing the JNDI lookup before I actually started the web server ie before calling server.start() , so the JNDI configuration was not initialized at that stage. 首先,配置和启动Web服务器的启动器代码在我实际启动Web服务器之前server.start()即在调用server.start()之前server.start()执行JNDI查找,因此JNDI配置未在该阶段初始化。

But even making this change didn't work, because the envCtx.lookup("jdbc/DataSource") needs to be called from a thread that's associated with the WebApp. 但即使进行此更改也不起作用,因为需要从与WebApp关联的线程调用envCtx.lookup("jdbc/DataSource") So I moved that code to a static block that gets called the first time a database connection is requested by a web server request. 所以我将该代码移动到静态块,在第一次Web服务器请求请求数据库连接时调用该块。

In the end, I ended up with something like this for my launcher code : 最后,我为我的启动器代码结束了这样的事情:

public static void main(String[] args) {
    Server server = new Server();

    //Enable parsing of jndi-related parts of web.xml and jetty-env.xml
    ClassList classlist = ClassList.setServerDefault(server);
    classlist.addAfter(
            "org.eclipse.jetty.webapp.FragmentConfiguration", 
            "org.eclipse.jetty.plus.webapp.EnvConfiguration", 
            "org.eclipse.jetty.plus.webapp.PlusConfiguration");
...
...
server.start();

The JNDI lookup cannot be made by this main thread, so put it somewhere like the init method of a servlet request, or like I did, a synchronized method of a static database accessor class that gets used by servlets eg JNDI查找不能由这个主线程进行,所以把它放在像servlet请求的init方法那样的地方,或者就像我做的那样,是servlet使用的静态数据库访问器类的同步方法,例如

public class DatabaseUtils {

    private static DataSource datasource;

    private static synchronized Connection getDBConnection() throws SQLException {
        if (datasource == null) {
            initDataSource();
        }
        return datasource.getConnection();
    }

    public static void initDataSource() {
        try {
             datasource = (DataSource) new InitialContext().lookup("java:comp/env/jdbc/DataSource");
             LOG.info("Database connection pool initalized successfully");
        } catch (Exception e) {
            LOG.error("Error while initialising the database connection pool", e);
        }
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM