Passed
Branch 3.0.0 (80e4da)
by Pieter
04:11
created

Apie::getResourceSerializer()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 6
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 2
eloc 3
c 1
b 0
f 0
nc 2
nop 0
dl 0
loc 6
rs 10
1
<?php
2
3
namespace W2w\Lib\Apie;
4
5
use Doctrine\Common\Annotations\Reader;
6
use Psr\Cache\CacheItemPoolInterface;
7
use Symfony\Component\PropertyAccess\PropertyAccessor;
8
use Symfony\Component\PropertyInfo\PropertyTypeExtractorInterface;
9
use Symfony\Component\Serializer\Encoder\DecoderInterface;
10
use Symfony\Component\Serializer\Encoder\EncoderInterface;
11
use Symfony\Component\Serializer\Mapping\Factory\ClassMetadataFactoryInterface;
12
use Symfony\Component\Serializer\NameConverter\NameConverterInterface;
13
use Symfony\Component\Serializer\Normalizer\DenormalizerInterface;
14
use Symfony\Component\Serializer\Normalizer\NormalizerInterface;
15
use W2w\Lib\Apie\Exceptions\BadConfigurationException;
16
use W2w\Lib\Apie\Exceptions\NotAnApiePluginException;
17
use W2w\Lib\Apie\PluginInterfaces\AnnotationReaderProviderInterface;
18
use W2w\Lib\Apie\PluginInterfaces\ApieAwareInterface;
19
use W2w\Lib\Apie\PluginInterfaces\CacheItemPoolProviderInterface;
20
use W2w\Lib\Apie\PluginInterfaces\EncoderProviderInterface;
21
use W2w\Lib\Apie\PluginInterfaces\NormalizerProviderInterface;
22
use W2w\Lib\Apie\PluginInterfaces\ResourceProviderInterface;
23
use W2w\Lib\Apie\PluginInterfaces\SerializerProviderInterface;
24
use W2w\Lib\Apie\PluginInterfaces\SymfonyComponentProviderInterface;
25
use W2w\Lib\Apie\Plugins\CorePlugin;
26
use W2w\Lib\Apie\Serializers\ResourceSerializerInterface;
27
28
final class Apie implements SerializerProviderInterface, ResourceProviderInterface, NormalizerProviderInterface, EncoderProviderInterface, SymfonyComponentProviderInterface, CacheItemPoolProviderInterface, AnnotationReaderProviderInterface
29
{
30
    /**
31
     * @var bool
32
     */
33
    private $debug;
34
35
    /**
36
     * @var string|null
37
     */
38
    private $cacheFolder;
39
40
    /**
41
     * @var SerializerProviderInterface[]
42
     */
43
    private $serializers = [];
44
45
    /**
46
     * @var ResourceProviderInterface[]
47
     */
48
    private $resources = [];
49
50
    /**
51
     * @var NormalizerProviderInterface[]
52
     */
53
    private $normalizers = [];
54
55
    /**
56
     * @var EncoderProviderInterface[]
57
     */
58
    private $encoders = [];
59
60
    /**
61
     * @var SymfonyComponentProviderInterface[]
62
     */
63
    private $symfonyComponents = [];
64
65
    /**
66
     * @var CacheItemPoolProviderInterface[]
67
     */
68
    private $cacheItemPools = [];
69
70
    /**
71
     * @var object[]
72
     */
73
    private $plugins = [];
74
75
    /**
76
     * @var AnnotationReaderProviderInterface[]
77
     */
78
    private $annotationReaders = [];
79
80
    /**
81
82
     * @param object[] $plugins
83
     * @param bool $debug
84
     * @param string|null $cacheFolder
85
     * @param bool $addCorePlugin
86
     */
87
    public function __construct(array $plugins, bool $debug = false, ?string $cacheFolder = null, bool $addCorePlugin = true)
88
    {
89
        $this->debug = $debug;
90
        $this->cacheFolder = $cacheFolder;
91
        static $mapping = [
92
            SerializerProviderInterface::class => 'serializers',
93
            ResourceProviderInterface::class => 'resources',
94
            NormalizerProviderInterface::class => 'normalizers',
95
            EncoderProviderInterface::class => 'encoders',
96
            SymfonyComponentProviderInterface::class => 'symfonyComponents',
97
            CacheItemPoolProviderInterface::class => 'cacheItemPools',
98
            AnnotationReaderProviderInterface::class => 'annotationReaders',
99
        ];
100
        if ($addCorePlugin) {
101
            $plugins[] = new CorePlugin();
102
        }
103
        $this->plugins = $plugins;
104
        foreach ($plugins as $plugin) {
105
            $isUsed = false;
106
            foreach ($mapping as $className => $propertyName) {
107
                if ($plugin instanceof $className) {
108
                    $this->$propertyName[] = $plugin;
109
                    if (!$isUsed && $plugin instanceof ApieAwareInterface) {
110
                        $plugin->setApie($this);
111
                    }
112
                    $isUsed = true;
113
                }
114
            }
115
            if (!$isUsed) {
116
                throw new NotAnApiePluginException($plugin);
117
            }
118
119
        }
120
    }
121
122
    /**
123
     * @return bool
124
     */
125
    public function isDebug(): bool
126
    {
127
        return $this->debug;
128
    }
129
130
    /**
131
     * @return string|null
132
     */
133
    public function getCacheFolder(): ?string
134
    {
135
        return $this->cacheFolder;
136
    }
137
138
    public function getPlugin(string $pluginClass): object
139
    {
140
        foreach ($this->plugins as $plugin) {
141
            if ($plugin instanceof $pluginClass) {
142
                return $plugin;
143
            }
144
        }
145
        throw new BadConfigurationException('Plugin ' . $pluginClass . ' not found!');
146
    }
147
148
    /**
149
     * @return ResourceSerializerInterface
150
     */
151
    public function getResourceSerializer(): ResourceSerializerInterface
152
    {
153
        if (empty($this->serializers)) {
154
            throw new BadConfigurationException('I have no resource serializer set up');
155
        }
156
        return reset($this->serializers)->getResourceSerializer();
157
    }
158
159
    /**
160
     * Returns a list of Api resources.
161
     *
162
     * @param string $context
163
     * @return string[]
164
     */
165
    public function getResources(string $context): array
166
    {
167
        $resources = [];
168
        foreach ($this->resources as $resourceProvider) {
169
            $resources = array_merge($resources, $resourceProvider->getResources($context));
170
        }
171
        return array_values(array_unique($resources));
172
    }
173
174
    /**
175
     * @return NormalizerInterface[]|DenormalizerInterface[]
176
     */
177
    public function getNormalizers(): array
178
    {
179
        $normalizers = [];
180
        foreach ($this->normalizers as $normalizerProvider) {
181
            $normalizers = array_merge($normalizers, $normalizerProvider->getNormalizers());
182
        }
183
        return $normalizers;
184
    }
185
186
    /**
187
     * @return EncoderInterface[]|DecoderInterface[]
188
     */
189
    public function getEncoders(): array
190
    {
191
        $encoders = [];
192
        foreach ($this->encoders as $encoderProvider) {
193
            $encoders = array_merge($encoders, $encoderProvider->getNormalizers());
0 ignored issues
show
Bug introduced by
The method getNormalizers() does not exist on W2w\Lib\Apie\PluginInter...ncoderProviderInterface. Since it exists in all sub-types, consider adding an abstract or default implementation to W2w\Lib\Apie\PluginInter...ncoderProviderInterface. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

193
            $encoders = array_merge($encoders, $encoderProvider->/** @scrutinizer ignore-call */ getNormalizers());
Loading history...
194
        }
195
        return $encoders;
196
    }
197
198
    public function getClassMetadataFactory(): ClassMetadataFactoryInterface
199
    {
200
        if (empty($this->symfonyComponents)) {
201
            throw new BadConfigurationException('I have no symfony component provider set up');
202
        }
203
        return reset($this->symfonyComponents)->getClassMetadataFactory();
204
    }
205
206
    public function getPropertyConverter(): NameConverterInterface
207
    {
208
        if (empty($this->symfonyComponents)) {
209
            throw new BadConfigurationException('I have no symfony component provider set up');
210
        }
211
        return reset($this->symfonyComponents)->getPropertyConverter();
212
    }
213
214
    public function getPropertyAccessor(): PropertyAccessor
215
    {
216
        if (empty($this->symfonyComponents)) {
217
            throw new BadConfigurationException('I have no symfony component provider set up');
218
        }
219
        return reset($this->symfonyComponents)->getPropertyAccessor();
220
    }
221
222
    public function getPropertyTypeExtractor(): PropertyTypeExtractorInterface
223
    {
224
        if (empty($this->symfonyComponents)) {
225
            throw new BadConfigurationException('I have no symfony component provider set up');
226
        }
227
        return reset($this->symfonyComponents)->getPropertyTypeExtractor();
228
    }
229
230
    public function getCacheItemPool(): CacheItemPoolInterface
231
    {
232
        if (empty($this->cacheItemPools)) {
233
            throw new BadConfigurationException('I have no cache item pool provider set up');
234
        }
235
        return reset($this->cacheItemPools)->getCacheItemPool();
236
    }
237
238
    public function getAnnotationReader(): Reader
239
    {
240
        if (empty($this->annotationReaders)) {
241
            throw new BadConfigurationException('I have no annotation reader set up');
242
        }
243
        return reset($this->annotationReaders)->getAnnotationReader();
244
    }
245
}
246