From 4c26f81a9b24ecf6d15bdfaf7dcda42e1be54b27 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?K=C3=A9vin=20Gomez?= Date: Sat, 14 Dec 2013 12:12:35 +0000 Subject: [PATCH] Ported all acl-related remaining tests --- Security/Acl/Domain/Acl.php | 6 +- Security/Acl/MutableAclProvider.php | 2 +- Tests/Fixtures/Acl/ArrayCache.php | 60 ++++ Tests/Security/Acl/AclProviderTest.php | 261 ++++++++++++++ .../Security/Acl/AuditableAclProviderTest.php | 85 +++++ Tests/Security/Acl/Domain/AclTest.php | 206 +++++++++++ .../Security/Acl/Domain/AuditableAclTest.php | 212 ++++++++++++ Tests/Security/Acl/Domain/EntryTest.php | 70 ++++ Tests/Security/Acl/Domain/FieldEntryTest.php | 73 ++++ Tests/Security/Acl/Domain/MutableAclTest.php | 276 +++++++++++++++ Tests/Security/Acl/MutableAclProviderTest.php | 321 ++++++++++++++++++ 11 files changed, 1568 insertions(+), 4 deletions(-) create mode 100644 Tests/Fixtures/Acl/ArrayCache.php create mode 100644 Tests/Security/Acl/AclProviderTest.php create mode 100644 Tests/Security/Acl/AuditableAclProviderTest.php create mode 100644 Tests/Security/Acl/Domain/AclTest.php create mode 100644 Tests/Security/Acl/Domain/AuditableAclTest.php create mode 100644 Tests/Security/Acl/Domain/EntryTest.php create mode 100644 Tests/Security/Acl/Domain/FieldEntryTest.php create mode 100644 Tests/Security/Acl/Domain/MutableAclTest.php create mode 100644 Tests/Security/Acl/MutableAclProviderTest.php diff --git a/Security/Acl/Domain/Acl.php b/Security/Acl/Domain/Acl.php index 01cf057..37d60e8 100644 --- a/Security/Acl/Domain/Acl.php +++ b/Security/Acl/Domain/Acl.php @@ -26,7 +26,7 @@ use Symfony\Component\Security\Acl\Model\SecurityIdentityInterface; */ class Acl implements AclInterface { - protected $model = 'Propel\PropelBundle\Model\Acl\Entry'; + protected $model = '\Propel\PropelBundle\Model\Acl\Entry'; protected $classAces = array(); protected $classFieldAces = array(); @@ -59,8 +59,8 @@ class Acl implements AclInterface */ public function __construct(ObjectCollection $entries, ObjectIdentityInterface $objectIdentity, PermissionGrantingStrategyInterface $permissionGrantingStrategy, array $loadedSecurityIdentities = array(), AclInterface $parentAcl = null, $inherited = true) { - if ($entries->getModel() !== $this->model) { - throw new AclException(sprintf('The given collection does not contain models of class "%s" but of class "%s".', $this->model, $entries->getModel())); + if ($entries->getFullyQualifiedModel() !== $this->model) { + throw new AclException(sprintf('The given collection does not contain models of class "%s" but of class "%s".', $this->model, $entries->getFullyQualifiedModel())); } foreach ($entries as $eachEntry) { diff --git a/Security/Acl/MutableAclProvider.php b/Security/Acl/MutableAclProvider.php index 651e0ed..67cdc17 100644 --- a/Security/Acl/MutableAclProvider.php +++ b/Security/Acl/MutableAclProvider.php @@ -190,7 +190,7 @@ class MutableAclProvider extends AclProvider implements MutableAclProviderInterf ); } - foreach ($modelEntries as &$eachEntry) { + foreach ($modelEntries as $eachEntry) { if (!in_array($eachEntry->getId(), $keepEntries)) { $eachEntry->delete($this->connection); } diff --git a/Tests/Fixtures/Acl/ArrayCache.php b/Tests/Fixtures/Acl/ArrayCache.php new file mode 100644 index 0000000..0a74dd1 --- /dev/null +++ b/Tests/Fixtures/Acl/ArrayCache.php @@ -0,0 +1,60 @@ +content[$primaryKey])) { + unset($this->content[$primaryKey]); + } + } + + public function evictFromCacheByIdentity(ObjectIdentityInterface $oid) + { + // Propel ACL does not make use of those. + } + + public function getFromCacheById($primaryKey) + { + if (isset($this->content[$primaryKey])) { + return $this->content[$primaryKey]; + } + + return null; + } + + public function getFromCacheByIdentity(ObjectIdentityInterface $oid) + { + // Propel ACL does not make use of those. + } + + public function putInCache(AclInterface $acl) + { + if (null === $acl->getId()) { + throw new \InvalidArgumentException('The given ACL does not have an ID.'); + } + + $this->content[$acl->getId()] = $acl; + } + + public function clearCache() + { + $this->content = array(); + } +} diff --git a/Tests/Security/Acl/AclProviderTest.php b/Tests/Security/Acl/AclProviderTest.php new file mode 100644 index 0000000..cd7e223 --- /dev/null +++ b/Tests/Security/Acl/AclProviderTest.php @@ -0,0 +1,261 @@ + + */ +class AclProviderTest extends AclTestCase +{ + public function testFindAclNoneGiven() + { + $provider = $this->getAclProvider(); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\AclNotFoundException', 'There is no ACL available for this object identity. Please create one using the MutableAclProvider.'); + $provider->findAcl($this->getAclObjectIdentity()); + } + + public function testFindAclNoneGivenFilterSecurityIdentity() + { + $provider = $this->getAclProvider(); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\AclNotFoundException', 'There is at least no ACL for this object identity and the given security identities. Try retrieving the ACL without security identity filter and add ACEs for the security identities.'); + $provider->findAcl($this->getAclObjectIdentity(), array($this->getRoleSecurityIdentity())); + } + + public function testFindAclWithEntries() + { + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($obj->getAclClass()) + ->setMask(64) + ; + $obj->addEntry($entry)->save($this->con); + + $acl = $this->getAclProvider()->findAcl($this->getAclObjectIdentity(1), array($this->getRoleSecurityIdentity('ROLE_USER'))); + + $this->assertNotEmpty($acl); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Acl', $acl); + + $this->assertEmpty($acl->getFields()); + $this->assertEmpty($acl->getClassAces()); + $this->assertNotEmpty($acl->getObjectAces()); + $this->assertCount(1, $acl->getObjectAces()); + + $this->assertNull($acl->getParentAcl()); + $this->assertTrue($acl->isEntriesInheriting()); + + $this->assertFalse($acl->isSidLoaded($this->getRoleSecurityIdentity('ROLE_ADMIN'))); + $this->assertTrue($acl->isSidLoaded($this->getRoleSecurityIdentity('ROLE_USER'))); + + $this->assertTrue($acl->isGranted(array(1, 2, 4, 8, 16, 32, 64), array($this->getRoleSecurityIdentity('ROLE_USER')))); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\NoAceFoundException'); + $acl->isGranted(array(128), array($this->getRoleSecurityIdentity('ROLE_USER'))); + } + + /** + * @depends testFindAclWithEntries + */ + public function testFindAclWithParent() + { + $parent = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($parent->getAclClass()) + ->setMask(128) + ; + $parent->addEntry($entry)->save($this->con); + + $obj = $this->createModelObjectIdentity(2); + $obj->setObjectIdentityRelatedByParentObjectIdentityId($parent); + + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($obj->getAclClass()) + ->setMask(64) + ; + $obj->addEntry($entry)->save($this->con); + + $acl = $this->getAclProvider()->findAcl($this->getAclObjectIdentity(2), array($this->getRoleSecurityIdentity('ROLE_USER'))); + $parent = $acl->getParentAcl(); + + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Acl', $acl); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Acl', $parent); + + $aces = $acl->getObjectAces(); + $parentAces = $parent->getObjectAces(); + $this->assertEquals(64, $aces[0]->getMask()); + $this->assertEquals(128, $parentAces[0]->getMask()); + } + + /** + * @depends testFindAclWithEntries + */ + public function testFindAcls() + { + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($obj->getAclClass()) + ; + $obj->addEntry($entry)->save($this->con); + + $aclObj = $this->getAclObjectIdentity(1); + + $acls = $this->getAclProvider()->findAcls(array($aclObj), array($this->getRoleSecurityIdentity('ROLE_USER'))); + $acl = $this->getAclProvider()->findAcl($aclObj, array($this->getRoleSecurityIdentity('ROLE_USER'))); + + $this->assertNotEmpty($acls); + $this->assertCount(1, $acls); + $this->assertTrue($acls->contains($aclObj)); + $this->assertEquals($acl, $acls[$aclObj]); + } + + public function testFindChildrenParentNotExists() + { + $this->assertEmpty($this->getAclProvider()->findChildren(new ObjectIdentity(5, 'Book'))); + } + + /** + * @depends testFindAclWithEntries + */ + public function testFindChildrenWithoutChildren() + { + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($obj->getAclClass()) + ->setMask(64) + ; + $obj->addEntry($entry)->save($this->con); + + $childrenAcl = $this->getAclProvider()->findChildren($this->getAclObjectIdentity(1)); + $this->assertEmpty($childrenAcl); + } + + public function testFindChildrenDirectOnly() + { + list($parentObj, $obj, $childObj) = $this->createObjectIdentities(); + + $obj->setObjectIdentityRelatedByParentObjectIdentityId($parentObj)->save($this->con); + $childObj->setObjectIdentityRelatedByParentObjectIdentityId($obj)->save($this->con); + + $children = $this->getAclProvider()->findChildren($this->getAclObjectIdentity(1), true); + + $this->assertNotEmpty($children); + $this->assertCount(1, $children); + $this->assertEquals(2, $children[0]->getIdentifier()); + } + + public function testFindChildrenWithGrandChildren() + { + list($parentObj, $obj, $childObj) = $this->createObjectIdentities(); + + $obj->setObjectIdentityRelatedByParentObjectIdentityId($parentObj)->save($this->con); + $childObj->setObjectIdentityRelatedByParentObjectIdentityId($obj)->save($this->con); + + $children = $this->getAclProvider()->findChildren($this->getAclObjectIdentity(1)); + + $this->assertNotEmpty($children); + $this->assertCount(2, $children); + $this->assertEquals(2, $children[0]->getIdentifier()); + $this->assertEquals(3, $children[1]->getIdentifier()); + } + + protected function createObjectIdentities() + { + $parentObj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($parentObj->getAclClass()) + ->setMask(64) + ; + $parentObj->addEntry($entry)->save($this->con); + + $obj = $this->createModelObjectIdentity(2); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($obj->getAclClass()) + ->setMask(64) + ; + $obj->addEntry($entry)->save($this->con); + + $childObj = $this->createModelObjectIdentity(3); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($childObj->getAclClass()) + ->setMask(64) + ; + $childObj->addEntry($entry)->save($this->con); + + return array($parentObj, $obj, $childObj); + } + + /** + * @depends testFindAclWithEntries + */ + public function testFindAclReadsFromCache() + { + $this->cache = new AclCache(); + + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_USER'))) + ->setAclClass($obj->getAclClass()) + ->setMask(64) + ; + $obj->addEntry($entry)->save($this->con); + + // Read and put into cache + $acl = $this->getAclProvider()->findAcl($this->getAclObjectIdentity(1), array($this->getRoleSecurityIdentity('ROLE_USER'))); + $this->cache->content[1] = $acl; + + // Change database + EntryQuery::create()->update(array(EntryTableMap::translateFieldName(EntryTableMap::MASK, TableMap::TYPE_COLNAME, TableMap::TYPE_PHPNAME) => 128), $this->con); + $this->assertEquals(0, EntryQuery::create()->filterByMask(64)->count($this->con)); + + // Verify cache has been read + $cachedAcl = $this->getAclProvider()->findAcl($this->getAclObjectIdentity(1), array($this->getRoleSecurityIdentity('ROLE_USER'))); + $cachedObjectAces = $cachedAcl->getObjectAces(); + $this->assertSame($acl, $cachedAcl); + $this->assertEquals(64, $cachedObjectAces[0]->getMask()); + } + + protected function getAclProvider() + { + return new AclProvider(new PermissionGrantingStrategy(), $this->con, $this->cache); + } +} diff --git a/Tests/Security/Acl/AuditableAclProviderTest.php b/Tests/Security/Acl/AuditableAclProviderTest.php new file mode 100644 index 0000000..6e22e56 --- /dev/null +++ b/Tests/Security/Acl/AuditableAclProviderTest.php @@ -0,0 +1,85 @@ + + */ +class AuditableAclProviderTest extends AclTestCase +{ + public function testCreateAcl() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + + $this->assertNotEmpty($acl); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\AuditableAcl', $acl); + $this->assertEquals(1, $acl->getId()); + } + + /** + * @depends testCreateAcl + */ + public function testUpdatePersistsAuditing() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $this->getAclProvider()->updateAcl($acl); + + $entries = EntryQuery::create()->find($this->con); + $this->assertCount(1, $entries); + // default values + $this->assertFalse($entries[0]->getAuditSuccess()); + $this->assertTrue($entries[0]->getAuditFailure()); + + $acl->updateObjectAuditing(0, true, true); + $this->getAclProvider()->updateAcl($acl); + + $entries = EntryQuery::create()->find($this->con); + $this->assertCount(1, $entries); + $this->assertTrue($entries[0]->getAuditSuccess()); + $this->assertTrue($entries[0]->getAuditFailure()); + + $acl->updateObjectAuditing(0, false, true); + $this->getAclProvider()->updateAcl($acl); + + $entries = EntryQuery::create()->find($this->con); + $this->assertCount(1, $entries); + $this->assertFalse($entries[0]->getAuditSuccess()); + $this->assertTrue($entries[0]->getAuditFailure()); + + $acl->updateObjectAuditing(0, true, false); + $this->getAclProvider()->updateAcl($acl); + + $entries = EntryQuery::create()->find($this->con); + $this->assertCount(1, $entries); + $this->assertTrue($entries[0]->getAuditSuccess()); + $this->assertFalse($entries[0]->getAuditFailure()); + + $acl->updateObjectAuditing(0, false, false); + $this->getAclProvider()->updateAcl($acl); + + $entries = EntryQuery::create()->find($this->con); + $this->assertCount(1, $entries); + $this->assertFalse($entries[0]->getAuditSuccess()); + $this->assertFalse($entries[0]->getAuditFailure()); + } + + protected function getAclProvider() + { + return new AuditableAclProvider(new PermissionGrantingStrategy(), $this->con); + } +} diff --git a/Tests/Security/Acl/Domain/AclTest.php b/Tests/Security/Acl/Domain/AclTest.php new file mode 100644 index 0000000..33e5cb3 --- /dev/null +++ b/Tests/Security/Acl/Domain/AclTest.php @@ -0,0 +1,206 @@ + + */ +class AclTest extends AclTestCase +{ + public function testConstructorInvalidCollection() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\AclClass'); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\Exception'); + new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + } + + public function testConstructorEmptyCollection() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $aclObj = $this->getAclObjectIdentity(); + $acl = new Acl($collection, $aclObj, new PermissionGrantingStrategy()); + + $this->assertEmpty($acl->getClassAces()); + $this->assertEmpty($acl->getObjectAces()); + $this->assertEmpty($acl->getFields()); + $this->assertNull($acl->getParentAcl()); + $this->assertSame($aclObj, $acl->getObjectIdentity()); + $this->assertTrue($acl->isEntriesInheriting()); + } + + /** + * @depends testConstructorEmptyCollection + */ + public function testConstructorWithAces() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $obj = $this->createModelObjectIdentity(1); + + // object based ACE + $entry = $this->createEntry(); + $entry + ->setObjectIdentity($obj) + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + // object field based ACE + $entry = $this->createEntry(); + $entry + ->setObjectIdentity($obj) + ->setFieldName('name') + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + // class based ACE + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + // class field based ACE + $entry = $this->createEntry(); + $entry + ->setFieldName('name') + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + $this->assertNotEmpty($acl->getClassAces()); + $this->assertNotEmpty($acl->getObjectAces()); + $this->assertEquals(array('name'), $acl->getFields()); + $this->assertNotEmpty($acl->getClassFieldAces('name')); + $this->assertNotEmpty($acl->getObjectFieldAces('name')); + + $classAces = $acl->getClassAces(); + $objectAces = $acl->getObjectAces(); + $classFieldAces = $acl->getClassFieldAces('name'); + $objectFieldAces = $acl->getObjectFieldAces('name'); + + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Entry', $classAces[0]); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Entry', $objectAces[0]); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\FieldEntry', $classFieldAces[0]); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\FieldEntry', $objectFieldAces[0]); + + $this->assertSame($acl, $classAces[0]->getAcl()); + $this->assertSame($acl, $objectAces[0]->getAcl()); + $this->assertSame($acl, $classFieldAces[0]->getAcl()); + $this->assertSame($acl, $objectFieldAces[0]->getAcl()); + + $this->assertEquals('name', $classFieldAces[0]->getField()); + $this->assertEquals('name', $objectFieldAces[0]->getField()); + } + + public function testIsSidLoadedNoneLoaded() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $this->assertFalse($acl->isSidLoaded($this->getRoleSecurityIdentity())); + } + + public function testIsSidLoadedInvalid() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $aclObj = $this->getAclObjectIdentity(); + $acl = new Acl($collection, $aclObj, new PermissionGrantingStrategy()); + + $this->setExpectedException('InvalidArgumentException'); + $acl->isSidLoaded('foo'); + } + + public function testIsGrantedNoAces() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\NoAceFoundException'); + $acl->isGranted(array(64), array($this->getRoleSecurityIdentity())); + } + + public function testIsGrantedNoMatchingSecurityIdentity() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_ADMIN'))) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\NoAceFoundException'); + $acl->isGranted(array(64), array($this->getRoleSecurityIdentity('ROLE_USER'))); + } + + public function testIsFieldGrantedNoAces() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\NoAceFoundException'); + $acl->isFieldGranted('name', array(64), array($this->getRoleSecurityIdentity())); + } + + public function testSerializeUnserialize() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_ADMIN'))) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + $serialized = serialize($acl); + $unserialized = unserialize($serialized); + + $this->assertNotEmpty($serialized); + $this->assertNotEmpty($unserialized); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Acl', $unserialized); + $this->assertEquals($serialized, serialize($unserialized)); + } +} diff --git a/Tests/Security/Acl/Domain/AuditableAclTest.php b/Tests/Security/Acl/Domain/AuditableAclTest.php new file mode 100644 index 0000000..00de69f --- /dev/null +++ b/Tests/Security/Acl/Domain/AuditableAclTest.php @@ -0,0 +1,212 @@ + + */ +class AuditableAclTest extends AclTestCase +{ + public function testUpdateAuditingInvalidIndex() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $acl = new AuditableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $this->setExpectedException('OutOfBoundsException'); + $acl->updateObjectAuditing(0, false, false); + } + + public function testUpdateAuditingInvalidField() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setObjectIdentity($obj) + ->setFieldName('name') + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + $acl = new AuditableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $this->setExpectedException('InvalidArgumentException'); + $acl->updateObjectFieldAuditing(0, 'foo', false, false); + } + + public function testUpdateAuditingInvalidFlag() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setObjectIdentity($obj) + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + $acl = new AuditableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $this->setExpectedException('InvalidArgumentException'); + $acl->updateObjectAuditing(0, 'foo', 'bar'); + } + + public function testUpdateObjectAuditing() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setObjectIdentity($obj) + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + $acl = new AuditableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $aces = $acl->getObjectAces(); + $this->assertCount(1, $aces); + + $acl->updateObjectAuditing(0, true, true); + $aces = $acl->getObjectAces(); + $this->assertTrue($aces[0]->isAuditSuccess()); + $this->assertTrue($aces[0]->isAuditFailure()); + + $acl->updateObjectAuditing(0, false, true); + $aces = $acl->getObjectAces(); + $this->assertFalse($aces[0]->isAuditSuccess()); + $this->assertTrue($aces[0]->isAuditFailure()); + + $acl->updateObjectAuditing(0, true, false); + $aces = $acl->getObjectAces(); + $this->assertTrue($aces[0]->isAuditSuccess()); + $this->assertFalse($aces[0]->isAuditFailure()); + + $acl->updateObjectAuditing(0, false, false); + $aces = $acl->getObjectAces(); + $this->assertFalse($aces[0]->isAuditSuccess()); + $this->assertFalse($aces[0]->isAuditFailure()); + } + + /** + * @depends testUpdateObjectAuditing + */ + public function testUpdateObjectFieldAuditing() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $obj = $this->createModelObjectIdentity(1); + $entry = $this->createEntry(); + $entry + ->setFieldName('name') + ->setObjectIdentity($obj) + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new AuditableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $aces = $acl->getObjectFieldAces('name'); + $this->assertCount(1, $aces); + + $acl->updateObjectFieldAuditing(0, 'name', true, true); + $aces = $acl->getObjectFieldAces('name'); + $this->assertTrue($aces[0]->isAuditSuccess()); + $this->assertTrue($aces[0]->isAuditFailure()); + + $acl->updateObjectFieldAuditing(0, 'name', false, false); + $aces = $acl->getObjectFieldAces('name'); + $this->assertFalse($aces[0]->isAuditSuccess()); + $this->assertFalse($aces[0]->isAuditFailure()); + } + + /** + * @depends testUpdateObjectAuditing + */ + public function testUpdateClassAuditing() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new AuditableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $aces = $acl->getClassAces(); + $this->assertCount(1, $aces); + + $acl->updateClassAuditing(0, true, true); + $aces = $acl->getClassAces('name'); + $this->assertTrue($aces[0]->isAuditSuccess()); + $this->assertTrue($aces[0]->isAuditFailure()); + + $acl->updateClassAuditing(0, false, false); + $aces = $acl->getClassAces(); + $this->assertFalse($aces[0]->isAuditSuccess()); + $this->assertFalse($aces[0]->isAuditFailure()); + } + + /** + * @depends testUpdateObjectAuditing + */ + public function testUpdateClassFieldAuditing() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $entry = $this->createEntry(); + $entry + ->setFieldName('name') + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new AuditableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $aces = $acl->getClassFieldAces('name'); + $this->assertCount(1, $aces); + + $acl->updateClassFieldAuditing(0, 'name', true, true); + $aces = $acl->getClassFieldAces('name'); + $this->assertTrue($aces[0]->isAuditSuccess()); + $this->assertTrue($aces[0]->isAuditFailure()); + + $acl->updateClassFieldAuditing(0, 'name', false, false); + $aces = $acl->getClassFieldAces('name'); + $this->assertFalse($aces[0]->isAuditSuccess()); + $this->assertFalse($aces[0]->isAuditFailure()); + } +} diff --git a/Tests/Security/Acl/Domain/EntryTest.php b/Tests/Security/Acl/Domain/EntryTest.php new file mode 100644 index 0000000..c35e7bb --- /dev/null +++ b/Tests/Security/Acl/Domain/EntryTest.php @@ -0,0 +1,70 @@ + + */ +class EntryTest extends AclTestCase +{ + public function testConstruct() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $model = $this->createEntry(); + $model->setAuditFailure(true); + $model->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())); + + $entry = new Entry($model, $acl); + + $this->assertEquals($model->getMask(), $entry->getMask()); + $this->assertEquals($model->getGranting(), $entry->isGranting()); + $this->assertEquals($model->getGrantingStrategy(), $entry->getStrategy()); + $this->assertEquals($model->getAuditFailure(), $entry->isAuditFailure()); + $this->assertEquals($model->getAuditSuccess(), $entry->isAuditSuccess()); + $this->assertEquals($this->getRoleSecurityIdentity(), $entry->getSecurityIdentity()); + + return $entry; + } + + /** + * @depends testConstruct + */ + public function testSerializeUnserialize(Entry $entry) + { + $serialized = serialize($entry); + $unserialized = unserialize($serialized); + + $this->assertNotEmpty($serialized); + $this->assertNotEmpty($unserialized); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Entry', $unserialized); + + $this->assertEquals($entry->getMask(), $unserialized->getMask()); + $this->assertEquals($entry->isGranting(), $unserialized->isGranting()); + $this->assertEquals($entry->getStrategy(), $unserialized->getStrategy()); + $this->assertEquals($entry->isAuditFailure(), $unserialized->isAuditFailure()); + $this->assertEquals($entry->isAuditSuccess(), $unserialized->isAuditSuccess()); + $this->assertEquals($entry->getSecurityIdentity(), $unserialized->getSecurityIdentity()); + + $this->assertEquals($serialized, serialize($unserialized)); + } +} diff --git a/Tests/Security/Acl/Domain/FieldEntryTest.php b/Tests/Security/Acl/Domain/FieldEntryTest.php new file mode 100644 index 0000000..b9257b2 --- /dev/null +++ b/Tests/Security/Acl/Domain/FieldEntryTest.php @@ -0,0 +1,73 @@ + + */ +class FieldEntryTest extends AclTestCase +{ + public function testConstruct() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + $acl = new Acl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + + $model = $this->createEntry(); + $model->setFieldName('name'); + $model->setAuditFailure(true); + $model->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity())); + + $entry = new FieldEntry($model, $acl); + + $this->assertEquals($model->getMask(), $entry->getMask()); + $this->assertEquals($model->getGranting(), $entry->isGranting()); + $this->assertEquals($model->getGrantingStrategy(), $entry->getStrategy()); + $this->assertEquals($model->getAuditFailure(), $entry->isAuditFailure()); + $this->assertEquals($model->getAuditSuccess(), $entry->isAuditSuccess()); + $this->assertEquals($model->getFieldName(), $entry->getField()); + $this->assertEquals($this->getRoleSecurityIdentity(), $entry->getSecurityIdentity()); + + return $entry; + } + + /** + * @depends testConstruct + */ + public function testSerializeUnserialize(FieldEntry $entry) + { + $serialized = serialize($entry); + $unserialized = unserialize($serialized); + + $this->assertNotEmpty($serialized); + $this->assertNotEmpty($unserialized); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\FieldEntry', $unserialized); + + $this->assertEquals($entry->getMask(), $unserialized->getMask()); + $this->assertEquals($entry->isGranting(), $unserialized->isGranting()); + $this->assertEquals($entry->getStrategy(), $unserialized->getStrategy()); + $this->assertEquals($entry->isAuditFailure(), $unserialized->isAuditFailure()); + $this->assertEquals($entry->isAuditSuccess(), $unserialized->isAuditSuccess()); + $this->assertEquals($entry->getSecurityIdentity(), $unserialized->getSecurityIdentity()); + $this->assertEquals($entry->getField(), $unserialized->getField()); + + $this->assertEquals($serialized, serialize($unserialized)); + } +} diff --git a/Tests/Security/Acl/Domain/MutableAclTest.php b/Tests/Security/Acl/Domain/MutableAclTest.php new file mode 100644 index 0000000..1bae03c --- /dev/null +++ b/Tests/Security/Acl/Domain/MutableAclTest.php @@ -0,0 +1,276 @@ + + */ +class MutableAclTest extends AclTestCase +{ + public function testConstructorInvalidCollection() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\AclClass'); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\Exception'); + new MutableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy(), array(), null, false, $this->con); + } + + public function testConstructorEmptyCollection() + { + $acl = $this->createEmptyAcl(1, array(), null, false); + + $this->assertEquals(1, $acl->getId()); + $this->assertEmpty($acl->getClassAces()); + $this->assertEmpty($acl->getObjectAces()); + $this->assertEmpty($acl->getFields()); + $this->assertNull($acl->getParentAcl()); + $this->assertFalse($acl->isEntriesInheriting()); + } + + /** + * @depends testConstructorEmptyCollection + */ + public function testSetUnsetParentAcl() + { + $parentAcl = $this->createEmptyAcl(1); + $acl = $this->createEmptyAcl(2); + + $acl->setParentAcl($parentAcl); + $acl->setEntriesInheriting(true); + + $this->assertSame($parentAcl, $acl->getParentAcl()); + $this->assertTrue($acl->isEntriesInheriting()); + $this->assertEquals(1, $acl->getParentAcl()->getId()); + + $acl->setParentAcl(null); + $this->assertNull($acl->getParentAcl()); + } + + public function testInsertAceInvalidMask() + { + $acl = $this->createEmptyAcl(); + $this->setExpectedException('InvalidArgumentException', 'The given mask is not valid. Please provide an integer.'); + $acl->insertClassAce($this->getRoleSecurityIdentity(), 'foo'); + } + + public function testInsertAceOutofBounds() + { + $acl = $this->createEmptyAcl(); + $this->setExpectedException('OutOfBoundsException', 'The index must be in the interval [0, 0].'); + $acl->insertClassAce($this->getRoleSecurityIdentity(), 64, 1); + } + + public function insertAceProvider() + { + return array( + array('ClassAce'), + array('ClassFieldAce', 'name'), + array('ObjectAce'), + array('ObjectFieldAce', 'name'), + ); + } + + /** + * @dataProvider insertAceProvider + */ + public function testInsertFirstAce($type, $field = null) + { + $acl = $this->createEmptyAcl(); + + if (null !== $field) { + $acl->{'insert'.$type}($field, $this->getRoleSecurityIdentity(), 64); + $aces = $acl->{'get'.$type.'s'}($field); + } else { + $acl->{'insert'.$type}($this->getRoleSecurityIdentity(), 64); + $aces = $acl->{'get'.$type.'s'}(); + } + + $this->assertNotEmpty($aces); + $this->assertCount(1, $aces); + $this->assertEquals($this->getRoleSecurityIdentity(), $aces[0]->getSecurityIdentity()); + $this->assertEquals(64, $aces[0]->getMask()); + $this->assertTrue($aces[0]->isGranting()); + $this->assertNull($aces[0]->getId()); + $this->assertEquals('all', $aces[0]->getStrategy()); + + if (null !== $field) { + $this->assertEquals($field, $aces[0]->getField()); + } + } + + public function testUpdateAceInvalidIndex() + { + $acl = $this->createEmptyAcl(); + $this->setExpectedException('OutOfBoundsException'); + $acl->updateClassAce(0, 64); + } + + /** + * @depends testInsertFirstAce + */ + public function testUpdateFieldAceInvalidField() + { + $acl = $this->createEmptyAcl(); + $acl->insertClassAce($this->getRoleSecurityIdentity(), 64); + + $this->setExpectedException('InvalidArgumentException', 'The given field "name" does not exist.'); + $acl->updateClassFieldAce(0, 'name', 128); + } + + /** + * @depends testInsertFirstAce + */ + public function testInsertUpdateDelete() + { + $secIdentity = $this->getRoleSecurityIdentity(); + + $acl = $this->createEmptyAcl(); + + // insert + + $acl->insertClassAce($secIdentity, 64); + $acl->insertClassFieldAce('name', $secIdentity, 32); + $acl->insertObjectAce($secIdentity, 128); + $acl->insertObjectFieldAce('name', $secIdentity, 16, 0, false); + + $classAces = $acl->getClassAces(); + $classFieldAces = $acl->getClassFieldAces('name'); + $objectAces = $acl->getObjectAces(); + $objectFieldAces = $acl->getObjectFieldAces('name'); + + $this->assertCount(1, $classAces); + $this->assertCount(1, $classFieldAces); + $this->assertCount(1, $objectAces); + $this->assertCount(1, $objectFieldAces); + $this->assertEquals(array('name'), $acl->getFields()); + + $this->assertEquals(64, $classAces[0]->getMask()); + $this->assertEquals(32, $classFieldAces[0]->getMask()); + $this->assertEquals(128, $objectAces[0]->getMask()); + $this->assertEquals(16, $objectFieldAces[0]->getMask()); + + $this->assertEquals('all', $classAces[0]->getStrategy()); + $this->assertEquals('all', $classFieldAces[0]->getStrategy()); + $this->assertEquals('all', $objectAces[0]->getStrategy()); + $this->assertEquals('any', $objectFieldAces[0]->getStrategy()); + + $this->assertFalse($objectFieldAces[0]->isGranting()); + + // update + + $acl->updateClassAce(0, 256); + $acl->updateClassFieldAce(0, 'name', 128, 'any'); + $acl->updateObjectAce(0, 64, 'equal'); + $acl->updateObjectFieldAce(0, 'name', 32, 'all'); + + $this->assertCount(1, $classAces); + $this->assertCount(1, $classFieldAces); + $this->assertCount(1, $objectAces); + $this->assertCount(1, $objectFieldAces); + + $classAces = $acl->getClassAces(); + $classFieldAces = $acl->getClassFieldAces('name'); + $objectAces = $acl->getObjectAces(); + $objectFieldAces = $acl->getObjectFieldAces('name'); + + $this->assertEquals(256, $classAces[0]->getMask()); + $this->assertEquals(128, $classFieldAces[0]->getMask()); + $this->assertEquals(64, $objectAces[0]->getMask()); + $this->assertEquals(32, $objectFieldAces[0]->getMask()); + + $this->assertEquals('all', $classAces[0]->getStrategy()); + $this->assertEquals('any', $classFieldAces[0]->getStrategy()); + $this->assertEquals('equal', $objectAces[0]->getStrategy()); + $this->assertEquals('all', $objectFieldAces[0]->getStrategy()); + + // delete + + $acl->deleteClassAce(0); + $acl->deleteClassFieldAce(0, 'name'); + $acl->deleteObjectAce(0); + $acl->deleteObjectFieldAce(0, 'name'); + + $classAces = $acl->getClassAces(); + $classFieldAces = $acl->getClassFieldAces('name'); + $objectAces = $acl->getObjectAces(); + $objectFieldAces = $acl->getObjectFieldAces('name'); + + $this->assertCount(0, $classAces); + $this->assertCount(0, $classFieldAces); + $this->assertCount(0, $objectAces); + $this->assertCount(0, $objectFieldAces); + } + + /** + * @depends testInsertUpdateDelete + */ + public function testUpdatePersistedAceKeepsId() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $entry = $this->createEntry(); + $entry + ->setId(42) + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_ADMIN'))) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new MutableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + $acl->updateClassAce(0, 128); + + $aces = $acl->getClassAces(); + $this->assertEquals(42, $aces[0]->getId()); + $this->assertEquals(128, $aces[0]->getMask()); + } + + public function testSerializeUnserialize() + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + $entry = $this->createEntry(); + $entry + ->setSecurityIdentity(SecurityIdentity::fromAclIdentity($this->getRoleSecurityIdentity('ROLE_ADMIN'))) + ->setAclClass($this->getAclClass()) + ; + $collection->append($entry); + + $acl = new MutableAcl($collection, $this->getAclObjectIdentity(), new PermissionGrantingStrategy()); + $serialized = serialize($acl); + $unserialized = unserialize($serialized); + + $this->assertNotEmpty($serialized); + $this->assertNotEmpty($unserialized); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\MutableAcl', $unserialized); + $this->assertEquals($serialized, serialize($unserialized)); + } + + protected function createEmptyAcl($identifier = 1, array $securityIdentities = array(), AclInterface $parentAcl = null, $inherited = null) + { + $collection = new ObjectCollection(); + $collection->setModel('Propel\PropelBundle\Model\Acl\Entry'); + + return new MutableAcl($collection, $this->getAclObjectIdentity($identifier), new PermissionGrantingStrategy(), $securityIdentities, $parentAcl, $inherited, $this->con); + } +} diff --git a/Tests/Security/Acl/MutableAclProviderTest.php b/Tests/Security/Acl/MutableAclProviderTest.php new file mode 100644 index 0000000..9edc309 --- /dev/null +++ b/Tests/Security/Acl/MutableAclProviderTest.php @@ -0,0 +1,321 @@ + + */ +class MutableAclProviderTest extends AclTestCase +{ + public function testCreateAcl() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + + $this->assertNotEmpty($acl); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\MutableAcl', $acl); + $this->assertEquals(1, $acl->getId()); + + $this->assertEmpty($acl->getClassAces()); + $this->assertEmpty($acl->getObjectAces()); + $this->assertEmpty($acl->getFields()); + } + + /** + * @depends testCreateAcl + */ + public function testUpdateAclCreatesInsertedAces() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $acl->insertClassFieldAce('name', $this->getRoleSecurityIdentity('ROLE_ADMIN'), 128); + + $this->assertCount(1, $acl->getObjectAces()); + $this->assertEquals(array('name'), $acl->getFields()); + $this->assertCount(1, $acl->getClassFieldAces('name')); + + $this->assertEquals(0, EntryQuery::create()->count($this->con)); + $this->assertTrue($this->getAclProvider()->updateAcl($acl)); + $this->assertEquals(2, EntryQuery::create()->count($this->con)); + + $acl = $this->getAclProvider()->findAcl($this->getAclObjectIdentity(1)); + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\MutableAcl', $acl); + + $objAces = $acl->getObjectAces(); + $this->assertCount(1, $objAces); + + $entry = $objAces[0]; + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\Entry', $entry); + $this->assertEquals(64, $entry->getMask()); + $this->assertEquals($this->getRoleSecurityIdentity(), $entry->getSecurityIdentity()); + + $classFieldAces = $acl->getClassFieldAces('name'); + $this->assertCount(1, $classFieldAces); + + $entry = $classFieldAces[0]; + $this->assertInstanceOf('Propel\PropelBundle\Security\Acl\Domain\FieldEntry', $entry); + $this->assertEquals('name', $entry->getField()); + $this->assertEquals(128, $entry->getMask()); + $this->assertEquals($this->getRoleSecurityIdentity('ROLE_ADMIN'), $entry->getSecurityIdentity()); + } + + /** + * @depends testUpdateAclCreatesInsertedAces + */ + public function testCreateAclAlreadyExists() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $this->getAclProvider()->updateAcl($acl); + + $this->setExpectedException('Symfony\Component\Security\Acl\Exception\AclAlreadyExistsException'); + $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + } + + /** + * @depends testUpdateAclCreatesInsertedAces + */ + public function testCreateAclWithParent() + { + $parentAcl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + $parentAcl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $this->getAclProvider()->updateAcl($parentAcl); + + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(2)); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 128); + $acl->setParentAcl($parentAcl); + $this->getAclProvider()->updateAcl($acl); + + $entries = ObjectIdentityQuery::create()->orderById(Criteria::ASC)->find($this->con); + $this->assertCount(2, $entries); + $this->assertNull($entries[0]->getParentObjectIdentityId()); + $this->assertEquals($entries[0]->getId(), $entries[1]->getParentObjectIdentityId()); + } + + public function testUpdateAclInvalidAcl() + { + $acl = $this->getMock('Symfony\Component\Security\Acl\Model\MutableAclInterface'); + + $this->setExpectedException('InvalidArgumentException'); + $this->getAclProvider()->updateAcl($acl); + } + + /** + * @depends testUpdateAclCreatesInsertedAces + */ + public function testUpdateAclRemovesDeletedEntries() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + + $acl->insertObjectFieldAce('name', $this->getRoleSecurityIdentity(), 4); + $acl->insertObjectFieldAce('slug', $this->getRoleSecurityIdentity(), 1); + $this->getAclProvider()->updateAcl($acl); + $this->assertEquals(2, EntryQuery::create()->count($this->con)); + + $acl->deleteObjectFieldAce(0, 'slug'); + $this->getAclProvider()->updateAcl($acl); + $this->assertEquals(1, EntryQuery::create()->count($this->con)); + + $entry = EntryQuery::create()->findOne($this->con); + $this->assertEquals('name', $entry->getFieldName()); + $this->assertEquals(4, $entry->getMask()); + } + + /** + * @depends testUpdateAclCreatesInsertedAces + */ + public function testUpdateAclCreatesMultipleAces() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + + $acl->insertObjectFieldAce('name', $this->getRoleSecurityIdentity(), 16, 0, true, 'all'); + $acl->insertObjectFieldAce('name', $this->getRoleSecurityIdentity(), 4); + $acl->insertObjectFieldAce('slug', $this->getRoleSecurityIdentity(), 1); + $this->assertCount(2, $acl->getObjectFieldAces('name')); + + $this->getAclProvider()->updateAcl($acl); + + $entries = EntryQuery::create()->orderByMask(Criteria::ASC)->find($this->con); + $this->assertCount(3, $entries); + + $slugAce = $entries[0]; + + $this->assertEquals('slug', $slugAce->getFieldName()); + $this->assertEquals(1, $slugAce->getMask()); + + $nameRead = $entries[1]; + $this->assertEquals('name', $nameRead->getFieldName()); + $this->assertEquals(0, $nameRead->getAceOrder()); + $this->assertEquals(4, $nameRead->getMask()); + $this->assertEquals('all', $nameRead->getGrantingStrategy()); + + $nameUndelete = $entries[2]; + $this->assertEquals('name', $nameUndelete->getFieldName()); + $this->assertEquals(1, $nameUndelete->getAceOrder()); + $this->assertEquals(16, $nameUndelete->getMask()); + $this->assertEquals('all', $nameUndelete->getGrantingStrategy()); + } + + /** + * @depends testUpdateAclCreatesInsertedAces + */ + public function testUpdateAclReadsExistingAce() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $this->getAclProvider()->updateAcl($acl); + + $entry = EntryQuery::create()->findOne($this->con); + + $acl = $this->getAclProvider()->findAcl($this->getAclObjectIdentity(1)); + $acl->updateObjectAce(0, 128); + $this->getAclProvider()->updateAcl($acl); + + $updatedEntry = clone $entry; + $updatedEntry->reload(false, $this->con); + + $this->assertEquals($entry->getId(), $updatedEntry->getId()); + $this->assertEquals(128, $updatedEntry->getMask()); + } + + public function testDeleteAclNotExisting() + { + $this->assertTrue($this->getAclProvider()->deleteAcl($this->getAclObjectIdentity())); + } + + /** + * @depends testUpdateAclCreatesInsertedAces + */ + public function testDeleteAcl() + { + $aclObj = $this->getAclObjectIdentity(1); + $acl = $this->getAclProvider()->createAcl($aclObj); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $acl->insertClassFieldAce('name', $this->getRoleSecurityIdentity('ROLE_ADMIN'), 128); + + $this->assertTrue($this->getAclProvider()->deleteAcl($aclObj)); + $this->assertEquals(0, ObjectIdentityQuery::create()->count($this->con)); + $this->assertEquals(0, EntryQuery::create()->count($this->con)); + } + + /** + * @depends testCreateAclWithParent + */ + public function testDeleteAclRemovesChildAcl() + { + $parentAcl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + $parentAcl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $this->getAclProvider()->updateAcl($parentAcl); + + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(2)); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 128); + $acl->setParentAcl($parentAcl); + $this->getAclProvider()->updateAcl($acl); + + $this->getAclProvider()->deleteAcl($this->getAclObjectIdentity(1)); + + $this->assertEquals(0, ObjectIdentityQuery::create()->count($this->con)); + } + + /** + * @depends testDeleteAcl + */ + public function testDeleteAclRemovesClassEntriesIfLastObject() + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity(1)); + $acl->insertClassAce($this->getRoleSecurityIdentity(), 128); + $this->getAclProvider()->updateAcl($acl); + + $this->getAclProvider()->deleteAcl($this->getAclObjectIdentity(1)); + $this->assertEquals(0, EntryQuery::create()->count($this->con)); + } + + /** + * @depends testUpdateAclCreatesInsertedAces + */ + public function testUpdateAclWritesCacheOfNewAcl() + { + $this->cache = new AclCache(); + $this->assertEmpty($this->cache->content); + + $acl = $this->getAcl(); + + $this->assertNotEmpty($this->cache->content); + $this->assertSame($acl, $this->cache->content[$acl->getId()]); + } + + /** + * @depends testUpdateAclWritesCacheOfNewAcl + */ + public function testUpdateAclUpdatesCacheOfAcl() + { + $this->cache = new AclCache(); + $acl = $this->getAcl(1); + + $acl->updateObjectAce(0, 128); + $this->getAclProvider()->updateAcl($acl); + + $objectAces = $this->cache->content[$acl->getId()]->getObjectAces(); + $this->assertEquals(128, $objectAces[0]->getMask()); + } + + /** + * @depends testUpdateAclWritesCacheOfNewAcl + */ + public function testDeleteAclEvictsFromCache() + { + $this->cache = new AclCache(); + + $this->getAcl(); + $this->getAclProvider()->deleteAcl($this->getAclObjectIdentity(1)); + + $this->assertEmpty($this->cache->content); + } + + /** + * @depends testCreateAclWithParent + * @depends testDeleteAclEvictsFromCache + */ + public function testDeleteAclEvictsChildrenFromCache() + { + $this->cache = new AclCache(); + + $parentAcl = $this->getAcl(1); + $childAcl = $this->getAcl(2); + $grandChildAcl = $this->getAcl(3); + $grandChildAcl->setParentAcl($childAcl); + $childAcl->setParentAcl($parentAcl); + + $this->getAclProvider()->updateAcl($grandChildAcl); + $this->getAclProvider()->updateAcl($childAcl); + + $this->assertCount(3, $this->cache->content); + + $this->getAclProvider()->deleteAcl($this->getAclObjectIdentity(1)); + $this->assertEmpty($this->cache->content); + } + + protected function getAcl($identifier = 1) + { + $acl = $this->getAclProvider()->createAcl($this->getAclObjectIdentity($identifier)); + $acl->insertObjectAce($this->getRoleSecurityIdentity(), 64); + $this->getAclProvider()->updateAcl($acl); + + return $acl; + } +}