Skip to content

Commit

Permalink
Merge branch 'master' of github.com:AidasK/yii-closure-table-behavior
Browse files Browse the repository at this point in the history
  • Loading branch information
AidasK committed Aug 5, 2013
2 parents 2a93cbd + b33d8df commit 165ee41
Show file tree
Hide file tree
Showing 3 changed files with 60 additions and 25 deletions.
51 changes: 26 additions & 25 deletions ClosureTableBehavior.php
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ class ClosureTableBehavior extends CActiveRecordBehavior

/**
* Finds descendants
* @param int $primaryKey.
* @param int|string $primaryKey.
* @param int $depth the depth.
* @return CActiveRecord the owner.
*/
Expand All @@ -34,9 +34,9 @@ public function descendantsOf($primaryKey, $depth = null)
$primaryKeyName = $db->quoteColumnName($owner->tableSchema->primaryKey);
$criteria->mergeWith(array(
'join' => 'JOIN ' . $closureTable
. ' ON ' . $closureTable . '.' . $db->quoteColumnName($this->childAttribute) . '='
. ' ON ' . $closureTable . '.' . $childAttribute . '='
. $alias . '.' . $primaryKeyName,
'condition' => $closureTable . '.' . $db->quoteColumnName($this->parentAttribute) . '=' . $primaryKey
'condition' => $closureTable . '.' . $parentAttribute . '=' . $db->quoteValue($primaryKey)
));
if ($depth === null) {
$criteria->addCondition(
Expand Down Expand Up @@ -64,7 +64,7 @@ public function descendants($depth = null)

/**
* Named scope. Gets children for node (direct descendants only).
* @param int $primaryKey
* @param int|string $primaryKey
* @return CActiveRecord the owner.
*/
public function childrenOf($primaryKey)
Expand All @@ -83,7 +83,7 @@ public function children()

/**
* Named scope. Gets ancestors for node.
* @param int $primaryKey primary key
* @param int|string $primaryKey primary key
* @param int $depth the depth.
* @return CActiveRecord the owner.
*/
Expand Down Expand Up @@ -123,7 +123,7 @@ public function ancestors($depth = null)

/**
* Named scope. Gets parent of node.
* @param int $primaryKey primary key
* @param int|string $primaryKey primary key
* @return CActiveRecord the owner.
*/
public function parentOf($primaryKey)
Expand All @@ -142,7 +142,7 @@ public function parent()

/**
* Named scope. Gets path to the node.
* @param int $primaryKey primary key
* @param int|string $primaryKey primary key
* @return CActiveRecord the owner.
*/
public function unorderedPathOf($primaryKey)
Expand All @@ -157,16 +157,17 @@ public function unorderedPathOf($primaryKey)
$primaryKeyName = $db->quoteColumnName($owner->tableSchema->primaryKey);
$criteria->mergeWith(array(
'join' => 'JOIN ' . $closureTable . ' ' . $closureTableAlias
. ' ON ' . $closureTableAlias . '.' . $db->quoteColumnName($this->parentAttribute) . '='
. $alias . '.' . $primaryKeyName,
'condition' => $closureTableAlias . '.' . $db->quoteColumnName($this->childAttribute) . '=' . $primaryKey
. ' ON ' . $closureTableAlias . '.' . $db->quoteColumnName($this->parentAttribute) . '='
. $alias . '.' . $primaryKeyName,
'condition' => $closureTableAlias . '.' . $db->quoteColumnName($this->childAttribute) . '='
. $db->quoteValue($primaryKey)
));
return $owner;
}

/**
* Named scope. Gets path to the node.
* @param int $primaryKey primary key
* @param int|string $primaryKey primary key
* @return CActiveRecord the owner.
*/
public function pathOf($primaryKey)
Expand Down Expand Up @@ -218,7 +219,7 @@ public function fullPathOf($primaryKey)
. ' ON ct1.' . $parentAttribute . '=ct2.' . $parentAttribute
. ' AND ' . $alias . '.' . $primaryKeyName . '=ct2.' . $childAttribute
. ' AND ct2.' . $db->quoteColumnName($this->depthAttribute) . '=1',
'condition' => 'ct1.' . $childAttribute . '=' . $primaryKey
'condition' => 'ct1.' . $childAttribute . '=' . $db->quoteValue($primaryKey)
));
return $owner;
}
Expand Down Expand Up @@ -274,7 +275,7 @@ public function leaf()
*/
public function isLeaf()
{
return (boolean)$this->getOwner()->{$this->isLeafParameter};
return (boolean) $this->getOwner()->{$this->isLeafParameter};
}

