Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 8051c8a

Browse files
committed
Fixed a bug related to fields without permission
1 parent 2cd317d commit 8051c8a

38 files changed

Lines changed: 122 additions & 21 deletions

src/Collection/EntityCollection.php

Lines changed: 10 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,20 @@ final class EntityCollection implements CollectionInterface
1313
/** @var EntityDto[] */
1414
private $entities;
1515

16-
private function __construct(EntityDto $entityDto, iterable $entityInstances)
16+
/**
17+
* @param EntityDto[] $entities
18+
*/
19+
private function __construct(array $entities)
1720
{
18-
$this->entities = $this->processEntities($entityDto, $entityInstances);
21+
$this->entities = $entities;
1922
}
2023

21-
public static function new(EntityDto $entityDto, iterable $entityInstances): self
24+
/**
25+
* @param EntityDto[] $entities
26+
*/
27+
public static function new(array $entities): self
2228
{
23-
return new self($entityDto, $entityInstances);
29+
return new self($entities);
2430
}
2531

2632
public function get(string $entityId): ?EntityDto
@@ -65,16 +71,4 @@ public function getIterator()
6571
{
6672
return new \ArrayIterator($this->entities);
6773
}
68-
69-
private function processEntities(EntityDto $entityDto, $entityInstances): array
70-
{
71-
$dtos = [];
72-
73-
foreach ($entityInstances as $entityInstance) {
74-
$dto = $entityDto->newWithInstance($entityInstance);
75-
$dtos[$dto->getPrimaryKeyValue()] = $dto;
76-
}
77-
78-
return $dtos;
79-
}
8074
}

src/Collection/FieldCollection.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,11 @@ public function set(FieldDto $newOrUpdatedField): void
4848
$this->fields[$newOrUpdatedField->getProperty()] = $newOrUpdatedField;
4949
}
5050

51+
public function unset(FieldDto $removedField): void
52+
{
53+
unset($this->fields[$removedField->getProperty()]);
54+
}
55+
5156
public function offsetExists($offset): bool
5257
{
5358
return \array_key_exists($offset, $this->fields);

src/Controller/AbstractCrudController.php

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
use EasyCorp\Bundle\EasyAdminBundle\Event\BeforeEntityUpdatedEvent;
2929
use EasyCorp\Bundle\EasyAdminBundle\Exception\EntityRemoveException;
3030
use EasyCorp\Bundle\EasyAdminBundle\Exception\ForbiddenActionException;
31+
use EasyCorp\Bundle\EasyAdminBundle\Exception\InsufficientEntityPermissionException;
3132
use EasyCorp\Bundle\EasyAdminBundle\Factory\ActionFactory;
3233
use EasyCorp\Bundle\EasyAdminBundle\Factory\EntityFactory;
3334
use EasyCorp\Bundle\EasyAdminBundle\Factory\FilterFactory;
@@ -115,7 +116,7 @@ public function index(AdminContext $context)
115116
$queryBuilder = $this->createIndexQueryBuilder($context->getSearch(), $context->getEntity(), $fields, $filters);
116117
$paginator = $this->get(PaginatorFactory::class)->create($queryBuilder);
117118

118-
$entities = EntityCollection::new($context->getEntity(), $paginator->getResults());
119+
$entities = $this->get(EntityFactory::class)->createCollection($context->getEntity(), $paginator->getResults());
119120
$this->get(EntityFactory::class)->processFieldsForAll($entities, $fields);
120121
$globalActions = $this->get(EntityFactory::class)->processActionsForAll($entities, $context->getCrud()->getActionsConfig());
121122

@@ -150,6 +151,10 @@ public function detail(AdminContext $context)
150151
throw new ForbiddenActionException($context);
151152
}
152153

154+
if (!$context->getEntity()->isAccessible()) {
155+
throw new InsufficientEntityPermissionException($context);
156+
}
157+
153158
$this->get(EntityFactory::class)->processFields($context->getEntity(), FieldCollection::new($this->configureFields(Crud::PAGE_DETAIL)));
154159
$this->get(EntityFactory::class)->processActions($context->getEntity(), $context->getCrud()->getActionsConfig());
155160

@@ -180,6 +185,10 @@ public function edit(AdminContext $context)
180185
throw new ForbiddenActionException($context);
181186
}
182187

188+
if (!$context->getEntity()->isAccessible()) {
189+
throw new InsufficientEntityPermissionException($context);
190+
}
191+
183192
$this->get(EntityFactory::class)->processFields($context->getEntity(), FieldCollection::new($this->configureFields(Crud::PAGE_EDIT)));
184193
$this->get(EntityFactory::class)->processActions($context->getEntity(), $context->getCrud()->getActionsConfig());
185194
$entityInstance = $context->getEntity()->getInstance();
@@ -259,6 +268,10 @@ public function new(AdminContext $context)
259268
throw new ForbiddenActionException($context);
260269
}
261270

271+
if (!$context->getEntity()->isAccessible()) {
272+
throw new InsufficientEntityPermissionException($context);
273+
}
274+
262275
$context->getEntity()->setInstance($this->createEntity($context->getEntity()->getFqcn()));
263276
$this->get(EntityFactory::class)->processFields($context->getEntity(), FieldCollection::new($this->configureFields(Crud::PAGE_NEW)));
264277
$this->get(EntityFactory::class)->processActions($context->getEntity(), $context->getCrud()->getActionsConfig());
@@ -333,6 +346,10 @@ public function delete(AdminContext $context)
333346
throw new ForbiddenActionException($context);
334347
}
335348

