Completed
Push — develop ( f05cec...11f198 )
by Daniel
07:33
created

EntitySubscriber::onFlush()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 10
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 6

Importance

Changes 0
Metric Value
cc 2
eloc 7
nc 2
nop 1
dl 0
loc 10
ccs 0
cts 8
cp 0
crap 6
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace Silverback\ApiComponentBundle\EventSubscriber\Doctrine;
4
5
use Doctrine\Common\EventSubscriber;
6
use Doctrine\DBAL\Platforms\SqlitePlatform;
7
use Doctrine\ORM\EntityManagerInterface;
8
use Doctrine\ORM\Event\OnFlushEventArgs;
9
use Doctrine\ORM\UnitOfWork;
10
use Liip\ImagineBundle\Imagine\Cache\CacheManager;
11
use Liip\ImagineBundle\Service\FilterService;
12
use Silverback\ApiComponentBundle\Entity\Content\FileInterface;
13
use Silverback\ApiComponentBundle\Entity\SortableInterface;
14
use Silverback\ApiComponentBundle\Imagine\PathResolver;
15
use Silverback\ApiComponentBundle\Validator\ImagineSupportedFilePath;
16
17
/**
18
 * Class FileEntitySubscriber
19
 * @package Silverback\ApiComponentBundle\EventListener
20
 * @author Daniel West <[email protected]>
21
 */
22
class EntitySubscriber implements EventSubscriber
23
{
24
    /**
25
     * @var CacheManager
26
     */
27
    private $imagineCacheManager;
28
    /**
29
     * @var FilterService
30
     */
31
    private $filterService;
32
    /**
33
     * @var PathResolver
34
     */
35
    private $pathResolver;
36
37
    /**
38
     * FileListener constructor.
39
     * @param CacheManager $imagineCacheManager
40
     * @param FilterService $filterService
41
     * @param PathResolver $pathResolver
42
     */
43
    public function __construct(
44
        CacheManager $imagineCacheManager,
45
        FilterService $filterService,
46
        PathResolver $pathResolver
47
    ) {
48
        $this->imagineCacheManager = $imagineCacheManager;
49
        $this->filterService = $filterService;
50
        $this->pathResolver = $pathResolver;
51
    }
52
53
    /**
54
     * @return array
55
     */
56
    public function getSubscribedEvents(): array
57
    {
58
        return [
59
            'onFlush'
60
        ];
61
    }
62
63
    /**
64
     * @param OnFlushEventArgs $eventArgs
65
     * @throws \Doctrine\DBAL\DBALException
66
     */
67
    public function onFlush(OnFlushEventArgs $eventArgs): void
68
    {
69
        $entityManager = $eventArgs->getEntityManager();
70
        if ($entityManager->getConnection()->getDatabasePlatform() instanceof SqlitePlatform) {
71
            $entityManager->getConnection()->exec('PRAGMA foreign_keys = ON;');
72
        }
73
        $unitOfWork = $entityManager->getUnitOfWork();
74
        $this->processNewEntities($unitOfWork, $entityManager);
75
        $this->processUpdatedEntities($unitOfWork);
76
        $this->processDeletedEntities($unitOfWork);
77
    }
78
79
    /**
80
     * @param UnitOfWork $unitOfWork
81
     * @param EntityManagerInterface $entityManager
82
     */
83
    private function processNewEntities(UnitOfWork $unitOfWork, EntityManagerInterface $entityManager): void
84
    {
85
        $newEntities = $unitOfWork->getScheduledEntityInsertions();
86
        foreach ($newEntities as $entity) {
87
            if ($entity instanceof SortableInterface && $entity->getSort() === null) {
88
                $entity->setSort($entity->calculateSort(true));
89
                $metadata = $entityManager->getClassMetadata(\get_class($entity));
90
                $unitOfWork->recomputeSingleEntityChangeSet($metadata, $entity);
91
            }
92
            if (
93
                $entity instanceof FileInterface &&
94
                ImagineSupportedFilePath::isValidFilePath($entity->getFilePath())
95
            ) {
96
                $this->createFilteredImages($entity);
97
            }
98
        }
99
    }
100
101
    /**
102
     * @param UnitOfWork $unitOfWork
103
     */
104
    private function processUpdatedEntities(UnitOfWork $unitOfWork): void
105
    {
106
        $updatedEntities = $unitOfWork->getScheduledEntityUpdates();
107
        foreach ($updatedEntities as $entity) {
108
            if ($entity instanceof FileInterface) {
109
                $changes = $unitOfWork->getEntityChangeSet($entity);
110
                if (!\is_array($changes)) {
111
                    return;
112
                }
113
                if (array_key_exists('filePath', $changes)) {
114
                    $fpChanges = $changes['filePath'];
115
                    $previousValueForField = $fpChanges[0] ?? null;
116
                    $newValueForField = $fpChanges[1] ?? null;
117
                    if ($previousValueForField !== $newValueForField) {
118
                        if (ImagineSupportedFilePath::isValidFilePath($previousValueForField)) {
119
                            $this->imagineCacheManager->remove($previousValueForField);
120
                        }
121
                        if (ImagineSupportedFilePath::isValidFilePath($newValueForField)) {
122
                            $this->createFilteredImages($entity);
123
                        }
124
                    }
125
                }
126
            }
127
        }
128
    }
129
130
    /**
131
     * @param UnitOfWork $unitOfWork
132
     */
133
    private function processDeletedEntities(UnitOfWork $unitOfWork): void
134
    {
135
        $deletedEntities = $unitOfWork->getScheduledEntityDeletions();
136
        foreach ($deletedEntities as $entity) {
137
            if (
138
                $entity instanceof FileInterface &&
139
                ImagineSupportedFilePath::isValidFilePath($entity->getFilePath())
140
            ) {
141
                $this->imagineCacheManager->remove($entity->getFilePath());
142
            }
143
        }
144
    }
145
146
    private function createFilteredImages(FileInterface $file): void
147
    {
148
        $filters = $file::getImagineFilters();
149
        foreach ($filters as $filter) {
150
            $this->filterService->getUrlOfFilteredImage($this->pathResolver->resolve($file->getFilePath()), $filter);
151
        }
152
    }
153
}
154