/**
Expand Down Expand Up @@ -333,13 +334,13 @@ public function markAsRoot($primaryKey)
. '(' . $parentAttribute . ',' . $childAttribute . ',' . $depthAttribute . ') '
. 'VALUES (:nodeId,:nodeId,\'0\')'
);
return $cmd->execute(array(':nodeId'=>$primaryKey));
return $cmd->execute(array(':nodeId' => $primaryKey));
}

/**
* Appends node to target as child (Only for new records).
* @param CActiveRecord|int $target where to append
* @param CActiveRecord|int $node node to append
* @param CActiveRecord|int|string $target where to append
* @param CActiveRecord|int|string $node node to append
* @return number of rows inserted, on fail - 0
*/
public function appendTo($target, $node = null)
Expand All @@ -349,9 +350,9 @@ public function appendTo($target, $node = null)
$db = $owner->getDbConnection();
$closureTable = $db->quoteTableName($this->closureTableName);
if ($target instanceof CActiveRecord) {
$primaryKey = $db->quoteValue($target->primaryKey);
$primaryKey = $target->primaryKey;
} else {
$primaryKey = $db->quoteValue($target);
$primaryKey = $target;
}
if ($node === null) {
$node = $owner;
Expand All @@ -370,10 +371,10 @@ public function appendTo($target, $node = null)
. 'SELECT ' . $parentAttribute . ',:nodeId'
. ',' . $depthAttribute . '+1 '
. 'FROM ' . $closureTable
. 'WHERE ' . $childAttribute . '=' . $primaryKey
. 'WHERE ' . $childAttribute . '=:pk '
. 'UNION ALL SELECT :nodeId,:nodeId,\'0\''
);
return $cmd->execute(array(':nodeId'=>$nodeId));
return $cmd->execute(array(':nodeId' => $nodeId, ':pk' => $primaryKey));
}


Expand All @@ -389,8 +390,8 @@ public function append(CActiveRecord $target)

/**
* Move node
* @param CActiveRecord|int $target
* @param CActiveRecord|int $node if null, owner id will be used
* @param CActiveRecord|int|string $target
* @param CActiveRecord|int|string $node if null, owner id will be used
* @throws CDbException|Exception
*/
public function moveTo($target, $node = null)
Expand Down Expand Up @@ -427,7 +428,7 @@ public function moveTo($target, $node = null)
. 'WHERE d.' . $parentAttribute . '=? AND x.' . $parentAttribute . ' IS NULL'
);
if (!$cmd->execute(array($nodeId))) {
throw new CDbException('Node had no records in closure table');
throw new CDbException('Node had no records in closure table', 200);
}
$cmd = $db->createCommand(
'INSERT INTO ' . $closureTable . '(' . $parentAttribute . ',' . $childAttribute . ',' . $depthAttribute . ')'
Expand All @@ -437,7 +438,7 @@ public function moveTo($target, $node = null)
. 'WHERE b.' . $parentAttribute . '=? AND u.' . $childAttribute . '=?'
);
if (!$cmd->execute(array($nodeId, $targetId))) {
throw new CDbException('Target node does not exist');
throw new CDbException('Target node does not exist', 201);
}
if (isset($transaction)) {
$transaction->commit();
Expand Down Expand Up @@ -470,7 +471,7 @@ public function deleteNode($primaryKey = null)
'DELETE t, f '
. 'FROM ' . $closureTable . ' t '
. 'JOIN ' . $closureTable . ' tt ON t.' . $childAttribute . '= tt.' . $childAttribute
. 'JOIN ' . $owner->tableName() . ' f ON t.' . $childAttribute . '=f.'.$primaryKeyName
. 'JOIN ' . $owner->tableName() . ' f ON t.' . $childAttribute . '=f.' . $primaryKeyName
. 'WHERE tt.' . $db->quoteColumnName($this->parentAttribute) . '=?'
);
return $cmd->execute(array($primaryKey));
Expand Down
1 change: 1 addition & 0 deletions tests/models/Folder.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
* @method Folder parent() Named scope. Gets parent
* @method Folder pathOf($primaryKey) Named scope. Gets path
* @method Folder path() Named scope. Gets path
* @method Folder unorderedPathOf($primaryKey) Named scope. Gets path to the node.
* @method Folder fullPathOf($primaryKey) Named scope. Get path with its children. (Warning: root node isn't returned.)
* @method Folder fullPath() Named scope. Get path with its children. (Warning: root node isn't returned.)
* @method Folder leaf() Named scope. Fills leaf attribute
Expand Down
33 changes: 33 additions & 0 deletions tests/unit/ClosureTableBehaviorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -247,4 +247,37 @@ public function testMixed()
$this->assertEquals(5, $folders[2]->primaryKey);
$this->assertEquals(8, $folders[3]->primaryKey);
}

public function testQuoting()
{
$this->assertEmpty(Folder::model()->findByPk("'"));
$this->assertEmpty(Folder::model()->ancestorsOf("'")->findAll());
$this->assertEmpty(Folder::model()->childrenOf("'")->findAll());
$this->assertEmpty(Folder::model()->parentOf("'")->findAll());
$this->assertEmpty(Folder::model()->deleteNode("'"));
$this->assertEmpty(Folder::model()->descendantsOf("'")->findAll());
$this->assertEmpty(Folder::model()->fullPathOf("'")->findAll());
$this->assertEmpty(Folder::model()->pathOf("'")->findAll());
$this->assertEmpty(Folder::model()->unorderedPathOf("'")->findAll());

/** @var Folder $folder5 */
$folder5 = Folder::model()->findByPk(5);
try {
$folder5->moveTo("'");
$this->fail();
} catch (CDbException $e) {
$this->assertEquals(201, $e->getCode());
}
$newFolder = new Folder();
$newFolder->name = 'Folder';
$this->assertTrue($newFolder->save());
$this->assertEquals(1, $newFolder->appendTo("'"));
try {
Folder::model()->markAsRoot("'");
$this->fail();
} catch (CDbException $e) {
// http://dev.mysql.com/doc/refman/5.5/en/error-messages-server.html
$this->assertEquals('1452', $e->errorInfo[1]);
}
}
}

0 comments on commit 165ee41

Please sign in to comment.