349+
if (!$context->getEntity()->isAccessible()) {
350+
throw new InsufficientEntityPermissionException($context);
351+
}
352+
336353
$csrfToken = $context->getRequest()->request->get('token');
337354
if (!$this->isCsrfTokenValid('ea-delete', $csrfToken)) {
338355
return $this->redirectToRoute($context->getDashboardRouteName());

src/Dto/EntityDto.php

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,26 +14,26 @@
1414
*/
1515
final class EntityDto
1616
{
17+
private $isAccessible;
1718
private $fqcn;
1819
private $metadata;
1920
private $instance;
2021
private $primaryKeyName;
2122
private $primaryKeyValue;
2223
private $permission;
23-
private $userHasPermission;
2424
/** @var ?FieldDtoCollection */
2525
private $fields;
2626
/** @var ActionCollection */
2727
private $actions;
2828

2929
public function __construct(string $entityFqcn, ClassMetadata $entityMetadata, ?string $entityPermission = null, $entityInstance = null)
3030
{
31+
$this->isAccessible = true;
3132
$this->fqcn = $entityFqcn;
3233
$this->metadata = $entityMetadata;
3334
$this->instance = $entityInstance;
3435
$this->primaryKeyName = $this->metadata->getIdentifierFieldNames()[0];
3536
$this->permission = $entityPermission;
36-
$this->userHasPermission = true;
3737
}
3838

3939
public function getFqcn(): string
@@ -103,14 +103,14 @@ public function getPermission(): ?string
103103

104104
public function isAccessible(): bool
105105
{
106-
return true === $this->userHasPermission;
106+
return $this->isAccessible;
107107
}
108108

109109
public function markAsInaccessible(): void
110110
{
111+
$this->isAccessible = false;
111112
$this->instance = null;
112113
$this->fields = null;
113-
$this->userHasPermission = false;
114114
}
115115

116116
public function getFields(): ?FieldCollection
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
<?php
2+
3+
namespace EasyCorp\Bundle\EasyAdminBundle\Exception;
4+
5+
use EasyCorp\Bundle\EasyAdminBundle\Context\AdminContext;
6+
use EasyCorp\Bundle\EasyAdminBundle\Context\ExceptionContext;
7+
8+
/**
9+
* @author Javier Eguiluz <[email protected]>
10+
*/
11+
final class InsufficientEntityPermissionException extends BaseException
12+
{
13+
public function __construct(AdminContext $adminContext)
14+
{
15+
$parameters = [
16+
'entity_fqcn' => $adminContext->getEntity()->getFqcn(),
17+
'entity_id' => $entityId = $adminContext->getRequest()->query->get('entityId'),
18+
];
19+
20+
if (empty($entityId)) {
21+
$debugMessage = sprintf('You don\'t have enough permissions to access this instance of the "%s" entity.', $parameters['entity_fqcn']);
22+
} else {
23+
$debugMessage = sprintf('You don\'t have enough permissions to access the instance of the "%s" entity with id = %s.', $parameters['entity_fqcn'], $entityId);
24+
}
25+
26+
$exceptionContext = new ExceptionContext(
27+
'exception.insufficient_entity_permission',
28+
$debugMessage,
29+
$parameters,
30+
403
31+
);
32+
33+
parent::__construct($exceptionContext);
34+
}
35+
}

src/Factory/EntityFactory.php

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,23 @@ public function createForEntityInstance($entityInstance): EntityDto
7575
return $this->doCreate(null, null, null, $entityInstance);
7676
}
7777

78+
public function createCollection(EntityDto $entityDto, ?iterable $entityInstances): EntityCollection
79+
{
80+
$entityDtos = [];
81+
82+
foreach ($entityInstances as $entityInstance) {
83+
$newEntityDto = $entityDto->newWithInstance($entityInstance);
84+
$newEntityId = $newEntityDto->getPrimaryKeyValue();
85+
if (!$this->authorizationChecker->isGranted(Permission::EA_VIEW_ENTITY, $newEntityDto)) {
86+
$newEntityDto->markAsInaccessible();
87+
}
88+
89+
$entityDtos[$newEntityId] = $newEntityDto;
90+
}
91+
92+
return EntityCollection::new($entityDtos);
93+
}
94+
7895
private function doCreate(?string $entityFqcn = null, $entityId = null, ?string $entityPermission = null, $entityInstance = null): EntityDto
7996
{
8097
if (null === $entityInstance && null !== $entityFqcn) {

src/Factory/FieldFactory.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,8 @@ public function processFields(EntityDto $entityDto, FieldCollection $fields): vo
7171

7272
foreach ($fields as $fieldName => $fieldDto) {
7373
if (false === $this->authorizationChecker->isGranted(Permission::EA_VIEW_FIELD, $fieldDto)) {
74+
$fields->unset($fieldDto);
75+
7476
continue;
7577
}
7678

src/Resources/translations/EasyAdminBundle.ar.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,5 +121,6 @@
121121
// 'entity_not_found' => '',
122122
// 'entity_remove' => '',
123123
// 'forbidden_action' => '',
124+
// 'insufficient_entity_permission' => 'You don't have permission to access this item.',
124125
],
125126
];

src/Resources/translations/EasyAdminBundle.bg.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,5 +121,6 @@
121121
'entity_not_found' => 'Този елемент вече не е налице.',
122122
'entity_remove' => 'Този елемент не може да бъде изтрит, защото други елементи зависят от него.',
123123
'forbidden_action' => 'Заявеното действие не може да се изпълни за този елемент.',
124+
// 'insufficient_entity_permission' => 'You don't have permission to access this item.',
124125
],
125126
];

src/Resources/translations/EasyAdminBundle.ca.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,5 +121,6 @@
121121
// 'entity_not_found' => '',
122122
// 'entity_remove' => '',
123123
// 'forbidden_action' => '',
124+
// 'insufficient_entity_permission' => 'You don't have permission to access this item.',
124125
],
125126
];

0 commit comments

Comments
 (0)