/* Generated by Together */

package com.docutech.viewer.db;

import java.io.*;
import java.sql.*;
import javax.sql.*;
import javax.naming.*;
import java.util.*;
import com.jnetdirect.jsql.JSQLConnectionPool;
import com.jnetdirect.jsql.JSQLConnectionPoolDataSource;

public class ConnectionPool {

  private String sFileStore = "TestJNDIFileStore"; // The name of the file for the JNDI implementation
  private String sPooledDSName = "PooledDataSource";   // The name of the pooling datasource
  private Context ctx; // JNDI context
  private static ConnectionPool instance;
  private JSQLConnectionPoolDataSource pooledDS = null;          
  
//------------------------------------------------------------------------------

    public ConnectionPool() {

      initJNDI();
      registerDataSources();      
      pooledDS = getPooledDataSourceFromJNDI();
   //   if (pooledDS != null)
//        useConnectionPool(pooledDS);

    }

//------------------------------------------------------------------------------
    
    public void error(String s, Exception e) {
      System.out.println("Error:"+s+ " "+e.toString());
    }    
//------------------------------------------------------------------------------
  
    public static synchronized ConnectionPool getInstance(){
      if (instance == null){
        instance = new ConnectionPool();
      }
      return instance;
    }

//------------------------------------------------------------------------------

 private JSQLConnectionPoolDataSource getPooledDataSourceFromJNDI() {
    /* Create the datasource to provide the physical connections to the connection pool.
       The datasource is looked up in our JNDI naming service. */
    JSQLConnectionPoolDataSource pooledDS = null;
    try {
      Context ctx = new InitialContext(System.getProperties());
      pooledDS = (JSQLConnectionPoolDataSource) ctx.lookup(sPooledDSName);
      return pooledDS;
    }
    catch (NamingException e) {
      log("JNDI Error:"+ e.toString());
      return null;
    }
  }

//------------------------------------------------------------------------------

  private void initJNDI() {

    /* Create the file store first time - the file store holds the JNDI entries */

    File root = new File(sFileStore);
    if (!root.exists())
      root.mkdir();

    /* Initialize JNDI - tell it to use the File Store provider */

    Hashtable env;
    env = System.getProperties();
    env.put(Context.INITIAL_CONTEXT_FACTORY,
      "com.sun.jndi.fscontext.RefFSContextFactory");
    env.put(Context.PROVIDER_URL, "file:"+sFileStore+"/");

    /* Create a JNDI context and bind it in the naming service */

    try {
      ctx = new InitialContext(env);
    }
    catch (javax.naming.NamingException e) {
      error("init JNDI ", e);
    }
  }

//------------------------------------------------------------------------------
  
  void log(String s){
    System.out.println(s);
  }
  
//------------------------------------------------------------------------------
  
  private void registerDataSources() {
    try {
      /* The datasource used to create physical connections by the pool manager */

      JSQLConnectionPoolDataSource ds = new JSQLConnectionPoolDataSource();
      ds.setServerName("127.0.0.1");
      ds.setDatabaseName("master");

      /* Configure some connection pool properties */

      ds.setMinPoolSize(2);
      ds.setMaxPoolSize(10);
      ds.setMaxIdleTime(60);
      ds.setManagementCycleTime(2);

      ctx.rebind(sPooledDSName, ds);
    }
    catch (Exception e) {
      error("Register Datasources ", e);
    }
  }
  
//------------------------------------------------------------------------------
    
    public java.sql.Connection getConnection() throws SQLException{
      JSQLConnectionPool pool;      
      java.sql.Connection con;
      
      if (pooledDS == null)  {
        throw new IllegalStateException("pooled datasource has not been initialized");      
      }      
      try{
        pool = new JSQLConnectionPool(pooledDS);      
        con = pool.getConnection("sa", "");      
      }
      catch(SQLException e){
        throw new SQLException("PooledDataSource SQL Error:"+ e.toString());          
      }
      return con;
    }
    
//------------------------------------------------------------------------------
    
 private void useConnectionPool(JSQLConnectionPoolDataSource pooledDS) {
    int nExpectedRows = -1;
    try {
      // Create the connection pool using the JNDI data source we have
      JSQLConnectionPool pool = new JSQLConnectionPool(pooledDS);

      // Get connections from the connection pool and use them

      for (int i = 0; i<30; i++) {
        java.sql.Connection c0 = pool.getConnection("sa", "");
        java.sql.Connection c1 = pool.getConnection("sa", "");

        java.sql.Statement s = c0.createStatement();
        java.sql.ResultSet rs = s.executeQuery("SELECT * FROM SYSFILES");
        int nRows = 0;
        while (rs.next()) {
          String sx = rs.getString(1);
          nRows++;
        }
        if (nExpectedRows < 0)
          nExpectedRows = nRows;
        else {
          if (nRows != nExpectedRows) {
            throw new SQLException("Wrong row count, got:"+nRows+" expected:"+nExpectedRows);
          }
        }

        c0.close();
        c1.close();
      }
      // Ask the pool manager to display the number of logical and physical connections it made
      System.out.println(pool.getStatus());
    }
    catch (SQLException e) {
      log("PooledDataSource SQL Error:"+ e.toString());
    }
  }
    
//------------------------------------------------------------------------------  
}
