<?xml version="1.0"?> 
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output method="text"/>


<xsl:template match="/"><xsl:if test="object/packageName">package <xsl:value-of select="object/packageName"/>;</xsl:if>

import java.sql.*;
import java.util.*;
import java.io.*;
 
/* 
 * <xsl:value-of select="object/className"/>
 *
 * $Author: jd $
 * $Date: 2002/08/10 02:57:13 $
 * $Revisions: $
 * $Source: /cvs/sqlObject/oracleObjectPersisterTemplate.xsl,v $
 *  To create a new <xsl:value-of select="object/className"/>
 * 
 *    <xsl:value-of select="object/className"/> instance = new <xsl:value-of select="object/className"/>
 *     .. call the set methods                       // Set the fields as needed
 *    String key = instance.store();                 // .store() inserts record to database
 *                                                   // DB sequence "<xsl:value-of select="object/sequenceName"/>" is used to get
 *                                                   // next primary key
 *
 *  To get a <xsl:value-of select="object/className"/> from the database
 *                                                       // To retrieve a <xsl:value-of select="object/className"/> from database
 *    <xsl:value-of select="object/className"/> instance = new <xsl:value-of select="object/className"/>("1234");              // pass the primary key to constructor
 *    ... call the get() methods                         // and then call the getter methods             
 * 
 *
 *  To update an existing <xsl:value-of select="object/className"/>                 
 *                                                        // To update an existing OrderObj
 *    <xsl:value-of select="object/className"/> instance = new <xsl:value-of select="object/className"/>("1234");               // get it from database, call the setter methods
 *     .. call the set methods                            // and then call store()
 *    instance.store(); 
 *
 *
 */
public class <xsl:value-of select="object/className"/> {

  private long key = 0;
<xsl:for-each select="object/column">  private <xsl:value-of select="javaDataType"/><xsl:text> </xsl:text><xsl:value-of select="property"/> = <xsl:choose>
<xsl:when test="treatAs = 'String'">""</xsl:when>
<xsl:when test="treatAs = 'int'">0</xsl:when>
<xsl:when test="treatAs = 'long'">0</xsl:when>
<xsl:when test="treatAs = 'float'">0</xsl:when>
<xsl:when test="treatAs = 'double'">0</xsl:when>
<xsl:when test="treatAs = 'GregorianCalendar'">null</xsl:when>
<xsl:when test="treatAs = 'OracleClob'">""</xsl:when>
<xsl:when test="treatAs = 'OracleLong'">""</xsl:when>
</xsl:choose><xsl:text>;
</xsl:text>
</xsl:for-each>
<xsl:for-each select="object/toOneJoinedTable">
<xsl:text>  </xsl:text>public <xsl:value-of select="ClassName"/><xsl:text> </xsl:text><xsl:value-of select="InstanceName"/>  = null;
</xsl:for-each>

<xsl:for-each select="object/toManyJoinedTable"><xsl:text>
  private ArrayList arrayListOf</xsl:text><xsl:value-of select="ClassName"/>s = null;  //Store sub-objects to this one
  </xsl:for-each>
<xsl:for-each select="object/xrefToManyJoinedTable"><xsl:text>
  private ArrayList arrayListOf</xsl:text><xsl:value-of select="ClassName"/>s = null; //Store sub-objects to this one
  </xsl:for-each>

  private boolean isDirty = false;

  /**
   *
   * To get an existing <xsl:value-of select="object/className"/> call constructor with primary key
   *
   */
  public <xsl:value-of select="object/className"/>(long keyIn) {  
    Connection conn = null;
    Statement stmt = null;
    try {
     conn = getConnection();
     stmt = conn.createStatement();
    } catch (SQLException exp) {             
      log("Driver(key) constructor, Exception: " + exp.getMessage());
    } 

    key = keyIn;
    ResultSet rset = doSelect(conn, stmt);
<xsl:for-each select="object/toOneJoinedTable"><xsl:text>    </xsl:text><xsl:value-of select="InstanceName"/> = new <xsl:value-of select="ClassName"/>(rset);
</xsl:for-each>
    try {
      rset.close();
      stmt.close();
      conn.close();
    } catch (SQLException exp) {             
      log("<xsl:value-of select="object/className"/>(key) constructor, Exception: " + exp.getMessage());
    } 
<xsl:for-each select="object/toManyJoinedTable"><xsl:text>    load</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s();</xsl:text>
</xsl:for-each>
<xsl:for-each select="object/xrefToManyJoinedTable"><xsl:text>    load</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s();
</xsl:text>
</xsl:for-each>

  }


