Index: Db/Table/Row/Abstract.php =================================================================== --- Db/Table/Row/Abstract.php (revision 8885) +++ Db/Table/Row/Abstract.php (working copy) @@ -144,7 +144,7 @@ $info = $table->info(); $this->_primary = (array) $info['primary']; } - + $this->init(); } @@ -480,7 +480,8 @@ $pkOld = $this->_getPrimaryKey(false); foreach ($depTables as $tableClass) { try { - @Zend_Loader::loadClass($tableClass); + //@Zend_Loader::loadClass($tableClass); + $tableClass = $this->_getTable()->_loadClass($tableClass); } catch (Zend_Exception $e) { require_once 'Zend/Db/Table/Row/Exception.php'; throw new Zend_Db_Table_Row_Exception($e->getMessage()); @@ -550,7 +551,8 @@ $pk = $this->_getPrimaryKey(); foreach ($depTables as $tableClass) { try { - @Zend_Loader::loadClass($tableClass); + //@Zend_Loader::loadClass($tableClass); + $tableClass = $this->_getTable()->_loadClass($tableClass); } catch (Zend_Exception $e) { require_once 'Zend/Db/Table/Row/Exception.php'; throw new Zend_Db_Table_Row_Exception($e->getMessage()); @@ -773,8 +775,12 @@ */ protected function _prepareReference(Zend_Db_Table_Abstract $dependentTable, Zend_Db_Table_Abstract $parentTable, $ruleKey) { - $map = $dependentTable->getReference(get_class($parentTable), $ruleKey); + foreach ($parentTable->getRelationshipPath() as $relationshipPath) { + $parentTable = str_replace('_', '', str_replace($relationshipPath, '', get_class($parentTable))); + } + $map = $dependentTable->getReference($parentTable, $ruleKey); + if (!isset($map[Zend_Db_Table_Abstract::REF_COLUMNS])) { $parentInfo = $parentTable->info(); $map[Zend_Db_Table_Abstract::REF_COLUMNS] = array_values((array) $parentInfo['primary']); @@ -797,10 +803,11 @@ public function findDependentRowset($dependentTable, $ruleKey = null, Zend_Db_Table_Select $select = null) { $db = $this->_getTable()->getAdapter(); - + if (is_string($dependentTable)) { try { - @Zend_Loader::loadClass($dependentTable); + //@Zend_Loader::loadClass($dependentTable); + $dependentTable = $this->_getTable()->_loadClass($dependentTable); } catch (Zend_Exception $e) { require_once 'Zend/Db/Table/Row/Exception.php'; throw new Zend_Db_Table_Row_Exception($e->getMessage()); @@ -853,7 +860,8 @@ if (is_string($parentTable)) { try { - @Zend_Loader::loadClass($parentTable); + //@Zend_Loader::loadClass($parentTable); + $parentTable = $this->_getTable()->_loadClass($parentTable); } catch (Zend_Exception $e) { require_once 'Zend/Db/Table/Row/Exception.php'; throw new Zend_Db_Table_Row_Exception($e->getMessage()); @@ -907,7 +915,8 @@ if (is_string($intersectionTable)) { try { - @Zend_Loader::loadClass($intersectionTable); + //@Zend_Loader::loadClass($intersectionTable); + $intersectionTable = $this->_getTable()->_loadClass($intersectionTable); } catch (Zend_Exception $e) { require_once 'Zend/Db/Table/Row/Exception.php'; throw new Zend_Db_Table_Row_Exception($e->getMessage()); @@ -925,7 +934,8 @@ if (is_string($matchTable)) { try { - @Zend_Loader::loadClass($matchTable); + //@Zend_Loader::loadClass($matchTable); + $matchTable = $this->_getTable()->_loadClass($matchTable); } catch (Zend_Exception $e) { require_once 'Zend/Db/Table/Row/Exception.php'; throw new Zend_Db_Table_Row_Exception($e->getMessage()); @@ -946,7 +956,7 @@ } else { $select->setTable($matchTable); } - + // Use adapter from intersection table to ensure correct query construction $interInfo = $intersectionTable->info(); $interDb = $intersectionTable->getAdapter(); @@ -1013,13 +1023,13 @@ protected function __call($method, array $args) { $matches = array(); - + if (count($args) && $args[0] instanceof Zend_Db_Table_Select) { $select = $args[0]; } else { $select = null; } - + /** * Recognize methods for Has-Many cases: * findParent() Index: Db/Table/Abstract.php =================================================================== --- Db/Table/Abstract.php (revision 8885) +++ Db/Table/Abstract.php (working copy) @@ -202,6 +202,13 @@ protected $_dependentTables = array(); /** + * Path stack for database tables. + * + * @var array + */ + protected static $_path = array(); + + /** * Constructor. * * Supported params for $config are: @@ -271,6 +278,81 @@ } /** + * @param string $path + * @param string $classPrefix + * @return void + */ + public static final function addRelationshipPath($path, $classPrefix = '') + { + if (!empty($classPrefix) && ('_' != substr($classPrefix, -1))) { + $classPrefix .= '_'; + } + + self::_addPath($path, $classPrefix); + } + + /** + * Returns relations + * + * @return array + */ + public static final function getRelationshipPath() + { + return self::$_path; + } + + /** + * @param string $name + * @return class name + */ + public function _loadClass($name) + { + // check to see if name => class mapping exists for helper/filter + $classLoaded = '_Loaded'; + $classAccess = '_setClass'; + if (isset($this->$classLoaded[$name])) { + return $this->$classLoaded[$name]; + } + + // only look for "$Name.php" + $file = ucfirst($name) . '.php'; + + // do LIFO search for helper + foreach (self::$_path as $info) { + $dir = $info['dir']; + $prefix = $info['prefix']; + + $class = $prefix . ucfirst($name); + $class = preg_replace('/([a-z])([A-Z])/', "$1_$2", $class); + + Zend_Loader::loadClass($class); + return $class; + } + + require_once 'Zend/View/Exception.php'; + throw new Zend_View_Exception("'$name' not found in path", $this); + } + + /** + * @param string $path + * @param string $prefix + * @return void + */ + private function _addPath($path, $prefix = null) + { + foreach ((array) $path as $dir) { + // attempt to strip any possible separator and + // append the system directory separator + $dir = str_replace(array('/', '\\'), DIRECTORY_SEPARATOR, $dir); + $dir = rtrim($dir, DIRECTORY_SEPARATOR . DIRECTORY_SEPARATOR) + . DIRECTORY_SEPARATOR; + + // add as array with prefix and dir keys + array_unshift(self::$_path, array('prefix' => $prefix, 'dir' => $dir)); + } + } + + /** * @param string $classname * @return Zend_Db_Table_Abstract Provides a fluent interface */ @@ -751,16 +833,16 @@ self::DEPENDENT_TABLES => $this->_dependentTables, self::SEQUENCE => $this->_sequence ); - + if ($key === null) { return $info; } - + if (!array_key_exists($key, $info)) { require_once 'Zend/Db/Table/Exception.php'; throw new Zend_Db_Table_Exception('There is no table information for the key "' . $key . '"'); } - + return $info[$key]; }