home.


Tagged: tomcat-jndi


Tomcat 7: JDBC via JNDI using sqlite

First download the sqlite jdbc driver from https://bitbucket.org/xerial/sqlite-jdbc/downloads and copy it into your lib/ folder in your tomcat directory, /usr/share/tomcat7/lib/. Then restart tomcat so it can find your new jar.

Then add a reference to a new jdbc resource in your web/META-INF/context.xml file. It defines a JNDI name, its class type, the driver class name that relates to the jar we just installed above, and a url to connect to the database. In my case I’m pointing to a directory (which must exist) on the file system.

<Context>
    <Resource name="jdbc/sqlite"
    type="javax.sql.DataSource"
    driverClassName="org.sqlite.JDBC"
    url="jdbc:sqlite:/var/lib/tomcat7/dbs/test.db"
    />
</Context>

In addition, you have to add the resource in your web.xml file. Note the name is the same the name above.

...
<resource-ref>
    <res-ref-name>jdbc/sqlite</res-ref-name>
    <res-type>javax.sql.DataSource</res-type>
</resource-ref>
...

Now you can make reference to the database in your Java code. This is lifted from the sqlite example page:

Connection conn = null;
try {
    Context ctx = new InitialContext();
    DataSource ds = (DataSource) ctx.lookup("java:comp/env/jdbc/sqlite");
    conn = ds.getConnection();
    Statement statement = conn.createStatement();
try {
    statement.executeUpdate("create table thing(x integer)");
} catch (Exception e) { 
     // Could well be already there
}
statement.executeUpdate("insert into thing values(42)");
ResultSet rs = statement.executeQuery("select * from thing");
while (rs.next()) {
writer.println("id = " + rs.getInt(1));
} catch (Exception e) {
    writer.println(e.getMessage());
} finally {
    try {
        if (conn != null) conn.close();
    } catch (SQLException e) {
        writer.println(e);
    }
}
java tomcat-jndi tomcat-jdbc jdbc sql sqlite tomcat

tomcat7-jdni-bean-factory

You can use a context to grab a simple JavaBean instance. First create the POJO in your src/ directory:

package org.denevell.tomcat;
 public class MyBean {
   private String foo = "Default Foo";
   public String getFoo() {
    return this.foo;
  }
 public void setFoo(String foo) {
    this.foo = foo;
 }
}

Then tell your web.xml that you can get this via JNDI:

 <web-app ... >
   ...
   <resource-env-ref>
     <resource-env-ref-name>
       bean/MyBeanFactory
     </resource-env-ref-name>
     <resource-env-ref-type>
       org.denevell.MyBean
     </resource-env-ref-type>
   </resource-env-ref>
   ...
 </webapp>

The resource-env-ref-name gives your factory name that will be used later. The resource-env-ref-type tells it what class to to return.

You also need to define the factory in the Tomcat specific web/META-INF/context.xml:

  <Context>
    <Resource name="bean/MyBeanFactory"
            type="org.denevell.tomcat.MyBean"
            factory="org.apache.naming.factory.BeanFactory"
            foo="From context.xml"/>
  </Context>

It first refers to the name above, and defines its class again, tells Tomcat what factory to use to create this resource and sets an initial parameter, calling getFoo() on the object in this case. This resource is by default a singleton.

You can now get an instance of that Java bean as follows:

  ...
  try {
    Context initCtx = new InitialContext();
    Context envCtx = (Context) initCtx.lookup("java:comp/env");
    MyBean bean = (MyBean) envCtx.lookup("bean/MyBeanFactory");
    bean.setFoo(bean.getFoo()+".");
    writer.println("foo = " + bean.getFoo());
  } catch(NamingException e) {
    writer.println("Naming exception.");
  }
  ...

We first get a InitialContext(), and get the environmental Context from such, ‘java:comp/env’ being the entry point to your servlet’s JNDI environment. Then we use that to refer to the factory using the JNDI name we defined. You can now play with the object to your heart’s content.

tomcat tomcat-jndi java

Page 1 of 1