  /**
   *
   * To populate a <xsl:value-of select="object/className"/> where the sql select was done earlier by another object
   * call this constructor with the result set.
   *   
   */
  public <xsl:value-of select="object/className"/>(ResultSet rset) {  
    applyResultSet(rset);                         //Populate this object with values from db 
<xsl:for-each select="object/toOneJoinedTable"><xsl:text>    </xsl:text><xsl:value-of select="InstanceName"/> = new <xsl:value-of select="ClassName"/>(rset);
</xsl:for-each>
  }

  /***
   * To create a new <xsl:value-of select="object/className"/> call no args constructor 
   * then call the "set()" methods, and finally "store()"
   */
  public <xsl:value-of select="object/className"/>() {  
<xsl:for-each select="object/toOneJoinedTable"><xsl:text>    </xsl:text><xsl:value-of select="InstanceName"/> = new <xsl:value-of select="ClassName"/>();
</xsl:for-each>
  }


  /**
   *
   * Persist our properties to the db.  Also call store() on any dependent objects.
   * If no Connection was passed in then we are responisible for beginning the transaction
   * Turn off auto commit, and rollback if we get exception from this or any dependent objects
   *
   */
  public long store() throws Exception { 
    long returnKey = key;
    Connection conn = getConnection();
    try { 
      conn.setAutoCommit(false); 
      log("<xsl:value-of select="object/className"/>.store(), Starting transaction");
      returnKey = store(conn);
      conn.commit();  
      log("<xsl:value-of select="object/className"/>.store(), No Exceptions Committing");
    }
    catch (Exception exp) {    //Any exception thrown by store causes a rollback. 
      log("<xsl:value-of select="object/className"/>.store(), Exception: " + exp.getMessage());
      try {                      
        log("<xsl:value-of select="object/className"/>.store(), Failed: RollingBack");
        conn.rollback();
      } catch (SQLException rollbackExp) {             
        log("<xsl:value-of select="object/className"/>.store(), Exception: " + rollbackExp.getMessage());
      } 
      throw exp;  //Throw exception back up so that user interface can report error
    }
    finally { 
      try {
        conn.close();
      } catch (SQLException closeExp) {             
        log("<xsl:value-of select="object/className"/>.store(), Exception: " + closeExp.getMessage());
      } 
    }
    return returnKey;

  }


  /**
   *
   * Persist our properties to the db.  Also call store() on any dependent objects.
   * If a Connection was passed in then a object higher up is handling the transactions 
   * for us. Throw on any exceptions so that the higher object can catch them and rollback. 
   * This method will do an insert for new <xsl:value-of select="object/className"/> and a update for existing ones    
   *
   */
  public long store(Connection conn) throws Exception { 
    long returnKey = key;
      if ( key == 0 ) {   
<xsl:for-each select="object/toOneJoinedTable"><xsl:if test="not(readOnly)"><xsl:text>        </xsl:text><xsl:value-of select="PropertyName"/> = <xsl:value-of select="InstanceName"/>.store(conn);<xsl:text>
</xsl:text></xsl:if></xsl:for-each>        returnKey = insertToDB(conn); 
      }
      else { 
<xsl:for-each select="object/toOneJoinedTable"><xsl:if test="not(readOnly)"><xsl:text>        </xsl:text><xsl:value-of select="InstanceName"/>.store(conn);<xsl:text>
</xsl:text></xsl:if></xsl:for-each>        if ( isDirty ) { updateOnDB(conn); }
      }
    return returnKey;
  }


