<?php

// This is a [rather messy] template that builds a Peer class.
//
// These templates use the classes in propel.engine.database.model which represent the model (database).
// These templates also use the propel.engine.builder classes (increasingly) to encapsulate some of the
// repeating logic.
//
// These are based on velocity templates in original Torque.
//
// TODO:
//      - move these into classes, perhaps, to further componentize the building of templates.
//      - if these were classes it would also be easy to customize them through extension
//
// $Id: Peer.tpl,v 1.24 2005/03/29 16:35:52 micha Exp $

include_once 'propel/engine/builder/om/PeerBuilder.php';
include_once 'propel/engine/builder/om/ClassTools.php';
include_once 'creole/CreoleTypes.php';

$db = $table->getDatabase();
if($table->getPackage()) {
  $package = $table->getPackage();
} else {
  $package = $targetPackage;
}

echo '<' . '?' . 'php';

$CLASS = $table->getPhpName() . 'Peer';
$basePeerClass = ClassTools::getBasePeer($table);
$basePeerClassname = ClassTools::classname($basePeerClass);
?>

require_once '<?php echo ClassTools::getFilePath($basePeerClass) ?>';

// The object class -- needed for instanceof checks in this class.
// actual class may be a subclass -- as returned by <?php echo $table->getPhpName() ?>Peer::getOMClass()
include_once '<?php echo ClassTools::getFilePath($package, $table->getPhpName()) ?>';
<?php 
foreach ($table->getForeignKeys() as $fk) {
    
   $tblFK = $table->getDatabase()->getTable($fk->getForeignTableName());
   $tblFKPackage = ($tblFK->getPackage() ? $tblFK->getPackage() : $package); 
   
   if (!$tblFK->isForReferenceOnly()) {
?>   
include_once '<?php echo ClassTools::getFilePath($tblFKPackage, $tblFK->getPhpName()) ?>';
include_once '<?php echo ClassTools::getFilePath($tblFKPackage, $tblFK->getPhpName() . 'Peer') ?>';
<?php 
    } // if (!$tblFK->isForReferenceOnly()
} // foreach
?>

/**
 * Base static class for performing query and update operations on the '<?php echo $table->getName() ?>' table.
 *
 * <?php echo $table->getDescription() ?>
 *
<?php if ($addTimeStamp) { ?>
 * This class was autogenerated by Propel on:
 *
 * [<?php echo $now ?>]
 *
<?php } ?>
 * @package <?php echo $package ?>
 */
class <?php echo $basePrefix . $table->getPhpName() ?>Peer 
{
<?php if (!$table->isAlias()) { ?>

  /** the default database name for this class */
  function DATABASE_NAME() { return "<?php echo $table->getDatabase()->getName() ?>"; }

  /** the table name for this class */
  function TABLE_NAME() { return "<?php echo $table->getName() ?>"; }

<?php foreach ($table->getColumns() as $col) { ?>
  /** the column name for the <?php echo strtoupper($col->getName()) ?> field */
  function <?php echo PeerBuilder::getColumnName($col) ?>() { return "<?php echo $table->getName() . '.' . strtoupper($col->getName()) ?>"; }
<?php } ?>
<?php } /* if (!$table->isAlias()) */ ?>

  /** number of columns for this peer (static) */
  function numColumns() { return <?php echo $table->getNumColumns() ?>; }

  /** number of lazy load columns for this peer */
  function numLazyLoadColumns() { return <?php echo $table->getNumLazyLoadColumns() ?>; }
  
  /** A class that can be returned by this peer. */
  function CLASS_DEFAULT() { return "<?php echo $package . '.' . $table->getPhpName() ?>"; }

  /** The PHP to DB Name Mapping (static) */
  var $phpNameMap = null;

  /**
  * @access private static
  */
  function & getInstance()
  {
    static $instance;

    if ($instance === null) {
      $instance = new <?php echo $table->getPhpName()?>Peer();
    }

    return $instance;
  }

  /**
   * @return MapBuilder the map builder for this peer
   * @access public static
   * @throws PropelException Any exceptions caught during processing will be
   *         rethrown wrapped into a PropelException.
   */
  function & getMapBuilder()
  {
    include_once '<?php echo ClassTools::getFilePath($pkmap, $table->getPhpName() . 'MapBuilder') ?>';
    return <?php echo $basePeerClassname ?>::getMapBuilder(<?php echo $table->getPhpName() ?>MapBuilder::CLASS_NAME());
  }

