diff --git a/src/Symfony/Component/Form/Extension/Validator/ViolationMapper/ViolationPath.php b/src/Symfony/Component/Form/Extension/Validator/ViolationMapper/ViolationPath.php index 757229d8a3..79a13fac7f 100644 --- a/src/Symfony/Component/Form/Extension/Validator/ViolationMapper/ViolationPath.php +++ b/src/Symfony/Component/Form/Extension/Validator/ViolationMapper/ViolationPath.php @@ -174,6 +174,10 @@ class ViolationPath implements \IteratorAggregate, PropertyPathInterface */ public function getElement($index) { + if (!isset($this->elements[$index])) { + throw new \OutOfBoundsException('The index ' . $index . ' is not within the violation path'); + } + return $this->elements[$index]; } @@ -182,6 +186,10 @@ class ViolationPath implements \IteratorAggregate, PropertyPathInterface */ public function isProperty($index) { + if (!isset($this->isIndex[$index])) { + throw new \OutOfBoundsException('The index ' . $index . ' is not within the violation path'); + } + return !$this->isIndex[$index]; } @@ -190,6 +198,10 @@ class ViolationPath implements \IteratorAggregate, PropertyPathInterface */ public function isIndex($index) { + if (!isset($this->isIndex[$index])) { + throw new \OutOfBoundsException('The index ' . $index . ' is not within the violation path'); + } + return $this->isIndex[$index]; } @@ -208,9 +220,15 @@ class ViolationPath implements \IteratorAggregate, PropertyPathInterface * @param integer $index The element index. * * @return Boolean Whether the element maps to a form. + * + * @throws \OutOfBoundsException If the offset is invalid. */ public function mapsForm($index) { + if (!isset($this->mapsForm[$index])) { + throw new \OutOfBoundsException('The index ' . $index . ' is not within the violation path'); + } + return $this->mapsForm[$index]; } diff --git a/src/Symfony/Component/Form/Tests/Extension/Validator/ViolationMapper/ViolationPathTest.php b/src/Symfony/Component/Form/Tests/Extension/Validator/ViolationMapper/ViolationPathTest.php index f663ce0bad..db64e9cd69 100644 --- a/src/Symfony/Component/Form/Tests/Extension/Validator/ViolationMapper/ViolationPathTest.php +++ b/src/Symfony/Component/Form/Tests/Extension/Validator/ViolationMapper/ViolationPathTest.php @@ -130,4 +130,117 @@ class ViolationPathTest extends \PHPUnit_Framework_TestCase $this->assertEquals($parent, $path->getParent()); } + + public function testGetElement() + { + $path = new ViolationPath('children[address].data[street].name'); + + $this->assertEquals('street', $path->getElement(1)); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testGetElementDoesNotAcceptInvalidIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->getElement(3); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testGetElementDoesNotAcceptNegativeIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->getElement(-1); + } + + public function testIsProperty() + { + $path = new ViolationPath('children[address].data[street].name'); + + $this->assertFalse($path->isProperty(1)); + $this->assertTrue($path->isProperty(2)); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsPropertyDoesNotAcceptInvalidIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->isProperty(3); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsPropertyDoesNotAcceptNegativeIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->isProperty(-1); + } + + public function testIsIndex() + { + $path = new ViolationPath('children[address].data[street].name'); + + $this->assertTrue($path->isIndex(1)); + $this->assertFalse($path->isIndex(2)); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsIndexDoesNotAcceptInvalidIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->isIndex(3); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsIndexDoesNotAcceptNegativeIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->isIndex(-1); + } + + public function testMapsForm() + { + $path = new ViolationPath('children[address].data[street].name'); + + $this->assertTrue($path->mapsForm(0)); + $this->assertFalse($path->mapsForm(1)); + $this->assertFalse($path->mapsForm(2)); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testMapsFormDoesNotAcceptInvalidIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->mapsForm(3); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testMapsFormDoesNotAcceptNegativeIndices() + { + $path = new ViolationPath('children[address].data[street].name'); + + $path->mapsForm(-1); + } } + diff --git a/src/Symfony/Component/Form/Tests/Util/PropertyPathBuilderTest.php b/src/Symfony/Component/Form/Tests/Util/PropertyPathBuilderTest.php index dda7c7821d..0c0424531e 100644 --- a/src/Symfony/Component/Form/Tests/Util/PropertyPathBuilderTest.php +++ b/src/Symfony/Component/Form/Tests/Util/PropertyPathBuilderTest.php @@ -100,6 +100,22 @@ class PropertyPathBuilderTest extends \PHPUnit_Framework_TestCase $this->assertEquals($path, $this->builder->getPropertyPath()); } + /** + * @expectedException \OutOfBoundsException + */ + public function testReplaceByIndexDoesNotAllowInvalidOffsets() + { + $this->builder->replaceByIndex(6, 'new1'); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testReplaceByIndexDoesNotAllowNegativeOffsets() + { + $this->builder->replaceByIndex(-1, 'new1'); + } + public function testReplaceByProperty() { $this->builder->replaceByProperty(1, 'new1'); @@ -109,6 +125,22 @@ class PropertyPathBuilderTest extends \PHPUnit_Framework_TestCase $this->assertEquals($path, $this->builder->getPropertyPath()); } + /** + * @expectedException \OutOfBoundsException + */ + public function testReplaceByPropertyDoesNotAllowInvalidOffsets() + { + $this->builder->replaceByProperty(6, 'new1'); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testReplaceByPropertyDoesNotAllowNegativeOffsets() + { + $this->builder->replaceByProperty(-1, 'new1'); + } + public function testReplace() { $this->builder->replace(1, 1, new PropertyPath('new1[new2].new3')); @@ -118,6 +150,22 @@ class PropertyPathBuilderTest extends \PHPUnit_Framework_TestCase $this->assertEquals($path, $this->builder->getPropertyPath()); } + /** + * @expectedException \OutOfBoundsException + */ + public function testReplaceDoesNotAllowInvalidOffsets() + { + $this->builder->replace(6, 1, new PropertyPath('new1[new2].new3')); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testReplaceDoesNotAllowNegativeOffsets() + { + $this->builder->replace(-1, 1, new PropertyPath('new1[new2].new3')); + } + public function testReplaceWithLengthGreaterOne() { $this->builder->replace(0, 2, new PropertyPath('new1[new2].new3')); @@ -153,4 +201,20 @@ class PropertyPathBuilderTest extends \PHPUnit_Framework_TestCase $this->assertEquals($path, $this->builder->getPropertyPath()); } + + /** + * @expectedException \OutOfBoundsException + */ + public function testRemoveDoesNotAllowInvalidOffsets() + { + $this->builder->remove(6); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testRemoveDoesNotAllowNegativeOffsets() + { + $this->builder->remove(-1); + } } diff --git a/src/Symfony/Component/Form/Tests/Util/PropertyPathTest.php b/src/Symfony/Component/Form/Tests/Util/PropertyPathTest.php index a9779bc429..f231c24f45 100644 --- a/src/Symfony/Component/Form/Tests/Util/PropertyPathTest.php +++ b/src/Symfony/Component/Form/Tests/Util/PropertyPathTest.php @@ -497,4 +497,87 @@ class PropertyPathTest extends \PHPUnit_Framework_TestCase $this->assertEquals($propertyPath, $copy); } + + public function testGetElement() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $this->assertEquals('child', $propertyPath->getElement(2)); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testGetElementDoesNotAcceptInvalidIndices() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $propertyPath->getElement(3); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testGetElementDoesNotAcceptNegativeIndices() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $propertyPath->getElement(-1); + } + + public function testIsProperty() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $this->assertTrue($propertyPath->isProperty(1)); + $this->assertFalse($propertyPath->isProperty(2)); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsPropertyDoesNotAcceptInvalidIndices() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $propertyPath->isProperty(3); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsPropertyDoesNotAcceptNegativeIndices() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $propertyPath->isProperty(-1); + } + + public function testIsIndex() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $this->assertFalse($propertyPath->isIndex(1)); + $this->assertTrue($propertyPath->isIndex(2)); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsIndexDoesNotAcceptInvalidIndices() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $propertyPath->isIndex(3); + } + + /** + * @expectedException \OutOfBoundsException + */ + public function testIsIndexDoesNotAcceptNegativeIndices() + { + $propertyPath = new PropertyPath('grandpa.parent[child]'); + + $propertyPath->isIndex(-1); + } } diff --git a/src/Symfony/Component/Form/Util/PropertyPath.php b/src/Symfony/Component/Form/Util/PropertyPath.php index 3443036fe2..d4d6aa7034 100644 --- a/src/Symfony/Component/Form/Util/PropertyPath.php +++ b/src/Symfony/Component/Form/Util/PropertyPath.php @@ -212,6 +212,10 @@ class PropertyPath implements \IteratorAggregate, PropertyPathInterface */ public function getElement($index) { + if (!isset($this->elements[$index])) { + throw new \OutOfBoundsException('The index ' . $index . ' is not within the property path'); + } + return $this->elements[$index]; } @@ -220,6 +224,10 @@ class PropertyPath implements \IteratorAggregate, PropertyPathInterface */ public function isProperty($index) { + if (!isset($this->isIndex[$index])) { + throw new \OutOfBoundsException('The index ' . $index . ' is not within the property path'); + } + return !$this->isIndex[$index]; } @@ -228,6 +236,10 @@ class PropertyPath implements \IteratorAggregate, PropertyPathInterface */ public function isIndex($index) { + if (!isset($this->isIndex[$index])) { + throw new \OutOfBoundsException('The index ' . $index . ' is not within the property path'); + } + return $this->isIndex[$index]; } diff --git a/src/Symfony/Component/Form/Util/PropertyPathBuilder.php b/src/Symfony/Component/Form/Util/PropertyPathBuilder.php index d97a01126d..ed0e5a263a 100644 --- a/src/Symfony/Component/Form/Util/PropertyPathBuilder.php +++ b/src/Symfony/Component/Form/Util/PropertyPathBuilder.php @@ -92,6 +92,10 @@ class PropertyPathBuilder */ public function remove($offset, $length = 1) { + if (!isset($this->elements[$offset])) { + throw new \OutOfBoundsException('The offset ' . $offset . ' is not within the property path'); + } + $this->resize($offset, $length, 0); } @@ -105,9 +109,15 @@ class PropertyPathBuilder * starts in $path. * @param integer $pathLength The length of the inserted piece. * If 0, the full path is inserted. + * + * @throws \OutOfBoundsException If the offset is invalid. */ public function replace($offset, $length, PropertyPathInterface $path, $pathOffset = 0, $pathLength = 0) { + if (!isset($this->elements[$offset])) { + throw new \OutOfBoundsException('The offset ' . $offset . ' is not within the property path'); + } + if (0 === $pathLength) { $pathLength = $path->getLength() - $pathOffset; } @@ -125,9 +135,15 @@ class PropertyPathBuilder * * @param integer $offset The offset at which to replace. * @param string $name The inserted index name. + * + * @throws \OutOfBoundsException If the offset is invalid. */ public function replaceByIndex($offset, $name) { + if (!isset($this->elements[$offset])) { + throw new \OutOfBoundsException('The offset ' . $offset . ' is not within the property path'); + } + $this->elements[$offset] = $name; $this->isIndex[$offset] = true; } @@ -137,9 +153,15 @@ class PropertyPathBuilder * * @param integer $offset The offset at which to replace. * @param string $name The inserted property name. + * + * @throws \OutOfBoundsException If the offset is invalid. */ public function replaceByProperty($offset, $name) { + if (!isset($this->elements[$offset])) { + throw new \OutOfBoundsException('The offset ' . $offset . ' is not within the property path'); + } + $this->elements[$offset] = $name; $this->isIndex[$offset] = false; } diff --git a/src/Symfony/Component/Form/Util/PropertyPathInterface.php b/src/Symfony/Component/Form/Util/PropertyPathInterface.php index da803e798d..8231ce7307 100644 --- a/src/Symfony/Component/Form/Util/PropertyPathInterface.php +++ b/src/Symfony/Component/Form/Util/PropertyPathInterface.php @@ -63,6 +63,8 @@ interface PropertyPathInterface extends \Traversable * @param integer $index The index key * * @return string A property or index name + * + * @throws \OutOfBoundsException If the offset is invalid. */ function getElement($index); @@ -72,6 +74,8 @@ interface PropertyPathInterface extends \Traversable * @param integer $index The index in the property path * * @return Boolean Whether the element at this index is a property + * + * @throws \OutOfBoundsException If the offset is invalid. */ function isProperty($index); @@ -81,6 +85,8 @@ interface PropertyPathInterface extends \Traversable * @param integer $index The index in the property path * * @return Boolean Whether the element at this index is an array index + * + * @throws \OutOfBoundsException If the offset is invalid. */ function isIndex($index); }