  /**
   *
   */
  private ResultSet doSelect(Connection conn, Statement stmt) { 
    ResultSet rset = null;

    try { 
      String sqlStmt = "select  \n" + 
      " <xsl:value-of select="object/tableName"/>.<xsl:value-of select="object/keyColumnName"/> as <xsl:value-of select="object/tableName"/>_<xsl:value-of select="object/keyColumnName"/><xsl:for-each select="object/column"><xsl:text>, \n" +
</xsl:text><xsl:text>      " </xsl:text><xsl:value-of select="/object/tableName"/>.<xsl:value-of select="column_name"/> as <xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/></xsl:for-each>
<xsl:for-each select="object/toOneJoinedTable">
<xsl:for-each select="column"><xsl:text>, \n" +
      " </xsl:text><xsl:value-of select="../tableName"/>.<xsl:value-of select="column_name"/> as <xsl:value-of select="../tableName"/>_<xsl:value-of select="column_name"/></xsl:for-each>
</xsl:for-each>  \n" + 
      " from <xsl:value-of select="object/tableName"/><xsl:text> </xsl:text><xsl:value-of select="object/tableName"/><xsl:for-each select="object/toOneJoinedTable"><xsl:text>, \n" + 
      " </xsl:text><xsl:value-of select="tableName"/><xsl:text> </xsl:text><xsl:value-of select="tableName"/> </xsl:for-each>    \n" +  
      " where <xsl:value-of select="object/tableName"/>.<xsl:value-of select="object/keyColumnName"/> = " + key <xsl:for-each select="object/toOneJoinedTable"><xsl:text>
      + " and </xsl:text><xsl:value-of select="joinTest"/>    \n"</xsl:for-each>;
      log("sqlStmt=" + sqlStmt);
      rset = stmt.executeQuery(sqlStmt);
      rset.next();
      applyResultSet(rset);
    }
    catch (Exception exp) {
      log("<xsl:value-of select="object/ClassName"/>.doSelect(), SQLException: " + exp.getMessage());
    }

   return rset;

  }


  /**
   *
   */
  private void applyResultSet(ResultSet rset) { 
    TimeZone timezone = TimeZone.getDefault();
    GregorianCalendar gc = null;
    java.sql.Clob textClob = null;
    InputStream in = null;
    int b = 0;
    StringBuffer stringBuffer = null;

    try { 
      key = rset.getLong("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="object/keyColumnName"/>");
<xsl:for-each select="object/column"><xsl:text>      </xsl:text>
<xsl:choose>
<xsl:when test="treatAs = 'String'"><xsl:value-of select="property"/> = rset.getString("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>"); </xsl:when>
<xsl:when test="treatAs = 'int'"><xsl:value-of select="property"/> = rset.getInt("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>"); </xsl:when>
<xsl:when test="treatAs = 'long'"><xsl:value-of select="property"/> = rset.getLong("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>"); </xsl:when>
<xsl:when test="treatAs = 'float'"><xsl:value-of select="property"/> = rset.getFloat("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>"); </xsl:when>
<xsl:when test="treatAs = 'double'"><xsl:value-of select="property"/> = rset.getDouble("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>"); </xsl:when>
<xsl:when test="treatAs = 'GregorianCalendar'">if ( rset.getTimestamp("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>") != null) { 
        gc  = new GregorianCalendar(timezone);
        gc.setTime(new java.util.Date( rset.getTimestamp("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>").getTime())); 
        <xsl:value-of select="property"/> = gc;
      }</xsl:when>
<xsl:when test="treatAs = 'OracleClob'">      textClob = rset.getClob("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>");
      in = textClob.getAsciiStream();
      b = 0;
      stringBuffer = new StringBuffer();
      if ( in != null) { 
        while ( (b = in.read()) != -1 ) { 
          stringBuffer.append( (char)b);
        }        
        <xsl:value-of select="property"/> = stringBuffer.toString();
      }</xsl:when>
<xsl:when test="treatAs = 'OracleLong'">in = rset.getBinaryStream("<xsl:value-of select="/object/tableName"/>_<xsl:value-of select="column_name"/>");
      if ( in != null) { 
        stringBuffer = new StringBuffer(5000);
        while ( (b = in.read()) != -1 ) { 
          stringBuffer.append( (char)b);
        }        
        <xsl:value-of select="property"/> = stringBuffer.toString();
      }</xsl:when></xsl:choose><xsl:text>
</xsl:text>
</xsl:for-each>
      isDirty = false;
    }
    catch (Exception exp) {
      log("<xsl:value-of select="object/className"/>.applyResultSet(): SQLException:" + exp.getMessage());
    }

  }


