I'm wondering about best practices to use for managing database connections in Stripes with Guice. Ideally I would want to enforce the following:
One db connection is used per thread/http request (possibly with guice binding the connection to a provider with the ServletScope.REQUEST scope) All queries are performed in one transaction, and then commited or rolled back at the end.
My question is: What should be creating/closing my database connections?
Is it a bad idea to use a Stripes Interceptor to open and close the connections?
I have a large connection of Manager classes which all perform custom SQL queries for various tables in my database. Currently all these Manager classes have a method like the following:
public abstract class MyManagerBase implements IMyManager {
@Inject
public void setConnection(Connection conn) {
this.conn = conn;
}
}
The managers themselves subclass this and don't create or close the connection.
I have action beans like this:
public class MyActionBean implements ActionBean {
@Inject IMyManager myManager;
@DefaultHandler
public Resolution save() {
myManager.doStuff(...);
}
...
}
I have a guice config like this:
public class MyConfigModule extends AbstractModule {
@Override
protected void configure() {
install(new ServletModule());
bind(IMyManager.class).to(MyManagerImpl.class);
bind(Connection.class).toProvider(MyConnectionProvider.class).in(ServletScopes.REQUEST);
}
So far what I'm thinking is using an interceptor to inject the managers and at the same time, the same connection into all the managers for that http request.
My interceptor attempt is looking like this so far:
@Override
public Resolution intercept(ExecutionContext executionContext) throws Exception {
Connection conn = null;
switch( executionContext.getLifecycleStage() ) {
case ActionBeanResolution:
log.debug("Intercepting: ActionBeanResolution");
// Inject dependencies into ActionBeans
injector.injectMembers( executionContext.getActionBeanContext() );
Resolution resolution = executionContext.proceed();
injector.injectMembers( executionContext.getActionBean() );
return resolution;
case RequestComplete:
log.debug("Intercepting: RequestComplete");
executionContext.getActionBean();
Connection conn = injector.getInstance(Connection.class);
conn.commit();
conn.close();
}
}
}