private static function joinTables(array &$arrSelectState, Prototype $aForPrototype) { // add columns for pass in prototype $arrColumns = array_merge($aForPrototype->columns(), $aForPrototype->keys()); foreach ($arrColumns as $sColumnName) { $arrSelectState['statement']->addColumn($sColumnName, null, $aForPrototype->sqlTableAlias()); } // join tables $sFromTableAlias = $aForPrototype->sqlTableAlias(); foreach ($aForPrototype->associationIterator() as $aAssoc) { $aPrototype = $aAssoc->toPrototype(); $sTableAlias = $aPrototype->sqlTableAlias(); // 一对一关联 if ($aAssoc->isType(Association::oneToOne)) { $arrSelectState['statement']->joinTableRaw($sFromTableAlias, $aPrototype->tableName(), $sTableAlias, $aAssoc->joinType(), self::makeResrictionForForeignKey($sFromTableAlias, $sTableAlias, $aAssoc->fromKeys(), $aAssoc->toKeys(), $aAssoc->joinOnRawSql())); // 递归 join self::joinTables($arrSelectState, $aPrototype); } else { $arrSelectState['multitermAssocs'][] = $aAssoc; // 三表关联 if ($aAssoc->isType(Association::triplet)) { $sBridgeTableAlias = $aAssoc->bridgeSqlTableAlias(); $sBridgeTable = $aAssoc->bridgeTableName(); // 从中间表连接到右表 $aPrototype->sharedStatementSelect()->joinTableRaw($sTableAlias, $sBridgeTable, $sBridgeTableAlias, $aAssoc->joinType(), self::makeResrictionForForeignKey($sTableAlias, $sBridgeTableAlias, $aAssoc->toKeys(), $aAssoc->fromBridgeKeys(), $aAssoc->joinOnRawSql())); } } } }
public static function buildRestriction(Prototype $aPrototype, $values = null, $keys = null) { if ($values === null) { return null; } $keys = $keys ? (array) $keys : $aPrototype->keys(); if ($values instanceof Restriction) { return $values; } else { $aRestriction = new Restriction(); $sSqlTableAlias = $aPrototype->sqlTableAlias(); $values = array_values((array) $values); foreach ($keys as $nIdx => $sKey) { list($sTable, $sColumn) = SQL::splitColumn($sKey); $aRestriction->expression(array(SQL::createRawColumn($sTable, $sColumn), '=', SQL::transValue($values[$nIdx])), true, true); } return $aRestriction; } }