  /**
   *
   */
  private long insertToDB(Connection conn) throws Exception { 
    long newKey = 0;
    String sqlStmt = "";
    ByteArrayInputStream bs = null;
    InputStream in = null;
    Statement stmt = null;
    ResultSet rset = null;

    sqlStmt = "select <xsl:value-of select="object/sequenceName"/>.nextval from dual \n";
    stmt = conn.createStatement();
    rset = stmt.executeQuery(sqlStmt);
    rset.next();
    newKey = rset.getLong(1);
    log("newKey=" + newKey);

    sqlStmt = "insert into <xsl:value-of select="object/tableName"/>  " + 
    " ( " + 
    " <xsl:value-of select="object/keyColumnName"/>, \n" +                      
<xsl:for-each select="object/column"><xsl:text>    " </xsl:text><xsl:value-of select="column_name"/><xsl:if test="not(position() = last())"><xsl:text>, </xsl:text></xsl:if>    \n" +<xsl:text>
</xsl:text></xsl:for-each>    "   ) " + 
    " values ( ?, <xsl:for-each select="object/column"><xsl:if test="not(sysdateOnInsert)"><xsl:text> ?</xsl:text></xsl:if><xsl:if test="sysdateOnInsert"><xsl:text> sysdate</xsl:text></xsl:if><xsl:if test="not(position() = last())"><xsl:text>,</xsl:text></xsl:if></xsl:for-each> )";
    log("Sql stmt=" + sqlStmt);
    PreparedStatement pStmt = conn.prepareStatement(sqlStmt);
    pStmt.setLong(1,newKey);
<xsl:for-each select="object/column">
<xsl:call-template name="jdbcPreparedStatementWrite">
<xsl:with-param name="startIndex" select="1"/>
</xsl:call-template>
</xsl:for-each>
    int rowsInserted = pStmt.executeUpdate();
    log("      rows inserted =" + rowsInserted);
    if ( rowsInserted != 1) { 
      log("Error:  <className/>.insertToDB failed no rows inserted");
    }
    pStmt.close();

    isDirty = false;

    return newKey;

  }


  /**
   *
   */
  private void updateOnDB(Connection conn) throws Exception { 

    ByteArrayInputStream bs = null;
    InputStream in = null;
    String sqlStmt = "update <xsl:value-of select="object/tableName"/>  " + 
    " set " + 
<xsl:for-each select="object/column">
<xsl:if test="not(skipOnUpdate)"><xsl:text>    " </xsl:text><xsl:value-of select="column_name"/> = <xsl:if test="sysdateOnUpdate">sysdate </xsl:if><xsl:if test="not(sysdateOnUpdate)">?</xsl:if><xsl:if test="not(position() = last())"><xsl:text>, </xsl:text></xsl:if><xsl:text>    \n" +</xsl:text><xsl:if test="not(skipOnUpdate)"><xsl:text>
</xsl:text></xsl:if></xsl:if></xsl:for-each>    " where <xsl:value-of select="object/keyColumnName"/> = '" + key + "'";

    log("Sql stmt=" + sqlStmt);
    PreparedStatement pStmt = conn.prepareStatement(sqlStmt);
<xsl:for-each select="object/column">
<xsl:call-template name="jdbcPreparedStatementWrite">
<xsl:with-param name="startIndex" select="0"/>
</xsl:call-template>
</xsl:for-each>
    int rowsUpdated = pStmt.executeUpdate();
    if ( rowsUpdated != 1) { 
      log("Error:  <className/>.insertToDB failed no rows inserted");
    }
    pStmt.close();
    isDirty = false;

  }


  /**
   *
   * Delete an <xsl:value-of select="object/className"/> 
   * Also call delete() on any dependent objects.
   * If no Connection was passed in then we are responisible for beginning the transaction
   * Turn off auto commit, and rollback if we get exception from this or any dependent objects
   *
   */
  public void delete() throws Exception { 
    long returnKey = key;
    Connection conn = getConnection();
    try { 
      conn.setAutoCommit(false);  
      delete(conn);
      conn.commit();              
    }
    catch (Exception exp) {    //Any exception thrown by store causes a rollback. 
      log("<xsl:value-of select="object/className"/>.delete(), Exception: " + exp.getMessage());
      try {
        conn.rollback(); 
      } catch (SQLException rollbackExp) {             
        log("<xsl:value-of select="object/classNam-e"/>.delete(), Exception: " + rollbackExp.getMessage());
      } 
      throw exp;  //Throw exception back up so that user interface can report error
    }
    finally { 
      try {
        conn.close();
      } catch (SQLException closeExp) {             
        log("<xsl:value-of select="object/className"/>.delete(), Exception: " + closeExp.getMessage());
      } 
    }
  }


