I overrode the ActionServlet's initOther() method and put this code in 
there:

// this code runs when the servlet gets initialized
DataSource ds =
this.findDataSource("org.apache.struts.action.DATA_SOURCE");

Database.setSystemDatabase(new Database(ds));

// now anywhere in the system you can call:
// Database db = Database.getSystemDatabase();
// Connection conn = db.getConnection();

The Database's getConnection() method just calls its internal DataSource's 
getConnection method.  The getSystemDatabase method does not instantiate a 
new Database, it just returns the one you passed in the setter.

I've added some things to your implementation below:


>There's a couple of pieces missing in my understanding of this:
>
>1.     How do you get hold of the DataSource of the ActionServlet subclass?
>Is this what getSystemDatabase() does? If so, then how?
>2.     Am I right in assuming that the getSystemDatabase() method
>instantiates a new Database class, finds the DataSource, then sets a
>property with a reference to the DataSource?
>
>My initial attempt at an implementation of this goes something like this:
>
>package au.com.sunesis.timesheets;
>
>import javax.sql.DataSource;
>import java.sql.Connection;
>import java.sql.SQLException;
>
>public class Database {
>     private DataSource dataSource;
>     // keep copy of system database here
>     private static Database systemDatabase = null;
>
>     public Database(DataSource dataSource) {
>             // who/what calls this constructor?
              // the servlet's initOther() method
>         this.dataSource = dataSource;
>     }
>
>     public static void setSystemDatabase(Database db) {
>             systemDatabase = db;
>     }
>     public static Database getSystemDatabase() {
>             // mysterious - what must go in here to make this work?
>             // just return the database set with setSystemDatabase()
>             return systemDatabase;
>     }
>
>     // let caller deal with SQLException, we don't know what to     // do 
>with it here
>     public Connection getConnection() throws SQLException{
>          return dataSource.getConnection();
>     }
>}
>
>
>Thanks
>
>Steve
>
>---
>
>
>Here's how I do it:
>I defined a Database class with a constructor that takes a Datasource
>object.  It also has a static getSystemDatabase() method and a 
>getConnection
>
>method.  I subclassed the struts ActionServlet and get ahold of its
>DataSource (defined in struts-config.xml) and pass it into my Database
>object.  Then anywhere in the system I can call
>Database.getSystemDatabase().getConnection() to get a connection to the
>database.
>
>This also works outside of webapps because the Database class just knows
>about DataSources and not struts stuff.  Also, this lets your logic beans
>not know about servlets or struts which is much cleaner in my opinion.
>
>Hope that helps,
>Dave
>
>-----Original Message-----
>From: Steve McLeod
>Sent: Monday, 2 September 2002 10:10 AM
>To: '[EMAIL PROTECTED]'
>Subject: Database Connection in Logic Beans - pooling?
>
>I am using:
>Tomcat 4.0
>Struts 1.0.2
>
>The problem
>========
>
>I have successfully used the Struts database connection pooling in a trial
>web app, but as far as I can tell, a reference to the datasource can only 
>be
>obtained from within an Action class (or directly within a JSP page but
>let's not think about that today).
>
>However I would like to have logic beans which handle database access,
>rather than have this in the Action class. But I can't get a reference to
>the datasource from the logic bean because it doesn't have a ServletContext
>to which I can get a handle.
>
>I have toyed with various ideas:
>- Initialise a logic bean by passing it a reference to the Servlet
>- Acquire a connection in the Action class and pass that to the bean
>
>But really, I would rather the logic bean know inherently how to acquire a
>database connection.
>
>My current workaround is to not use the Struts connection pooling, and
>rather to manually create a connection each time database access needs to 
>be
>done, then destroy it. But this is clearly not suitable for our production
>environment.
>
>
>The context of my problem
>==================
>
>I want to use some code like this in a JSP:
>
><jsp:useBean id="abean" scope="page"
>class="au.com.sunesis.timesheets.ClientManager" />
><table border="1">
>     <tr>
>         <th>#</th>
>         <th>Client</th>
>         <th>Active</th>
>     </tr>
><logic:iterate id="clientList" name="abean" property="clients"
>type="au.com.sunesis.timesheets.Client">
>     <tr>
>         <td><bean:write name="clientList" property="clientID"/></td>
>         <td><bean:write name="clientList" property="clientName"/></td>
>         <td><bean:write name="clientList" property="active"/></td>
>     </tr>
></logic:iterate>
>
>
>The idea is that ClientManager is used to handle all general database tasks
>for the Client bean (which maps to a Client entity in the database).
>ClientManager.getClients() connects to the database, creates an ArrayList 
>of
>Client objects, one for each row in the database, and returns the 
>ArrayList.
>
>ClientManager has other methods, such as:
>-         ClientManager.delete(Client c), which deletes the row in the
>database entity corresponding to the specified client.
>-         ClientManager.findByPrimaryKey(int ID) which returns the Client
>which matches the specified ID
>-         ClientManager.save(Client c), which stores the client in the
>database, creating or updating as necessary
>
>So an Action class can also call any of these directly, and it really
>shouldn't care about how these work and how they store to/retrieve from the
>database. But I can't think of the elegant way to do this and still be able
>to use the Struts connection pooling.
>
>Any thoughts?
>
>Thanks
>
>Steve McLeod
>
>
>




_________________________________________________________________
Chat with friends online, try MSN Messenger: http://messenger.msn.com


--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to