  /**
   * Gets a map (hash) of PHP names to DB column names.
   *
   * @return array The PHP to DB name map for this peer
   * @access public static
   * @throws PropelException Any exceptions caught during processing will be
   *         rethrown wrapped into a PropelException.
   * @todo Consider having template build the array rather than doing it at runtime.
   */
  function getPhpNameMap()
  {
    $self =& <?php echo $table->getPhpName()?>Peer::getInstance();

    if ($self->phpNameMap === null) {
      $map = $self->getTableMap();
      $columns = $map->getColumns();
      $nameMap = array();
      foreach ($columns as $column) {
        $nameMap[$column->getPhpName()] = $column->getColumnName();
      }
      $self->phpNameMap = $nameMap;
    }
    return $self->phpNameMap;
  }
<?php

if (!$table->isAlias()) {


  if ($table->getChildrenColumn()) {

    $col = $table->getChildrenColumn();
    $tfc = $table->getPhpName();
    $cfc = $col->getPhpName();

    if ($col->isEnumeratedClasses()) {

      if ($col->isPrimitiveNumeric()) $quote = "";
      else $quote = '"';

      foreach ($col->getChildren() as $child) {
	    $childpkg = ($child->getPackage() ? $child->getPackage() : $package);
?>
  /** A key representing a particular subclass */
  function CLASSKEY_<?php echo strtoupper($child->getKey()) ?>() { return <?php echo $quote . $child->getKey() . $quote ?>; }

  /** A class that can be returned by this peer. */
  function CLASSNAME_<?php echo strtoupper($child->getKey()) ?>() { return "<?php echo $childpkg . '.' . $child->getClassName() ?>"; }
<?php
      } /* foreach children */
    } /* if col->isenumerated...() */
  } /* if table->getchildrencolumn() */
?>
  /**
   * Convenience method which changes table.column to alias.column.
   *
   * Using this method you can maintain SQL abstraction while using column aliases.
   * <code>
   *    $c->addAlias("alias1", TablePeer::TABLE_NAME);
   *    $c->addJoin(TablePeer::alias("alias1", TablePeer::PRIMARY_KEY_COLUMN), TablePeer::PRIMARY_KEY_COLUMN);
   * </code>
   * @param string $alias The alias for the current table.
   * @param string $column The column name for current table. (i.e. <?php echo $table->getPhpName() ?>Peer::COLUMN_NAME).
   * @return string
   * @access public static
   */
  function alias($alias, $column)
  {
    return $alias . substr($column, strlen(<?php echo $table->getPhpName()?>Peer::TABLE_NAME()));
  }

  /**
  * Add all the columns needed to create a new object.
  *
  * Note: any columns that were marked with lazyLoad="true" in the
  * XML schema will not be added to the select list and only loaded
  * on demand.
  *
  * @param criteria object containing the columns to add.
  * @throws PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  * @access public static
  */
  function addSelectColumns(/*Criteria*/ &$criteria)
  {
    Propel::typeHint($criteria, 'Criteria', '<?php echo $CLASS; ?>', 'addSelectColumns', 1);

<?php
    foreach ($table->getColumns() as $col) { 
      if (! $col->isLazyLoad()) {
?>
    $criteria->addSelectColumn(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>());
<?php 
      } 
    }
?>
  }

<?php
  $countColumn = "*";
  if ($table->hasPrimaryKey()) {
    $pk = $table->getPrimaryKey();
    $countColumn = $table->getName() . "." . strtoupper($pk[0]->getName());
  }
?>

  function COUNT() { return "COUNT(<?php echo $countColumn?>)"; }
  function COUNT_DISTINCT() { return "COUNT(DISTINCT <?php echo $countColumn?>)"; }

  /**
  * Returns the number of rows matching criteria.
  *
  * @param Criteria $criteria a <code>Criteria</code> object.
  * @param boolean $distinct Whether to select only distinct columns.
  * @param Connection $con An optional Connection object.
  *
  * @return int Number of matching rows.
  */
  function doCount(/*Criteria*/ $criteria, $distinct = false, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doCount', 3);
    Propel::typeHint($criteria, 'Criteria', '<?php echo $CLASS; ?>', 'doCount', 1);

    /*
    * clear out anything that might confuse the ORDER BY clause. 
    * Note: unlike php5 version $criteria is passed by value and has not to be cloned.
    */
    $criteria->clearSelectColumns();
    $criteria->clearOrderByColumns();
    
    if ($distinct || in_array(Criteria::DISTINCT(), $criteria->getSelectModifiers())) {
      $criteria->addSelectColumn(<?php echo $table->getPhpName()?>Peer::COUNT_DISTINCT());
    } else {
      $criteria->addSelectColumn(<?php echo $table->getPhpName()?>Peer::COUNT());
    }
    // just in case we're grouping: add those columns to the select statement
    foreach($criteria->getGroupByColumns() as $column)
    {
      $criteria->addSelectColumn($column);
    }

    $rs =& <?php echo $table->getPhpName()?>Peer::doSelectRS($criteria, $con);
    if (Propel::isError($rs)) { return $rs; }

    if ($rs->next() === true) {
      return $rs->getInt(1);
    }

    /* no rows returned; we infer that means 0 matches */
    return 0;
  }

  /**
  * Method to select one object from the DB.
  * 
  * @param Criteria $criteria Object used to create the SELECT statement.
  * @param Connection $con An optional Connection object.
  *
  * @return mixed <?php echo $table->getPhpName() ?> on success, NULL on failure.
  */
  function & doSelectOne($criteria, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doSelectOne', 2);

    $criteria->setLimit(1);

    $objects =& <?php echo $table->getPhpName()?>Peer::doSelect($criteria, $con);
    if (Propel::isError($objects)) { return $objects; }

    if ($objects) {
      return $objects[0];
    }

    return null;
  }

  /**
  * Method to do selects.
  *
  * @param Criteria $criteria Object used to create the SELECT statement.
  * @param Connection $con An optional Connection object.
  *
  * @return array Array of selected Objects
  * @throws PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  */
  function & doSelect($criteria, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doSelect', 2);

    $rs =& <?php echo $table->getPhpName()?>Peer::doSelectRS($criteria, $con);
    if (Propel::isError($rs)) { return $rs; }

    return <?php echo $table->getPhpName()?>Peer::populateObjects($rs);
  }

  /**
  * Prepares the Criteria object and uses the parent doSelect()
  * method to get a ResultSet.
  *
  * Use this method directly if you want to just get the resultset
  * (instead of an array of objects).
  *
  * @param Criteria $criteria
  * @param Connection $con An optional Connection object.
  *
  * @return ResultSet The resultset object with numerically-indexed fields.
  *         PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  * @see <?php echo $basePeerClassname ?>::doSelect()
  */
  function & doSelectRS($criteria, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doSelectRS', 2);

    /* [MA] do not retrieve connection here, BasePeer::doSelect will do */
    
    if (!$criteria->getSelectColumns()) {
      <?php echo $table->getPhpName()?>Peer::addSelectColumns($criteria);
    }

    // Set the correct dbName
    $criteria->setDbName(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());    

    // BasePeer returns a Creole ResultSet, set to return
    // rows indexed numerically.
    return <?php echo $basePeerClassname ?>::doSelect($criteria, $con);
  }

  /**
  * The returned array will contain objects of the default type or
  * objects that inherit from the default.
  *
  * @return Array of <?php echo $table->getPhpName()?> objects on success OR
  *         PropelException Any exceptions caught during processing will be
  *         returned wrapped into a PropelException.
  */
  function & populateObjects(/*ResultSet*/ &$rs)
  {
    $results = array();

    if (! is_a($rs, 'ResultSet')) {
      return new PropelException(PROPEL_ERROR, "parameter not of type 'ResultSet'");
    }

<?php if (!$table->getChildrenColumn()) { ?>
    // set the class once to avoid overhead in the loop
    $cls = <?php echo $table->getPhpName() ?>Peer::getOMClass();

    if (Propel::isError($cls =& Propel::import($cls))) {
      return $cls;
    }
<?php } ?>

    // populate the object(s)
    while($rs->next())
    {
<?php if ($table->getChildrenColumn()) { ?>
      // class must be set each time from the record row
      $cls =& Propel::import(<?php echo $table->getPhpName() ?>Peer::getOMClass($rs, 1));
      if (Propel::isError($cls)) {
        return $cls;
      }
      $obj =& new $cls();

      if (Propel::isError($e =& $obj->hydrate($rs))) {
        return $e;
      }

      $results[] =& $obj;
<?php } else { ?>
      $obj =& new $cls();

      if (Propel::isError($e =& $obj->hydrate($rs))) {
        return $e;
      }

      $results[] =& $obj;
<?php } ?>
    }

    return $results;
  }

<?php  } /* if !table->isAlias() */ ?>

<?php if ($table->getChildrenColumn()) {

  $col = $table->getChildrenColumn();
?>

  /**
  * The returned Class will contain objects of the default type or
  * objects that inherit from the default.
  *
  * @param ResultSet $rs ResultSet with pointer to record containing om class.
  * @param int $colnum Column to examine for OM class information (first is 1).
  *
  * @throws PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  */
  function getOMClass(/*ResultSet*/ &$rs, $colnum)
  {
    $c = null;

<?php if ($col->isEnumeratedClasses()) { ?>

    $omClass = null;
    $classKey = $rs->getString($colnum - 1 + <?php echo $col->getPosition() ?>);

    switch($classKey)
    {
<?php
      foreach ($col->getChildren() as $child) {
?>
      case <?php echo $table->getPhpName()?>Peer::CLASSKEY_<?php echo strtoupper($child->getKey()) ?>():
        $omClass = <?php echo $table->getPhpName()?>Peer::CLASSNAME_<?php echo strtoupper($child->getKey()) ?>();
        break;
<?php } /* foreach */ ?>
      default:
<?php if ($table->isAbstract()) { ?>
        $error = "You must implement the getOMClass method in your"
            ." Peer object in order for things to work properly."
            ." This method should return the proper Class that"
            ." represents the Peer's Business Object.";

        return new PropelException(PROPEL_ERROR, $error);
<?php } else { ?>

    $omClass = <?php echo $table->getPhpName()?>Peer::CLASS_DEFAULT();

<?php } ?>

    } // switch

    $c = $omClass;

<?php } else { /* if not enumerated */ ?>

    $c =& Propel::import($rs->getString($colnum - 1 + <?php echo $col->getPosition() ?>));

    if (Propel::isError($c)) {
      return $c;
    }
  <?php } ?>

    return $c;
  }

<?php } else { /* if table->getchildrencolumn */ ?>

  /**
   * The class that the Peer will make instances of.
   * If the BO is abstract then you must implement this method
   * in the BO.
   *
   * @throws PropelException Any exceptions caught during processing will be
   *         rethrown wrapped into a PropelException.
   */
  function getOMClass()
  {
<?php if ($table->isAbstract()) { ?>
    $error = "You must implement the getOMClass method in your"
        ." Peer object in order for things to work properly."
        ." This method should return the proper Class that"
        ." represents the Peer's Business Object.";

    return new PropelException(PROPEL_ERROR, $error);
<?php } else { ?>
    return <?php echo $table->getPhpName()?>Peer::CLASS_DEFAULT();
<?php } ?>
  }
<?php }  /* if table->getchildrencolumn */

if (!$table->isAlias() && ! $table->isReadOnly()) 
{ 
?>
  /**
  * Method to do inserts.  This method is to be used during a transaction,
  * otherwise use the doInsert(Criteria) method.  It will take care of
  * the connection details internally.
  *
  * @param mixed $values Criteria or <?php echo $table->getPhpName() ?> object containing data
  *                      that is used to create the INSERT statement.
  * @param Connection $con The connection to use
  *
  * @return mixed The new primary key.
  * @throws PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  */
  function doInsert(&$values, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doInsert', 2);

    $con =& Param::get($con);

    if ($con === null) {
      $con =& Propel::getConnection(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
      if (Propel::isError($con)) { return $con; }
    }

    if (is_a($values, 'Criteria')) {
        $criteria =& $values;
    } else {
        $criteria =& $values->buildCriteria();
    }

<?php 
  foreach ($table->getColumns() as $col) 
  {
    $cfc = $col->getPhpName();
    if ($col->isPrimaryKey() && $col->isAutoIncrement() && $table->getIdMethod() != "none") 
    { 
?>
    $criteria->remove(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>()); // remove pkey col since this table uses auto-increment
<?php
    }
  }
?> 
    // Set the correct dbName
    $criteria->setDbName(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());

    // use transaction because $criteria could contain info
    // for more than one table (I guess, conceivably)
    $e = $con->begin();
    if (Creole::isError($e)) { $con->rollback(); return new PropelException(PROPEL_ERROR_DB, $e); }

    $pk = <?php echo $basePeerClassname ?>::doInsert($criteria, $con);
    if (Propel::isError($pk)) { $con->rollback(); return $pk; }

    $e = $con->commit();
    if (Creole::isError($e)) { $con->rollback(); return new PropelException(PROPEL_ERROR_DB, $e); }

    return $pk;
  }

<?php
  // Both UPDATE and DELETE can use cascade emulation if the DB driver
  // doesn't natively support ON UPDATE CASCADE / ON DELETE CASCADE
  //
  // Support for ON UPDATE CASCADE emulation has been removed because
  // it doesn't make any sense for Propel.  ON UPDATE CASCADE works by
  // updating referring rows when the pkey is updated; pkeys can never be
  // updated unless using the BasePeer class directly.  This behavior may
  // change, but for now updateCascade has been removed.

  // Check to see whether this table has any foreign keys that should be
  // cascaded and set the $deleteCascadeRelevant

  $deleteCascadeRelevant = false;
  $deleteSetNullRelevant = false;

  if (! $platform->supportsNativeDeleteTrigger() && count($table->getReferrers()) > 0) {
    foreach ($table->getReferrers() as $fk) {
      if ( $fk->getOnDelete() == ForeignKey::CASCADE ) {
        $deleteCascadeRelevant = true;
      } 
      elseif ($fk->getOnDelete() == ForeignKey::SETNULL) {
        $deleteSetNullRelevant = true;
      }
    }
  } // if count(foreign keys)
?>
  /**
  * Method perform an UPDATE on the database, given a <?php echo $table->getPhpName() ?> or Criteria object.
  *
  * @param mixed $values Criteria or <?php echo $table->getPhpName() ?> object containing data that is used to create the UPDATE statement.
  * @param Connection $con The connection to use.
  *
  * @return mixed number of affected rows on success, any exceptions returned during processing
  *         wrapped in a PropelException on failure.
  */
  function doUpdate(&$values, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doUpdate', 2);

    $con =& Param::get($con);

    if ($con === null) {
      $con =& Propel::getConnection(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
      if (Propel::isError($con)) { return $con; }
    }

    $selectCriteria =& new Criteria(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());

    if (is_a($values, 'Criteria')) {
      $criteria =& $values;
<?php 
  foreach ($table->getColumns() as $col) 
  {
    if($col->isPrimaryKey()) 
    { 
      $pn = $table->getPhpName() . 'Peer';
      $cn = PeerBuilder::getColumnName($col);
?>
      $comparison = $criteria->getComparison(<?php echo $pn?>::<?php echo $cn?>());
      $selectCriteria->add(<?php echo $pn?>::<?php echo $cn ?>(), $criteria->remove(<?php echo $pn ?>::<?php echo $cn ?>()), $comparison);
<?php 
    }  /* if col is prim key */
  } /* foreach */
?>
    } else { // $values is <?php echo $table->getPhpName() ?> object
        $criteria = $values->buildCriteria(); // gets full criteria
        $selectCriteria = $values->buildPkeyCriteria(); // gets criteria w/ primary key(s)            
    }	

    // Set the correct dbName
    $criteria->setDbName(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());    

    return <?php echo $basePeerClassname ?>::doUpdate($selectCriteria, $criteria, $con);
  }

  /**
  * Method to DELETE all rows from the <?php echo $table->getName() ?> table.
  *
  * <b>Note</b>: If you want to pass a Connection object as reference,
  * use Param::set() :
  *
  * <code>
  *  $con =& Propel::getConnection();
  *  $e = BasePeer::doDeleteAll(Param::set($con));
  * </code>
  *
  * @return mixed number of affected rows on success, PropelException on failure.
  */
  function doDeleteAll($con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doDeleteAll', 2);

    $con =& Param::get($con);

    if ($con === null) {
      $con =& Propel::getConnection(<?php echo $table->getPhpName() ?>Peer::DATABASE_NAME());
      if (Propel::isError($con)) { return $con; }
    }

    $affectedRows = 0; // initialize var to track total num of affected rows    
    
    // use transaction because $criteria could contain info
    // for more than one table or we could emulating ON DELETE CASCADE, etc.
    $e = $con->begin();
    if (Creole::isError($e)) { $con->rollback(); return new PropelException(PROPEL_ERROR_DB, $e); }
<?php if ($deleteCascadeRelevant) { ?>

    $e = <?php echo $table->getPhpName() ?>Peer::doOnDeleteCascade(new Criteria(), $con);
    if (Propel::isError($e)) { $con->rollback(); return $e; }
    $affectedRows += $e;
<?php } elseif ($deleteSetNullRelevant) { ?>

    $e = <?php echo $table->getPhpName() ?>Peer::doOnDeleteSetNull(new Criteria(), $con);
    if (Propel::isError($e)) { $con->rollback(); return $e; }
    $affectedRows += $e;
<?php } ?>

    $e = BasePeer::doDeleteAll(<?php echo $table->getPhpName() ?>Peer::TABLE_NAME(), $con);
    if (Propel::isError($e)) { $con->rollback(); return $e; }
    $affectedRows += $e;

    $e = $con->commit();
    if (Creole::isError($e)) { $con->rollback(); return new PropelException(PROPEL_ERROR_DB, $e); }

    return $affectedRows;
  }

  /**
  * Method perform a DELETE on the database, given a <?php echo $table->getPhpName() ?> or Criteria object OR a primary key value.
  *
  * @param mixed $values Criteria or <?php echo $table->getPhpName() ?> object containing data that is used to create the DELETE statement.
  * @param Connection $con the connection to use
  *
  * @return mixed number of affected rows on success, any exception returned during processing wrapped into a PropelException on failure.
  */
  function doDelete(&$values, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doDelete', 2);

    $con =& Param::get($con);

    if ($con === null) {
      $con =& Propel::getConnection(<?php echo $table->getPhpName() ?>Peer::DATABASE_NAME());
      if (Propel::isError($con)) { return $con; }
    }

    if (is_a($values, 'Criteria')) {
      $criteria =& $values;
    } 
    elseif (is_a($values, '<?php echo $table->getPhpName() ?>')) {
<?php
  $pkey_count = 0;
  foreach ($table->getColumns() as $col) {
    if($col->isPrimaryKey()) {
      $pkey_count++;
    }
  }

  if ($pkey_count > 0) { 
?>
      $criteria =& $values->buildPkeyCriteria();
<?php  } else { ?>
      $criteria =& $values->buildCriteria();
<?php  } ?>
    } 
    else {
      // it must be the primary key
      $criteria =& new Criteria(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
<?php
  if (count($table->getPrimaryKey()) == 1) { 
    $col = array_shift($table->getPrimaryKey()); 
?>
      $criteria->add(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>(), $values);
<?php  
  } else { 
?>
      // primary key is composite; we therefore, expect
      // the primary key passed to be an array of pkey
      // values
<?php
    $i=0;
    foreach($table->getPrimaryKey() as $col) { 
?>
      $criteria->add(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col)?>(), $values[<?php echo $i ?>]);
<?php 
      $i++; 
    }
  } /* if count(table.PrimaryKeys) */ 
?>
    }

    // Set the correct dbName    
    $criteria->setDbName(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
    
    $affectedRows = 0; // initialize var to track total num of affected rows    

    // use transaction because $criteria could contain info
    // for more than one table or we could emulating ON DELETE CASCADE, etc.
    $e = $con->begin();
    if (Creole::isError($e)) { $con->rollback(); return new PropelException(PROPEL_ERROR_DB, $e); }

<?php
  if ($deleteCascadeRelevant) { 
?>
    $e = <?php echo $table->getPhpName()?>Peer::doOnDeleteCascade($criteria, $con);
    if (Propel::isError($e)) { $con->rollback(); return $e; }
    $affectedRows += $e;
<?php
  } elseif ($deleteSetNullRelevant) { 
?>
    $e = <?php echo $table->getPhpName()?>Peer::doOnDeleteSetNull($criteria, $con);
    if (Propel::isError($e)) { $con->rollback(); return $e; }
    $affectedRows += $e;

<?php
  } 
?>
    $e = <?php echo $basePeerClassname ?>::doDelete($criteria, $con);
    if (Propel::isError($e)) { $con->rollback(); return $e; }
    $affectedRows += $e;

    $e = $con->commit();
    if (Creole::isError($e)) { $con->rollback(); return new PropelException(PROPEL_ERROR_DB, $e); }

    return $affectedRows;
  }

<?php
  if ($deleteCascadeRelevant) 
  { 
?>
  /**
  * This is a method for emulating ON DELETE CASCADE for DBs that don't support this
  * feature (like MySQL or SQLite).
  *
  * This method is not very speedy because it must perform a query first to get
  * the implicated records and then perform the deletes by calling those Peer classes.
  *
  * This method should be used within a transaction if possible.
  *
  * @param Criteria $criteria
  * @param Connection $con
  *
  * @return number of affected rows on success, PropelException on failure.
  */
  function doOnDeleteCascade(/*Criteria*/ $criteria, /*Connection*/ &$con)
  {
    // initialize var to track total num of affected rows
    $affectedRows = 0;

    // first find the objects that are implicated by the $criteria
    $objects =& <?php echo $table->getPhpName()?>Peer::doSelect($criteria, Param::set($con));
    if (Propel::isError($objects)) { return $objects; }

    for($i=0, $j=count($objects); $i < $j; $i++)
    {
      $obj =& $objects[$i];
<?php
    foreach ($table->getReferrers() as $fk) 
    {
      // $fk is the foreign key in the other table, so localTableName will
      // actually be the table name of other table
      $tblFK = $fk->getTable();
      $tblFKPackage = ($tblFK->getPackage() ? $tblFK->getPackage() : $package);

      if (!$tblFK->isForReferenceOnly()) 
      {
        // we can't perform operations on tables that are
        // not within the schema (i.e. that we have no map for, etc.)
        $fkClassName = $tblFK->getPhpName();

        // i'm not sure whether we can allow delete cascade for foreign keys
        // within the same table?  perhaps we can?
        if ( $fk->getOnDelete() == ForeignKey::CASCADE && $fk->getTable()->getName() != $table->getName()) 
        {
          // backwards on purpose
          $columnNamesF = $fk->getLocalColumns();
          $columnNamesL = $fk->getForeignColumns(); // should be same num as foreign
?>

      include_once '<?php echo ClassTools::getFilePath($tblFKPackage, $tblFK->getPhpName()); ?>';

      // delete related <?php echo $fkClassName ?> objects
      $c =& new Criteria();
<?php
          for($x=0,$xlen=count($columnNamesF); $x < $xlen; $x++) {
            $columnFK = $tblFK->getColumn($columnNamesF[$x]);
            $columnL = $table->getColumn($columnNamesL[$x]);
?>
      $c->add(<?php echo PeerBuilder::getColumnName($columnFK, $fkClassName) ?>(), $obj->get<?php echo $columnL->getPhpName() ?>());

<?php
            //$delCmds[] = $fkClassName.'Peer::doDelete('.');
          }
?>
      $e = <?php echo $fkClassName ?>Peer::doDelete($c, Param::set($con));
      if (Propel::isError($e)) { return $e; }
      $affectedRows += $e;
<?php
        } // if cascade && fkey table name != curr table name

      } // if not for ref only
    } // foreach foreign keys
?>
    }

    return $affectedRows;
  }

<?php } elseif ($deleteSetNullRelevant) { ?>

  /**
  * This is a method for emulating ON DELETE SET NULL DBs that don't support this
  * feature (like MySQL or SQLite).
  *
  * This method is not very speedy because it must perform a query first to get
  * the implicated records and then perform the deletes by calling those Peer classes.
  *
  * This method should be used within a transaction if possible.
  *
  * @param Criteria $criteria
  * @param Connection $con
  *
  * @return mixed number of affected rows on success, PropelException on failure.
  */
  function doOnDeleteSetNull(/*Criteria*/ $criteria, /*Connection*/ &$con)
  {
    // initialize var to track total num of affected rows
    $affectedRows = 0;

    // first find the objects that are implicated by the $criteria
    $objects =& <?php echo $table->getPhpName()?>Peer::doSelect($criteria, Param::set($con));
    if (Propel::isError($objects)) { return $objects; }

    for($i=0, $j=count($objects); $i < $j; $i++)
    {
      $obj =& $objects[$i];
<?php

        // This logic is almost exactly the same as that in doOnDeleteCascade()
        // it may make sense to refactor this, provided that thigns don't
        // get too complicated.

      foreach ($table->getReferrers() as $fk) {

        // $fk is the foreign key in the other table, so localTableName will
        // actually be the table name of other table
        $tblFK = $fk->getTable();

        if (!$tblFK->isForReferenceOnly()) {
          // we can't perform operations on tables that are
          // not within the schema (i.e. that we have no map for, etc.)

          $fkClassName = $tblFK->getPhpName();

          // i'm not sure whether we can allow delete setnull for foreign keys
          // within the same table?  perhaps we can?
          if ( $fk->getOnDelete() == ForeignKey::SETNULL &&
              $fk->getTable()->getName() != $table->getName()) {

            // backwards on purpose
            $columnNamesF = $fk->getLocalColumns();
            $columnNamesL = $fk->getForeignColumns(); // should be same num as foreign
?>
      // set fkey col in related <?php echo $fkClassName ?> rows to NULL
      $selectCriteria =& new Criteria(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
      $updateValues =& new Criteria(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
<?php
            for($x=0,$xlen=count($columnNamesF); $x < $xlen; $x++) {
              $columnFK = $tblFK->getColumn($columnNamesF[$x]);
              $columnL = $table->getColumn($columnNamesL[$x]);

?>
      $selectCriteria->add(<?php echo PeerBuilder::getColumnName($columnFK, $fkClassName) ?>(),
                           $obj->get<?php echo $columnL->getPhpName() ?>());
      $updateValues->add(<?php echo PeerBuilder::getColumnName($columnFK, $fkClassName) ?>(), null);
<?php
   }
?>
      // use BasePeer because generated Peer doUpdate() methods only update using pkey
      $e = <?php echo $basePeerClassname ?>::doUpdate($selectCriteria, $updateValues, $con);
      if (Propel::isError($e)) { return $e; }
      $affectedRows += $e;
<?php
          } // if cascade && fkey table name != curr table name

        } // if not for ref only
      } // foreach foreign keys
?>
    }

    return $affectedRows;
  }

<?php } /* if setnull relevant */ ?>


  /**
  * Validates all modified columns of given <?php echo $table->getPhpName()?> object.
  * If parameter $columns is either a single column name or an array of column names
  * than only those columns are validated.
  *
  * NOTICE: This does not apply to primary or foreign keys for now.
  *
  * @param <?php echo $table->getPhpName()?> $obj The object to validate.
  * @param mixed $cols Column name or array of column names.
  *
  * @return mixed TRUE if all columns are valid or the error message of the first invalid column.
  */
  function doValidate(&$obj, $cols = null)
  {
    Propel::typeHint($obj, '<?php echo $table->getPhpName()?>', '<?php echo $CLASS; ?>', 'doValidate');

    $dbName = <?php echo $table->getPhpName()?>Peer::DATABASE_NAME();
    $tableName = <?php echo $table->getPhpName()?>Peer::TABLE_NAME();
    $columns = array();

    if ($cols)
    {
      $dbMap =& Propel::getDatabaseMap($dbName);
      $tableMap =& $dbMap->getTable($tableName);

      if (! is_array($cols)) {
        $cols = array($cols);
      }

      foreach($cols as $colName)
      {
        if ($tableMap->containsColumn($colName))
        {
          $colMap =& $tableMap->getColumn($colName);
          $get = 'get' . $colMap->getPhpName();
          $columns[$colName] = $obj->$get();
        }
      }
    }
    else
    {
<?php
  foreach ($table->getValidators() as $val) {
    $col = $val->getColumn();
    if (! $col->isAutoIncrement()) {
      $cfc = $col->getPhpName();
      $cup = strtoupper($col->getName());
?>
    if ($obj->isNew() || $obj->isColumnModified(<?php echo $table->getPhpName()?>Peer::<?php echo $cup?>()))
      $columns[<?php echo $table->getPhpName()?>Peer::<?php echo $cup?>()] = $obj->get<?php echo $cfc?>();
<?php
    } // if
  } // foreach
?>
    }

    return <?php echo $basePeerClassname ?>::doValidate($dbName, $tableName, $columns);
  }

  /**
   * Build a Criteria object from the data object for this peer or from primary key(s).
   *
   * @param mixed $obj <?php echo $table->getPhpName() ?> object or <?php if (count($table->getPrimaryKey()) == 1) { ?>scalar primary key<?php } else { ?>array primary keys<?php } ?>.
   * @return Criteria The compiled Criteria object.
   */
  function buildCriteria(&$obj)
  {
    if (is_a($obj, '<?php echo $table->getPhpName() ?>' )) {
      $criteria =& new Criteria(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
<?php
        foreach ($table->getColumns() as $col) {
          $cfc = $col->getPhpName();
          if ($col->isPrimaryKey() && $table->getIdMethod() != "none") {
?>
      if (! $obj->isNew())
        $criteria->add(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>(), $obj->get<?php echo $cfc ?>()); // primary key on tables w/ id generation is only added if not new
<?php   } else { /* if col is not prim key */ ?>
      if ($obj->isColumnModified(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>()))
        $criteria->add(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>(), $obj->get<?php echo $cfc ?>());
<?php
          }
        }
?>

    } else {
      // it must be the primary key
      $criteria =& new Criteria(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
      <?php if (count($table->getPrimaryKey()) == 1) {
          $col = array_shift($table->getPrimaryKey()); ?>

      $criteria->add(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>(), $obj);
      <?php } else { ?>
        // primary key is composite; we therefore, expect
      // the primary key passed to be an array of pkey
      // values
    <?php
        $i=0;
          foreach($table->getPrimaryKey() as $col) { ?>
      $criteria->add(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col)?>(), $obj[<?php echo $i ?>]);
    <?php     $i++;
        }
      } /* if count(table.PrimaryKeys) */ ?>

    }

    return $criteria;
  }
<?php } /* if !table->isalias */ ?>

<?php if (count($table->getPrimaryKey()) > 0) {

  if ($table->isAlias()) {
    $retrieveMethod = "retrieve" . $table->getPhpName() . "ByPK";
  } else {
    $retrieveMethod = "retrieveByPK";
  }

  $pks = $table->getPrimaryKey();

if (count($table->getPrimaryKey()) === 1) {  ?>

  /**
  * Retrieve a single object by pkey or <em>NULL</em> if not found.
  *
  * @param mixed $pk The primary key.
  * @param Connection $con The connection to use.
  *
  * @return mixed <?php echo $table->getPhpName(); ?> on success, NULL on failure
  */
  function & <?php echo $retrieveMethod ?>($pk, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', '<?php echo $retrieveMethod; ?>', 2);

    $criteria =& new Criteria();
<?php if (count($table->getPrimaryKey()) === 1) { 
        $col = array_shift($table->getPrimaryKey());
?>
    $criteria->add(<?php echo $table->getPhpName() ?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>(), $pk);
<?php
      } else {
?>
    // primary key is composite; we therefore, expect
    // the primary key passed to be an array of pkey
    // values
<?php
       $i=0;
       foreach($table->getPrimaryKey() as $col) {
?>
    $criteria->add(<?php echo $table->getPhpName() ?>Peer::<?php echo PeerBuilder::getColumnName($col)?>, $pk[<?php echo $i ?>]);
<?php
          $i++; 
       }
     } /* if count(table.PrimaryKeys) */
?>

    $v = <?php echo $table->getPhpName() ?>Peer::doSelect($criteria, $con);
    return count($v) > 0 ? $v[0] : null;
  }

  /**
  * Retrieve multiple objects by pkey.
  *
  * @param array $pks List of primary keys
  * @param Connection $con The connection to use.
  *
  * @throws PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  */
  function & <?php echo $retrieveMethod ?>s($pks, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', '<?php echo $retrieveMethod; ?>', 2);

    $objs = null;
    if (empty($pks)) {
      $objs = array();
    } else {
      $criteria =& new Criteria();
<?php if (count($table->getPrimaryKey()) == 1) { ?>

      $criteria->add(<?php echo $table->getPhpName() ?>Peer::<?php $k1 = $table->getPrimaryKey(); echo strtoupper($k1[0]->getName()); ?>(), $pks, Criteria::IN());
<?php } else { ?>

      for($k=0,$size=count($pks); $k < $size; $k++) {
        $pk = $pks[$k];
        <?php $i = 0;
          foreach($table->getPrimaryKey() as $col) { ?>

        $c<?php echo $i ?> =& $criteria->getNewCriterion(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>(), $pk[<?php echo $i ?>], Criteria::EQUAL());
        <?php
        $j = $i - 1;
        if ($i > 0) { ?>

        $c<?php echo $j ?>->addAnd($c<?php echo $i ?>);
          <?php } /* if $i > 0 */
            $i++;
          } /* foreach */ ?>

        $criteria->addOr($c0);
      }
  <?php } /* if count prim keys == 1 */ ?>

      $objs =& <?php echo $table->getPhpName()?>Peer::doSelect($criteria, $con);
      if (Propel::isError($objs)) { return $objs; }
    }
    return $objs;
  }

<?php } else  {  // pkey count > 1

$comma = false;
?>
  /**
  * Retrieve object using pk values or <em>NULL</em> if not found.
  *
<?php foreach ($table->getPrimaryKey() as $col) {
  $clo = strtolower($col->getName());
  $cptype = $col->getPhpNative();
?> 
  * @param <?php echo $cptype ?> $<?php echo $clo ?>
<?php } ?>
  * @param Connection $con
  *
  * @return <?php echo $table->getPhpName() ?>
  */
  function <?php echo $retrieveMethod ?>(<?php foreach ($table->getPrimaryKey() as $col) { $clo = strtolower($col->getName()); ?><?php if ($comma) { ?>,<?php } ?> $<?php echo $clo ?><?php $comma = true; ?><?php } /* foreach */ ?>, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', '<?php echo $retrieveMethod ?>', -1);

    $criteria = new Criteria();
<?php foreach ($table->getPrimaryKey() as $col) {
  $clo = strtolower($col->getName());
?>
    $criteria->add(<?php echo $table->getPhpName()?>Peer::<?php echo PeerBuilder::getColumnName($col) ?>(), $<?php echo $clo ?>);
<?php } ?>

    $v =& <?php echo $table->getPhpName()?>Peer::doSelect($criteria, $con);
    return count($v) > 0 ? $v[0] : null;
  }

<?php } /* if pkey > 1 */

}  /* if pkey > 0 */ ?>

<?php

if ($complexObjectModel) {

 //
 // setup joins
 //
 $className = $table->getPhpName();
 $countFK = count($table->getForeignKeys());

 if ($countFK >= 1) {
  foreach ($table->getForeignKeys() as $fk) {
    $tblFK = $table->getDatabase()->getTable($fk->getForeignTableName());
    if (!$tblFK->isForReferenceOnly()) {
    // want to cover this other case, but the code is not there yet.
      if ( $fk->getForeignTableName() != $table->getName() ) {

        $partJoinName = "";
        foreach ($fk->getLocalColumns() as $columnName ) {
          $column = $table->getColumn($columnName);
          if ($column->isMultipleFK() || $fk->getForeignTableName() == $table->getName()) {
            $partJoinName = $partJoinName . $column->getPhpName();
          }
        }

        $joinTable = $table->getDatabase()->getTable($fk->getForeignTableName());
        $joinClassName = $joinTable->getPhpName();
        $interfaceName = $joinTable->getPhpName();
        if ($joinTable->getInterface()) {
           $interfaceName = $joinTable->getInterface();
        }

        if ($partJoinName == "") {
          $joinColumnId = $joinClassName;
          $joinInterface = $interfaceName;
          $collThisTable = $className . "s";
          $collThisTableMs = $className;
        } else {
          $joinColumnId= $joinClassName . "RelatedBy" . $partJoinName;
          $joinInterface= $interfaceName . "RelatedBy" . $partJoinName;
          $collThisTable= $className . "sRelatedBy" . $partJoinName;
          $collThisTableMs= $className . "RelatedBy" . $partJoinName;
        }

// ------------------------------------------------------------
?>
  /**
  * Selects a collection of <?php echo $className ?> objects pre-filled with their
  * <?php echo $joinClassName ?> objects.
  *
  * @return array Array of <?php echo $className ?> objects.
  * @throws PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  */
  function & doSelectJoin<?php echo $joinColumnId ?>(/*Criteria*/ $c, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doSelectJoin<?php echo $joinColumnId; ?>', 2);

    // Set the correct dbName if it has not been overridden
    if ($c->getDbName() == Propel::getDefaultDB()) {
      $c->setDbName(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
    }

    <?php echo $table->getPhpName() ?>Peer::addSelectColumns($c);
    $startcol = <?php echo $table->getPhpName() ?>Peer::numColumns() - <?php echo $table->getPhpName() ?>Peer::numLazyLoadColumns() + 1;
    <?php echo $joinClassName ?>Peer::addSelectColumns($c);

<?php
   $lfMap = $fk->getLocalForeignMapping();
   foreach ($fk->getLocalColumns() as $columnName ) {
    $column = $table->getColumn($columnName);
    $columnFk = $joinTable->getColumn( $lfMap[$columnName]);
?>
    $c->addJoin(<?php echo PeerBuilder::getColumnName($column, $table->getPhpName()) ?>(), <?php echo PeerBuilder::getColumnName($columnFk,$joinClassName)?>());
   <?php } ?>

    $rs =& <?php echo $basePeerClassname ?>::doSelect($c, $con);
    if (Propel::isError($rs)) { return $rs; }

    $results = array();

    while($rs->next())
    {
<?php if ($table->getChildrenColumn()) { ?>
      $omClass = <?php echo $table->getPhpName() ?>Peer::getOMClass($rs, 1);
<?php } else { ?>
      $omClass = <?php echo $table->getPhpName() ?>Peer::getOMClass();
<?php } ?>

      $cls =& Propel::import($omClass);
      if (Propel::isError($cls)) { return $cls; }

      $obj1 =& new $cls();

      $e =& $obj1->hydrate($rs);
      if (Propel::isError($e)) { return $e; }

<?php if ($joinTable->getChildrenColumn()) { ?>
      $omClass = <?php echo $joinClassName ?>Peer::getOMClass($rs, $startcol);
<?php } else { ?>
      $omClass = <?php echo $joinClassName ?>Peer::getOMClass();
<?php } ?>

      $cls =& Propel::import($omClass);
      if (Propel::isError($cls)) { return $cls; }

      $obj2 =& new $cls();

      $e =& $obj2->hydrate($rs, $startcol);
      if (Propel::isError($e)) { return $e; }

      $newObject = true;
      foreach($results as $temp_obj1)
      {
        $temp_obj2 =& $temp_obj1->get<?php echo $joinInterface ?>();
        if ($temp_obj2->getPrimaryKey() === $obj2->getPrimaryKey()) {
          $newObject = false;
          $temp_obj2->add<?php echo $collThisTableMs ?>($obj1);
          break;
        }
      }
      if ($newObject) {
        $obj2->init<?php echo $collThisTable ?>();
        $obj2->add<?php echo $collThisTableMs ?>($obj1);
      }
      $results[] =& $obj1;
    }

    return $results;
  }
<?php
    } // if fk table name != this table name
   } // if ! is reference only
  } // foreach column
 } // if count(fk) > 1

// ===========================================================

  if ($countFK > 1) {
    $includeJoinAll = true;
    foreach ($table->getForeignKeys() as $fk) {
      $tblFK = $table->getDatabase()->getTable($fk->getForeignTableName());
      if ($tblFK->isForReferenceOnly()) {
        $includeJoinAll = false;
      }
    }

    if ($includeJoinAll) {
      // ------------------------------------------------------------------------
      // doSelectJoinAll()
      // ------------------------------------------------------------------------
  
      //1 ) create the master doSelectJoinAll() method
      
      $tblFK = $table->getDatabase()->getTable($fk->getForeignTableName());
      
      $relatedByCol = "";
      foreach ($fk->getLocalColumns() as $columnName) {
        $column = $table->getColumn($columnName);
        if ($column->isMultipleFK()) {
          $relatedByCol .= $column->getPhpName();
        }
      }
    
      if ($relatedByCol == "") {
        $collThisTable = "${className}s";
        $collThisTableMs = $className;
      } else {
        $collThisTable = $className . "sRelatedBy" . $relatedByCol;
        $collThisTableMs = $className . "RelatedBy" . $relatedByCol;
      }
?>

  /**
  * Selects a collection of <?php echo $className ?> objects pre-filled with
  * all related objects.
  *
  * @return array Array of <?php echo $className ?> objects.
  * @throws PropelException Any exceptions caught during processing will be
  *         rethrown wrapped into a PropelException.
  */
  function doSelectJoinAll(/*Criteria*/ &$c, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doSelectJoinAll', 2);
    
    // Set the correct dbName if it has not been overridden
    if ($c->getDbName() == Propel::getDefaultDB()) {
      $c->setDbName(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
    }

    <?php echo $table->getPhpName() ?>Peer::addSelectColumns($c);
    $startcol2 = <?php echo $table->getPhpName() ?>Peer::numColumns() - <?php echo $table->getPhpName() ?>Peer::numLazyLoadColumns() + 1;
<?php
      $index = 2;
      foreach ($table->getForeignKeys() as $fk) {
        // want to cover this case, but the code is not there yet.
        if ( $fk->getForeignTableName() != $table->getName() ) {
          $joinTable = $table->getDatabase()->getTable($fk->getForeignTableName());
          $joinClassName = $joinTable->getPhpName();
          $new_index = $index + 1;
?> 
    <?php echo $joinClassName ?>Peer::addSelectColumns($c);
    $startcol<?php echo $new_index ?> = $startcol<?php echo $index?> + <?php echo $joinClassName ?>Peer::numColumns();
<?php
          $index = $new_index;
      } // if fk->getForeignTableName != table->getName
    } // foreach [sub] foreign keys
    
    foreach ($table->getForeignKeys() as $fk) {
      // want to cover this case, but the code is not there yet.
      if ( $fk->getForeignTableName() != $table->getName() ) {
        $joinTable = $table->getDatabase()->getTable($fk->getForeignTableName());
        $joinClassName = $joinTable->getPhpName();
        $lfMap = $fk->getLocalForeignMapping();
        foreach ($fk->getLocalColumns() as $columnName ) {
          $column = $table->getColumn($columnName);
          $columnFk = $joinTable->getColumn( $lfMap[$columnName]);
?>
    $c->addJoin(<?php echo PeerBuilder::getColumnName($column, $table->getPhpName()) ?>(), <?php echo PeerBuilder::getColumnName($columnFk,$joinClassName)?>());
<?php
        } // foreach
      } // if
    } // foreach
?>

    $rs =& <?php echo $basePeerClassname ?>::doSelect($c, $con);
    if (Propel::isError($rs)) { return $rs; }
    $results = array();
    
    while($rs->next()) {
<?php 
    if ($table->getChildrenColumn()) { 
?> 
      $omClass = <?php echo $table->getPhpName() ?>Peer::getOMClass($rs, 1);
<?php 
    } else {
?> 
      $omClass = <?php echo $table->getPhpName() ?>Peer::getOMClass();
<?php 
    } 
?>
      
      $cls = Propel::import($omClass);
      if (Propel::isError($cls)) { return $cls; }
      
      $obj1 =& new $cls();
      
      $e =& $obj1->hydrate($rs);
      if (Propel::isError($e)) { return $e; }
<?php
    $index = 1;
    foreach ($table->getForeignKeys() as $fk ) {
      // want to cover this case, but the code is not there yet.
      if ( $fk->getForeignTableName() != $table->getName() ) {
        $joinTable = $table->getDatabase()->getTable($fk->getForeignTableName());
        $joinClassName = $joinTable->getPhpName();
        $interfaceName = $joinTable->getPhpName();
        if($joinTable->getInterface()) {
          $interfaceName = $joinTable->getInterface();
        }
        
        $partJoinName = "";
        foreach ($fk->getLocalColumns() as $columnName ) {
          $column = $table->getColumn($columnName);
          if ($column->isMultipleFK()) {
            $partJoinName .= $column->getPhpName();
          }
        }
        
        if ($partJoinName == "") {
          $joinString = $interfaceName;
          $collThisTable = "${className}s";
          $collThisTableMs = $className;
        } else {
          $joinString= $interfaceName."RelatedBy" . $partJoinName;
          $collThisTable= $className . "sRelatedBy" . $partJoinName;
          $collThisTableMs= $className . "RelatedBy" . $partJoinName;
        }
        
        $index++;
?> 
      
      // Add objects for joined <?php echo $joinClassName ?> rows
<?php
        if ($joinTable->getChildrenColumn()) {
?> 
      $omClass = <?php echo $joinClassName ?>Peer::getOMClass($rs, $startcol<?php echo $index ?>);
<?php   } else { ?>
      $omClass = <?php echo $joinClassName ?>Peer::getOMClass();
<?php 
        } /* $joinTable->getChildrenColumn() */
?>
  
      $cls = Propel::import($omClass);
      if (Propel::isError($cls)) { return $cls; }
      
      $obj<?php echo $index ?> =& new $cls();
      
      $e = $obj<?php echo $index ?>->hydrate($rs, $startcol<?php echo $index ?>);
      if (Propel::isError($e)) { return $e; }
      
      $newObject = true;
      for ($j=0, $resCount=count($results); $j < $resCount; $j++) {
        $temp_obj1 =& $results[$j];
        $temp_obj<?php echo $index ?> =& $temp_obj1->get<?php echo $joinString ?>();
        if ($temp_obj<?php echo $index ?>->getPrimaryKey() === $obj<?php echo $index ?>->getPrimaryKey()) {
          $newObject = false;
          $temp_obj<?php echo $index ?>->add<?php echo $collThisTableMs ?>($obj1);
          break;
        }
      }
      
      if ($newObject) {
        $obj<?php echo $index ?>->init<?php echo $collThisTable ?>();
        $obj<?php echo $index ?>->add<?php echo $collThisTableMs ?>($obj1);
      }
  <?php

      } // $fk->getForeignTableName() != $table->getName()
    } //foreach foreign key
?>
      $results[] =& $obj1;
    }
    
    return $results;
  }
<?php   
    
    // ------------------------------------------------------------------------
    // doSelectJoinAllExcept*()
    // ------------------------------------------------------------------------
    
    // 2) create a bunch of doSelectJoinAllExcept*() methods
    // -- these were existing in original Torque, so we should keep them for compatibility
    
    $fkeys = $table->getForeignKeys();  // this sep assignment is necessary otherwise sub-loops over 
    foreach ($fkeys as $fk ) {          // getForeignKeys() will cause this to only execute one time.
      $tblFK = $table->getDatabase()->getTable($fk->getForeignTableName());

      $excludeTable = $table->getDatabase()->getTable($fk->getForeignTableName());
      $excludeClassName = $excludeTable->getPhpName();

      $relatedByCol = "";
      foreach ($fk->getLocalColumns() as $columnName) {
        $column = $table->getColumn($columnName);
        if ($column->isMultipleFK()) {
          $relatedByCol .= $column->getPhpName();
        }
      }

      if ($relatedByCol == "") {
        $excludeString = $excludeClassName;
        $collThisTable = "${className}s";
        $collThisTableMs = $className;
      } else {
        $excludeString = $excludeClassName . "RelatedBy" . $relatedByCol;
        $collThisTable = $className . "sRelatedBy" . $relatedByCol;
        $collThisTableMs = $className . "RelatedBy" . $relatedByCol;
      }
?>

  /**
  * Selects a collection of <?php echo $className ?> objects pre-filled with
  * all related objects except <?php echo $excludeString ?>.
  *
  * @return array Array of <?php echo $className ?> objects.
  * @throws PropelException Any exceptions caught during processing will be
  *     rethrown wrapped into a PropelException.
  */
  function doSelectJoinAllExcept<?php echo $excludeString ?>(/*Criteria*/ &$c, $con = null)
  {
    /* [MA] temporarily check */
    Propel::assertParam($con, '<?php echo $CLASS; ?>', 'doSelectJoinAllExcept<?php echo $excludeString; ?>', 2);
    
    // Set the correct dbName if it has not been overridden
    // $c->getDbName() will return the same object if not set to another value
    // so == check is okay and faster
    if ($c->getDbName() == Propel::getDefaultDB()) {
      $c->setDbName(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
    }

    <?php echo $table->getPhpName() ?>Peer::addSelectColumns($c);
    $startcol2 = <?php echo $table->getPhpName() ?>Peer::numColumns() - <?php echo $table->getPhpName() ?>Peer::numLazyLoadColumns() + 1;
<?php
      $index = 2;
      foreach ($table->getForeignKeys() as $subfk) {
        // want to cover this case, but the code is not there yet.
      if ( !($subfk->getForeignTableName() == $table->getName())) {
        $joinTable = $table->getDatabase()->getTable($subfk->getForeignTableName());
        $joinClassName = $joinTable->getPhpName();
  
        if ($joinClassName != $excludeClassName) {
          $new_index = $index + 1;
?> 
    <?php echo $joinClassName ?>Peer::addSelectColumns($c);
    $startcol<?php echo $new_index ?> = $startcol<?php echo $index?> + <?php echo $joinClassName ?>Peer::numColumns();
<?php
          $index = $new_index;
        } 
      }
    } // foreach [sub] foreign keys    
    
    foreach ($table->getForeignKeys() as $subfk) {
      // want to cover this case, but the code is not there yet.
      if ( $subfk->getForeignTableName() != $table->getName() ) {
        $joinTable = $table->getDatabase()->getTable($subfk->getForeignTableName());
        $joinClassName = $joinTable->getPhpName();
        if($joinClassName != $excludeClassName)
        {
          $lfMap = $subfk->getLocalForeignMapping();
          foreach ($subfk->getLocalColumns() as $columnName ) {
            $column = $table->getColumn($columnName);
            $columnFk = $joinTable->getColumn( $lfMap[$columnName]);
?>
    $c->addJoin(<?php echo PeerBuilder::getColumnName($column, $table->getPhpName()) ?>(), <?php echo PeerBuilder::getColumnName($columnFk,$joinClassName)?>());
<?php
          }
        }
      }
    }
?>

    $rs =& <?php echo $basePeerClassname ?>::doSelect($c, $con);
    if (Propel::isError($rs)) { return $rs; }
    
    $results = array();
    
    while($rs->next()) {
<?php
    if ($table->getChildrenColumn()) {
?> 
      $omClass = <?php echo $table->getPhpName() ?>Peer::getOMClass($rs, 1);
<?php
    } else {
?> 
      $omClass = <?php echo $table->getPhpName() ?>Peer::getOMClass();
<?php
    }
?>
      
      $cls = Propel::import($omClass);
      if (Propel::isError($cls)) { return $cls; }
      
      $obj1 =& new $cls();
      $e = $obj1->hydrate($rs);
      if (Propel::isError($e)) { return $e; }
      
<?php
    $index = 1;
    foreach ($table->getForeignKeys() as $subfk ) {
      // want to cover this case, but the code is not there yet.
      if ( $subfk->getForeignTableName() != $table->getName() ) {
        $joinTable = $table->getDatabase()->getTable($subfk->getForeignTableName());
        $joinClassName = $joinTable->getPhpName();
        $interfaceName = $joinTable->getPhpName();

        if($joinTable->getInterface()) {
          $interfaceName = $joinTable->getInterface();
        }

        if ($joinClassName != $excludeClassName) {
          $partJoinName = "";
          foreach ($subfk->getLocalColumns() as $columnName ) {
            $column = $table->getColumn($columnName);
            if ($column->isMultipleFK()) {
              $partJoinName .= $column->getPhpName();
            }
          }

          if ($partJoinName == "") {
            $joinString = $interfaceName;
            $collThisTable = "${className}s";
            $collThisTableMs = $className;
          } else {
            $joinString= $interfaceName."RelatedBy" . $partJoinName;
            $collThisTable= $className . "sRelatedBy" . $partJoinName;
            $collThisTableMs= $className . "RelatedBy" . $partJoinName;
          }

          $index++;

          if ($joinTable->getChildrenColumn()) {
?>
      $omClass = <?php echo $joinClassName ?>Peer::getOMClass($rs, $startcol<?php echo $index ?>);
<?php     } else { ?>
      $omClass = <?php echo $joinClassName ?>Peer::getOMClass();
<?php 
          } /* $joinTable->getChildrenColumn() */
?>
  
      $cls = Propel::import($omClass);
      if (Propel::isError($cls)) { return $cls; }
      
      $obj<?php echo $index ?>  =& new $cls();
      
      $e = $obj<?php echo $index ?>->hydrate($rs, $startcol<?php echo $index ?>);
      if (Propel::isError($e)) { return $e; }
      
      $newObject = true;
      for ($j=0, $resCount=count($results); $j < $resCount; $j++) {
        $temp_obj1 =& $results[$j];
        $temp_obj<?php echo $index ?> =& $temp_obj1->get<?php echo $joinString ?>();
        if ($temp_obj<?php echo $index ?>->getPrimaryKey() === $obj<?php echo $index ?>->getPrimaryKey()) {
          $newObject = false;
          $temp_obj<?php echo $index ?>->add<?php echo $collThisTableMs ?>($obj1);
          break;
        }
      }
      
      if ($newObject) {
        $obj<?php echo $index ?>->init<?php echo $collThisTable ?>();
        $obj<?php echo $index ?>->add<?php echo $collThisTableMs ?>($obj1);
      }
  <?php
        } // if ($joinClassName != $excludeClassName) {
      } // $subfk->getForeignTableName() != $table->getName()
    } // foreach  
?>
      $results[] =& $obj1;
    }
    
    return $results;
  }
<?php
       } // foreach fk
         // end of doSelectJoinAllExcept*() block
     } // if includeJoinAll
   } /* if count($fk) > 2 */
 } /* if complex object model */

 // two extra #end ...


//------------------------------------------------------------

if (!$table->isAlias()) {
?>
  /**
   * Returns the TableMap related to this peer.  This method is not
   * needed for general use but a specific application could have a need.
   * @return TableMap
   * @throws PropelException Any exceptions caught during processing will be
   *         rethrown wrapped into a PropelException.
   */
  function & getTableMap()
  {
    $dbMap =& Propel::getDatabaseMap(<?php echo $table->getPhpName()?>Peer::DATABASE_NAME());
    if (Propel::isError($dbMap)) {
      return $dbMap;
    }
    return $dbMap->getTable(<?php echo $table->getPhpName()?>Peer::TABLE_NAME());
  }

<?php } /* !table->isalias */ ?>
}

// static code to register the map builder for this Peer with the main Propel class
if (Propel::isInit()) {
  // the MapBuilder classes register themselves with Propel during initialization
  // so we need to load them here.
  if (Propel::isError($e = <?php echo $basePrefix . $table->getPhpName() ?>Peer::getMapBuilder())) {
    Propel::log("Could not initialize Peer: " . $e->getMessage(), PROPEL_LOG_ERR);
  }
} else {
  // even if Propel is not yet initialized, the map builder class can be registered
  // now and then it will be loaded when Propel initializes.
  require_once '<?php echo ClassTools::getFilePath($pkmap, $table->getPhpName() . 'MapBuilder') ?>';
  Propel::registerMapBuilder(<?php echo $table->getPhpName()?>MapBuilder::CLASS_NAME());
}