  /**
   *
   *
   */
  public void delete(Connection conn) throws Exception { <xsl:for-each select="object/toOneJoinedTable"><xsl:if test="not(readOnly)">
<xsl:text>    </xsl:text><xsl:value-of select="InstanceName"/>.delete(conn);</xsl:if>
</xsl:for-each>
<xsl:for-each select="object/toManyJoinedTable"><xsl:text>
    Iterator iteratorOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s = list</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s();
    while (iteratorOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s.hasNext() ) { 
      </xsl:text><xsl:value-of select="ClassName"/><xsl:text> object = (</xsl:text><xsl:value-of select="ClassName"/><xsl:text>)iteratorOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s.next();
      object.delete();
    } </xsl:text>
</xsl:for-each>
<xsl:for-each select="object/xrefToManyJoinedTable"><xsl:text>
    // Before deleting this </xsl:text><xsl:value-of select="/object/ClassName"/><xsl:text> remove all </xsl:text><xsl:value-of select="ClassName"/><xsl:text>s linked to it. 
    // By deleting the row on the xref table </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text>, that links them.
    Iterator iteratorOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s = list</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s();
    while (iteratorOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s.hasNext() ) { 
      </xsl:text><xsl:value-of select="ClassName"/><xsl:text> object = (</xsl:text><xsl:value-of select="ClassName"/><xsl:text>)iteratorOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s.next();
      remove</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(conn, object);
    } </xsl:text>
</xsl:for-each>
    String sqlStmt = "delete from <xsl:value-of select="object/tableName"/> " + 
    "where <xsl:value-of select="object/keyColumnName"/> = ?";
    PreparedStatement pStmt = conn.prepareStatement(sqlStmt);
    pStmt.setLong(1,key);
    int rowsDeleted = pStmt.executeUpdate(); 
    log("   Deleted row from <xsl:value-of select="object/tableName"/> where primary key was " + key);
    if ( rowsDeleted != 1) { 
      log("Error:  <xsl:value-of select="object/className"/>.delete failed no rows deleted");
     }
  }


  public long getKey() { return key; } 

<xsl:for-each select="object/column">  public <xsl:value-of select="javaDataType"/><xsl:text> </xsl:text>get<xsl:value-of select="concat(translate(substring(property,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(property,2),'')"/>() { 
    return <xsl:value-of select="property"/>;
  }<xsl:text>


</xsl:text>
</xsl:for-each>

<xsl:for-each select="object/column">  public void<xsl:text> </xsl:text>set<xsl:value-of select="concat(translate(substring(property,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(property,2),'')"/>(<xsl:value-of select="javaDataType"/> in) { 
    <xsl:value-of select="property"/> = in;
    isDirty = true;
  }<xsl:text>


</xsl:text>
</xsl:for-each>


<xsl:for-each select="object/toOneJoinedTable">
<xsl:if test="provideGetMethodForObject">
  //  Get Methods for joined objects in <xsl:value-of select="ClassName"/>
<xsl:text>
</xsl:text>
  public <xsl:value-of select="ClassName"/><xsl:text> </xsl:text>get<xsl:value-of select="concat(translate(substring(InstanceName,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(InstanceName,2),'')"/>() { 
    return <xsl:value-of select="InstanceName"/>;
  }<xsl:text>
</xsl:text>
</xsl:if>
</xsl:for-each>

<xsl:for-each select="object/toOneJoinedTable">
  //  Getter Methods for properties in <xsl:value-of select="ClassName"/>
<xsl:text>
</xsl:text>
<xsl:for-each select="column">
<xsl:if test="includeGetSetMethodsFor">
  public <xsl:value-of select="javaDataType"/><xsl:text> </xsl:text>get<xsl:value-of select="concat(translate(substring(property,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(property,2),'')"/>() { 
    return <xsl:value-of select="../InstanceName"/>.get<xsl:value-of select="concat(translate(substring(property,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(property,2),'')"/>();
  }<xsl:text>
</xsl:text>
</xsl:if>
</xsl:for-each>
</xsl:for-each>


<xsl:for-each select="object/toOneJoinedTable">
<xsl:if test="not(readOnly)">
  //  Setter Methods for properties in <xsl:value-of select="ClassName"/>
<xsl:text>
</xsl:text>
<xsl:for-each select="column">
<xsl:if test="includeGetSetMethodsFor">
  public void<xsl:text> </xsl:text>set<xsl:value-of select="concat(translate(substring(property,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(property,2),'')"/>(<xsl:value-of select="javaDataType"/> in) { 
    <xsl:value-of select="../InstanceName"/>.set<xsl:value-of select="concat(translate(substring(property,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(property,2),'')"/>(in);
  }<xsl:text>
</xsl:text>
</xsl:if>
</xsl:for-each>
</xsl:if>
</xsl:for-each>


<xsl:for-each select="object/toManyJoinedTable"><xsl:text>


