CommentSecurityProcessor::__construct()   A
last analyzed

Complexity

Conditions 1
Paths 1

Size

Total Lines 5
Code Lines 0

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 1
eloc 0
c 1
b 0
f 0
nc 1
nop 3
dl 0
loc 5
rs 10
1
<?php
2
3
declare(strict_types=1);
4
5
namespace ProjetNormandie\ArticleBundle\State;
6
7
use ApiPlatform\Metadata\Operation;
8
use ApiPlatform\State\ProcessorInterface;
9
use ProjetNormandie\ArticleBundle\Entity\Comment;
10
use Symfony\Bundle\SecurityBundle\Security;
11
use Symfony\Component\Security\Core\Exception\AccessDeniedException;
12
13
/**
14
 * StateProcessor pour gérer la sécurité des commentaires selon l'environnement
15
 */
16
readonly class CommentSecurityProcessor implements ProcessorInterface
17
{
18
    public function __construct(
19
        private ProcessorInterface $persistProcessor,
20
        private Security $security,
21
        private string $environment = 'prod'
22
    ) {
23
    }
24
25
    public function process(mixed $data, Operation $operation, array $uriVariables = [], array $context = []): mixed
26
    {
27
        if ($this->environment !== 'test' && $data instanceof Comment) {
28
            $this->checkSecurity($data, $operation, $context);
29
        }
30
31
        return $this->persistProcessor->process($data, $operation, $uriVariables, $context);
32
    }
33
34
    private function checkSecurity(Comment $comment, Operation $operation, array $context): void
35
    {
36
        $operationName = $operation->getName();
37
38
        // Vérifier l'authentification pour POST et PUT
39
        if (in_array($operationName, ['post', 'put'])) {
40
            if (!$this->security->isGranted('ROLE_USER')) {
41
                throw new AccessDeniedException('Authentication required to manage comments');
42
            }
43
        }
44
45
        // Pour PUT, vérifier que l'utilisateur peut modifier ce commentaire
46
        if ($operationName === 'put') {
47
            $currentUser = $this->security->getUser();
48
49
            // Si c'est une création depuis la base, récupérer l'entité existante
50
            if (!$comment->getUser() && isset($context['previous_data'])) {
51
                $previousComment = $context['previous_data'];
52
                if ($previousComment instanceof Comment && $previousComment->getUser() !== $currentUser) {
53
                    throw new AccessDeniedException('You can only modify your own comments');
54
                }
55
            } elseif ($comment->getUser() && $comment->getUser() !== $currentUser) {
56
                throw new AccessDeniedException('You can only modify your own comments');
57
            }
58
        }
59
60
        // Pour POST, s'assurer que l'utilisateur est défini
61
        if ($operationName === 'post' && !$comment->getUser()) {
62
            $comment->setUser($this->security->getUser());
63
        }
64
    }
65
}
66