Example: Using connections with concurrency
A Runnable or Callable can use the connections that its creating component obtained using java:comp resource references.
For more information on resource references, refer to the References topic. The following is an example of a task that uses connections correctly:
class GoodTask implements Callable<Object>
{
DataSource ds;
public Task() throws NamingException
{
// Cache a connection factory or datasource
// as class instance data.
InitialContext ic = new InitialContext();
// It is assumed that the created Java EE component has this
// resource reference defined in its deployment descriptor.
ds = (DataSource)ic.lookup("java:comp/env/jdbc/myDataSource");
}
// When the asynchronous bean method is called, get a connection,
// use it, then close it.
public Object call() throws SQLException
{
try (Connection c = ds.getConnection()) {
// Use the connection now.
return someResult;
}
}
}
The following example of a task that uses connections incorrectly:
class BadTask implements Callable<Object>
{
DataSource ds;
// Do not do this. You cannot cache connections across method calls.
Connection c;
public BadTask() throws NamingException, SQLException
{
// Cache a connection factory or datasource as
// class instance data.
InitialContext ic = new InitialContext();
ds = (DataSource)ic.lookup("java:comp/env/jdbc/myDataSource");
// Here, you broke the rules.
c = ds.getConnection();
}
// Now when the method is called, illegally use the cached connection
// and you likely see J2C related exceptions at run time.
public Object call()
{
// Use the connection now.
return someResult;
}
}