  /**
   *   Get all </xsl:text><xsl:value-of select="ClassName"/><xsl:text>s for this </xsl:text><xsl:value-of select="/object/className"/><xsl:text>
   */
  private void load</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s() { 
    Connection conn = null;
    Statement stmt = null;
    ResultSet rset = null;
    arrayListOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s = new  ArrayList();
    String sqlStmt = "select  \n" + </xsl:text><xsl:for-each select="column"><xsl:text>
      " </xsl:text><xsl:value-of select="../tableName"/><xsl:text>.</xsl:text><xsl:value-of select="column_name"/><xsl:text> as </xsl:text><xsl:value-of select="../tableName"/>_<xsl:value-of select="column_name"/><xsl:if test="not(position() = last())"><xsl:text>, </xsl:text></xsl:if><xsl:text>  \n" +  </xsl:text></xsl:for-each><xsl:text>
      " from </xsl:text><xsl:value-of select="/object/tableName"/><xsl:text> </xsl:text><xsl:value-of select="/object/tableName"/><xsl:text>, " + 
      " </xsl:text><xsl:value-of select="tableName"/><xsl:text> </xsl:text><xsl:value-of select="tableName"/><xsl:text> \n" + 
      " where </xsl:text><xsl:value-of select="/object/tableName"/><xsl:text>.</xsl:text><xsl:value-of select="joinColumnName"/><xsl:text> = </xsl:text><xsl:value-of select="tableName"/><xsl:text>.</xsl:text><xsl:value-of select="joinColumnName"/><xsl:text> \n" + 
      " and </xsl:text><xsl:value-of select="tableName"/><xsl:text>.</xsl:text><xsl:value-of select="joinColumnName"/><xsl:text> = " + key;
    try {
      conn = getConnection();
      stmt = conn.createStatement();
      log("sqlStmt=" + sqlStmt);
      rset = stmt.executeQuery(sqlStmt);
      while ( rset.next() ) { 
        </xsl:text><xsl:value-of select="ClassName"/><xsl:text> object = new </xsl:text><xsl:value-of select="ClassName"/><xsl:text>(rset);
        arrayListOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s.add(object);
      }
    }
    catch (Exception exp) {
      log("get</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s(), SQLException: " + exp.getMessage());
    }
    finally { 
      try {
        rset.close();
        stmt.close();
        conn.close();
      } catch (SQLException exp) {             
        log("get</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s()- closing rset,stmt,conn:  Exception: " + exp.getMessage());
      } 
    }

  }
</xsl:text></xsl:for-each>


<xsl:for-each select="object/toManyJoinedTable"><xsl:text>


  /**
   *   Get Iterator of </xsl:text><xsl:value-of select="ClassName"/><xsl:text>s 
   */
  public Iterator list</xsl:text><xsl:value-of select="ClassName"/>s() { <xsl:text>
    return arrayListOf</xsl:text><xsl:value-of select="ClassName"/>s<xsl:text>.iterator();
  }</xsl:text>
</xsl:for-each>


<xsl:for-each select="object/toManyJoinedTable"><xsl:text>


  /**
   *   Add a </xsl:text><xsl:value-of select="ClassName"/><xsl:text>
   *   To add a </xsl:text><xsl:value-of select="ClassName"/><xsl:text> instantiate one,
   *   call it's set() methods, but dont store().  Call this method passing in the 
   *   </xsl:text><xsl:value-of select="ClassName"/>.<xsl:text> This method will link it with this 
   *   object/table and store() it.
   */
  public long add</xsl:text><xsl:value-of select="ClassName"/>(<xsl:value-of select="ClassName"/><xsl:text> in)  throws Exception { 
    long newKey = 0;
    in.set</xsl:text><xsl:value-of select="concat(translate(substring(joinPropertyName,1,1),'abcdefghijklmnopqrstuvwxyz','ABCDEFGHIJKLMNOPQRSTUVWXYZ'),substring(joinPropertyName,2),'')"/><xsl:text>(key);
    newKey = in.store(); 
    load</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s();   
    return newKey;
  }
</xsl:text>
</xsl:for-each>


<xsl:for-each select="object/toManyJoinedTable"><xsl:text>
  /**
   *   Remove a </xsl:text><xsl:value-of select="ClassName"/><xsl:text>
   *   To delete a </xsl:text><xsl:value-of select="ClassName"/><xsl:text> call this method.
   *   This will delete this row compeletly no just de-link it from this row.
   */
  public void remove</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(</xsl:text><xsl:value-of select="ClassName"/><xsl:text> in) throws Exception { 
    in.delete();
    load</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s();
   }
</xsl:text>
</xsl:for-each>


<xsl:for-each select="object/xrefToManyJoinedTable"><xsl:text>
  /**
   *  Get all </xsl:text><xsl:value-of select="ClassName"/><xsl:text>s for this </xsl:text><xsl:value-of select="/object/className"/><xsl:text>
   *  Join is done through an xref table: </xsl:text><xsl:value-of select="tableName"/><xsl:text>
   */
  private void load</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s() { 
    Connection conn = null;
    Statement stmt = null;
    ResultSet rset = null;
    arrayListOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s = new  ArrayList();

    String sqlStmt = "select </xsl:text><xsl:value-of select="otherTablesPrimaryKeyColumnName"/><xsl:text> \n" +
      " from </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text>  \n" + 
      " where </xsl:text><xsl:value-of select="ourPrimaryKeyColumnName"/><xsl:text> = " + key;
    try {
      conn = getConnection();
      stmt = conn.createStatement();
      log("sqlStmt=" + sqlStmt);
      rset = stmt.executeQuery(sqlStmt);
      while ( rset.next() ) { 
        </xsl:text><xsl:value-of select="ClassName"/><xsl:text> object = new </xsl:text><xsl:value-of select="ClassName"/><xsl:text>(rset.getLong(1));
        arrayListOf</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s.add(object);
      }
    }
    catch (Exception exp) {
      log("get</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s(), SQLException: " + exp.getMessage());
    }
    finally { 
      try {
        rset.close();
        stmt.close();
        conn.close();
      } catch (SQLException exp) {             
        log("get</xsl:text><xsl:value-of select="ClassName"/><xsl:text>s()- closing rset,stmt,conn:  Exception: " + exp.getMessage());
      } 
    }

  }
</xsl:text></xsl:for-each>

<xsl:for-each select="object/xrefToManyJoinedTable"><xsl:text>


  /**
   *   Get Iterator of </xsl:text><xsl:value-of select="ClassName"/><xsl:text>s 
   */
  public Iterator list</xsl:text><xsl:value-of select="ClassName"/>s() { <xsl:text>
    return arrayListOf</xsl:text><xsl:value-of select="ClassName"/>s<xsl:text>.iterator();
  }</xsl:text>
</xsl:for-each>


<xsl:for-each select="object/xrefToManyJoinedTable"><xsl:text>


  /**
   *   Add </xsl:text><xsl:value-of select="ClassName"/><xsl:text> to this </xsl:text><xsl:value-of select="/object/className"/><xsl:text>
   *   by inserting a row to the xref table </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text> linking them.
   */
  public void add</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(Connection conn, </xsl:text><xsl:value-of select="ClassName"/><xsl:text> in)  throws Exception { 
    String sqlStmt = null;
    sqlStmt = "insert into </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text>  " + 
    " (  </xsl:text><xsl:value-of select="ourPrimaryKeyColumnName"/><xsl:text>, </xsl:text><xsl:value-of select="otherTablesPrimaryKeyColumnName"/><xsl:text> ) " + 
    " values ( ?, ? )";
    log("Sql stmt=" + sqlStmt);
    PreparedStatement pStmt = conn.prepareStatement(sqlStmt);
    pStmt.setLong(1, key);
    pStmt.setLong(2, in.getKey());
    int rowsInserted = pStmt.executeUpdate();
    log("      rows inserted =" + rowsInserted);
    if ( rowsInserted != 1) { 
      log("Error:  insert to xref table </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text> failed no rows inserted");
    }
    pStmt.close();
  }


  /**
   * same as above but used when Connection object not supplied
   */
  public void add</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(</xsl:text><xsl:value-of select="ClassName"/><xsl:text> in)  throws Exception { 
    Connection conn = getConnection();
    add</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(conn, in);
  }


</xsl:text>
</xsl:for-each>


<xsl:for-each select="object/xrefToManyJoinedTable"><xsl:text>


  /**
   *   Remove a </xsl:text><xsl:value-of select="ClassName"/><xsl:text> from this </xsl:text><xsl:value-of select="/object/className"/><xsl:text>
   *   by deleting the row on the xref table </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text>, that links 
   *   them.
   */
  public void remove</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(Connection conn, </xsl:text><xsl:value-of select="ClassName"/><xsl:text> in)  throws Exception { 
    String sqlStmt = null;
    sqlStmt = "delete from </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text>  " + 
    " where </xsl:text><xsl:value-of select="ourPrimaryKeyColumnName"/><xsl:text> = ? and </xsl:text><xsl:value-of select="otherTablesPrimaryKeyColumnName"/><xsl:text>= ? ";
    log("Sql stmt=" + sqlStmt);
    PreparedStatement pStmt = conn.prepareStatement(sqlStmt);
    pStmt.setLong(1, key);
    pStmt.setLong(2, in.getKey());
    int rowsDeleted = pStmt.executeUpdate();
    log("      rows deleted =" + rowsDeleted);
    if ( rowsDeleted != 1) { 
      log("Error:  delete from xref table </xsl:text><xsl:value-of select="xrefTableName"/><xsl:text> failed no rows deleted");
    }
    pStmt.close();
  }

  /**
   * same as above but used when Connection object not supplied
   */
  public void remove</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(</xsl:text><xsl:value-of select="ClassName"/><xsl:text> in)  throws Exception { 
    Connection conn = getConnection();
    remove</xsl:text><xsl:value-of select="ClassName"/><xsl:text>(conn, in);
  }


</xsl:text>
</xsl:for-each>
  /**
   *  Write to Log
   */
  private void log(String messageIn) { 
    System.out.println(messageIn);
  }


  /**
   *  Get JDBC Connection to the DataBase 
   *  Note: this should be returning connections from a pool.
   */
  private Connection getConnection() { 

    Connection conn = null;

    String dbServer   =  "@myserver.mycompnay.com";
    String dbPort     =  "1526";
    String dbSid      =  "mysid";
    String dbUserId   =  "username";
    String dbPassword =  "password";
    try {
      DriverManager.registerDriver(new oracle.jdbc.driver.OracleDriver());
      String connectString = "jdbc:oracle:thin:" + dbServer + ":" + dbPort + ":" + dbSid;
      conn = DriverManager.getConnection (connectString,  dbUserId, dbPassword);
    }
    catch (SQLException exp) {
      log("Exception: " + exp.getMessage() );
    }
    return conn;
  }


  /**
   *  A main method for testing
   */
  public static void main(String args[] ) { 
    <xsl:value-of select="object/className"/> object = new <xsl:value-of select="object/className"/>(1);
<xsl:for-each select="object/column"> 
<xsl:text>    System.out.println("</xsl:text><xsl:value-of select="property"/> = " + object.<xsl:value-of select="property"/> );
</xsl:for-each>
  }


}


</xsl:template>

<xsl:include href="jdbcPreparedStatementWrite.xsl"/>

</xsl:stylesheet>



