GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Completed
Push — master ( 84e592...894b2c )
by joseph
127:56 queued 125:09
created

clearEntityManagerAndReloadEntity()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 4
nc 1
nop 0
dl 0
loc 7
rs 10
c 0
b 0
f 0
1
<?php declare(strict_types=1);
2
3
namespace EdmondsCommerce\DoctrineStaticMeta\Tests\Large\C\Entity\Fields\Traits;
4
5
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\AbstractGenerator;
6
use EdmondsCommerce\DoctrineStaticMeta\Entity\Fields\FakerData\FakerDataProviderInterface;
7
use EdmondsCommerce\DoctrineStaticMeta\Entity\Interfaces\EntityInterface;
8
use EdmondsCommerce\DoctrineStaticMeta\Entity\Savers\EntitySaver;
9
use EdmondsCommerce\DoctrineStaticMeta\Entity\Testing\EntityTestInterface;
10
use EdmondsCommerce\DoctrineStaticMeta\Exception\ValidationException;
11
use EdmondsCommerce\DoctrineStaticMeta\Tests\Assets\AbstractLargeTest;
12
use Faker\Generator;
13
14
/**
15
 * Extend this test with your Field Trait test to get basic test coverage.
16
 *
17
 * You should extend your field trait test to test your validation
18
 *
19
 * Class AbstractFieldTraitTest
20
 *
21
 * @package EdmondsCommerce\DoctrineStaticMeta\Entity\Fields\Traits
22
 * @SuppressWarnings(PHPMD.NumberOfChildren)
23
 * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
24
 * @large
25
 */
26
abstract class AbstractFieldTraitTest extends AbstractLargeTest
27
{
28
    protected const TEST_ENTITY_FQN_BASE = self::TEST_PROJECT_ROOT_NAMESPACE
29
                                           . '\\' . AbstractGenerator::ENTITIES_FOLDER_NAME
30
                                           . '\\';
31
32
    protected const TEST_FIELD_FQN = 'Override Me';
33
34
    /**
35
     * The expected default value for the field. Most fields are marked as nullable so the default is null.
36
     * Should be overriden in the actual field test for any fields that are not nullable
37
     */
38
    protected const TEST_FIELD_DEFAULT = null;
39
40
    protected const TEST_FIELD_PROP = 'Override Me';
41
42
    /**
43
     * set to false for read only fields (with no setter)
44
     */
45
    protected const HAS_SETTER = true;
46
47
    /**
48
     * set to false for fields that do not have a validator configuration
49
     */
50
    protected const VALIDATES = true;
51
52
    /**
53
     * Override this with an array of valid values to set
54
     */
55
    protected const VALID_VALUES = [];
56
57
    /**
58
     * Override this with an array of invalid values to set.
59
     */
60
    protected const INVALID_VALUES = [];
61
62
    /**
63
     * @var Generator
64
     */
65
    protected static $fakerGenerator;
66
    protected static $buildOnce = true;
67
    protected        $entitySuffix;
68
69
    public function setup()
70
    {
71
        parent::setUp();
72
        $this->entitySuffix = substr(static::class, strrpos(static::class, '\\') + 1);
73
        if (false === static::$built) {
74
            $this->generateCode();
75
            static::$built = true;
76
        }
77
        $this->setupCopiedWorkDir();
78
        $this->recreateDtos();
79
    }
80
81
    protected function generateCode()
82
    {
83
        $this->getEntityGenerator()
84
             ->generateEntity(static::TEST_ENTITY_FQN_BASE . $this->entitySuffix);
85
        $this->getFieldSetter()
86
             ->setEntityHasField(
87
                 static::TEST_ENTITY_FQN_BASE . $this->entitySuffix,
88
                 static::TEST_FIELD_FQN
89
             );
90
    }
91
92
    /**
93
     * @SuppressWarnings(PHPMD.StaticAccess)
94
     */
95
    public static function setUpBeforeClass()
96
    {
97
        parent::setUpBeforeClass();
98
        self::$fakerGenerator = \Faker\Factory::create();
99
    }
100
101
    /**
102
     * @throws \ReflectionException
103
     * @large
104
     * @test
105
     */
106
    public function createEntityWithField(): void
107
    {
108
        $entity = $this->getEntity();
109
        $getter = $this->getGetter($entity);
110
        self::assertTrue(\method_exists($entity, $getter));
111
        $value = $entity->$getter();
112
        self::assertSame(
113
            static::TEST_FIELD_DEFAULT,
114
            $value,
115
            'The getter on a newly created entity returns ' . var_export($value, true)
116
            . ' whereas the configured default value is ' . var_export(static::TEST_FIELD_DEFAULT, true)
117
        );
118
        if (false === static::HAS_SETTER) {
0 ignored issues
show
introduced by
The condition false === static::HAS_SETTER is always false.
Loading history...
119
            return;
120
        }
121
        $setValue = $this->setFakerValueForProperty($entity);
122
        self::assertSame($setValue, $entity->$getter());
123
    }
124
125
    protected function getEntity()
126
    {
127
        return $this->createEntity($this->getEntityFqn());
128
    }
129
130
    protected function getEntityFqn(): string
131
    {
132
        return $this->getCopiedFqn(self::TEST_ENTITY_FQN_BASE . $this->entitySuffix);
133
    }
134
135
    /**
136
     * @param EntityInterface $entity
137
     *
138
     * @return string
139
     * @throws \Exception
140
     */
141
    protected function getGetter(EntityInterface $entity): string
142
    {
143
        foreach (['get', 'is', 'has'] as $prefix) {
144
            $method = $prefix . static::TEST_FIELD_PROP;
145
            if (\method_exists($entity, $method)) {
146
                return $method;
147
            }
148
        }
149
        throw new \RuntimeException('Failed finding a getter in ' . __METHOD__);
150
    }
151
152
    /**
153
     * @param EntityInterface $entity
154
     *
155
     * @return mixed
156
     * @throws \ReflectionException
157
     * @throws \Exception
158
     */
159
    protected function setFakerValueForProperty(EntityInterface $entity)
160
    {
161
        $setter        = 'set' . static::TEST_FIELD_PROP;
162
        $fakerProvider = $this->getFakerDataProvider();
163
        if ($fakerProvider instanceof FakerDataProviderInterface) {
164
            $setValue = $fakerProvider();
165
            $this->updateWithDto($setter, $entity, $setValue);
166
167
            return $setValue;
168
        }
169
170
        $reflection       = new  \ts\Reflection\ReflectionClass(\get_class($entity));
171
        $setterReflection = $reflection->getMethod($setter);
172
173
        $setParamType = current($setterReflection->getParameters())->getType()->getName();
174
        switch ($setParamType) {
175
            case 'string':
176
                $setValue = self::$fakerGenerator->text();
177
                break;
178
            case 'int':
179
                $setValue = self::$fakerGenerator->numberBetween(0, PHP_INT_MAX);
180
                break;
181
            case 'float':
182
                $setValue = self::$fakerGenerator->randomFloat(12, 0, 10000);
183
                break;
184
            case 'bool':
185
                $setValue = self::$fakerGenerator->boolean;
186
                break;
187
            case 'DateTime':
188
                $setValue = self::$fakerGenerator->dateTime;
189
                break;
190
            case 'DateTimeImmutable':
191
                $setValue = new \DateTimeImmutable(
192
                    self::$fakerGenerator->dateTime->format('Y-m-d')
193
                );
194
                break;
195
            default:
196
                throw new \RuntimeException('Failed getting a data provider for the property type ' . $setParamType);
197
        }
198
        $this->updateWithDto($setter, $entity, $setValue);
199
200
        return $setValue;
201
    }
202
203
    protected function getFakerDataProvider(): ?FakerDataProviderInterface
204
    {
205
        if (isset(EntityTestInterface::FAKER_DATA_PROVIDERS[static::TEST_FIELD_PROP])) {
206
            $provider = EntityTestInterface::FAKER_DATA_PROVIDERS[static::TEST_FIELD_PROP];
207
208
            return new $provider(self::$fakerGenerator);
209
        }
210
211
        return null;
212
    }
213
214
    private function updateWithDto(string $setterName, EntityInterface $entity, $setValue): void
215
    {
216
        $dto = $this->getEntityDtoFactory()->createDtoFromEntity($entity);
217
        $dto->$setterName($setValue);
218
        $entity->update($dto);
219
    }
220
221
    /**
222
     * @test
223
     * @large
224
     * @throws \EdmondsCommerce\DoctrineStaticMeta\Exception\DoctrineStaticMetaException
225
     * @throws \ReflectionException
226
     */
227
    public function createDatabaseSchema()
228
    {
229
        $this->createDatabase();
230
        $entity   = $this->getEntity();
231
        $setValue = null;
232
        if (false !== static::HAS_SETTER) {
0 ignored issues
show
introduced by
The condition false !== static::HAS_SETTER is always true.
Loading history...
233
            $setValue = $this->setFakerValueForProperty($entity);
234
        }
235
        $saver = $this->container->get(EntitySaver::class);
236
        $saver->save($entity);
237
        $reloadedEntity = $this->clearEntityManagerAndReloadEntity();
238
        $getter         = $this->getGetter($entity);
239
        $gotValue       = $reloadedEntity->$getter();
240
        if (false !== static::HAS_SETTER) {
0 ignored issues
show
introduced by
The condition false !== static::HAS_SETTER is always true.
Loading history...
241
            self::assertEquals($setValue, $gotValue);
242
243
            return;
244
        }
245
        self::assertNotNull($gotValue);
246
    }
247
248
    protected function clearEntityManagerAndReloadEntity(): EntityInterface
249
    {
250
        $this->getEntityManager()->clear();
251
        $repository = $this->getRepositoryFactory()->getRepository($this->getEntityFqn());
252
        $entities   = $repository->findAll();
253
254
        return current($entities);
255
    }
256
257
    /**
258
     * @test
259
     * @large
260
     */
261
    public function validValuesAreAccepted(): void
262
    {
263
        if (false === static::VALIDATES) {
0 ignored issues
show
introduced by
The condition false === static::VALIDATES is always false.
Loading history...
264
            self::markTestSkipped('This field does has no validation');
265
        }
266
        if (false === static::HAS_SETTER) {
0 ignored issues
show
introduced by
The condition false === static::HAS_SETTER is always false.
Loading history...
267
            self::markTestSkipped('No setter for this field');
268
        }
269
        if ([] === static::VALID_VALUES) {
270
            self::fail('You need to assign some valid values to ' . static::class . '::VALID_VALUES');
271
        }
272
        $entity = $this->getEntity();
273
        $setter = 'set' . static::TEST_FIELD_PROP;
274
        $getter = $this->getGetter($entity);
275
        foreach (static::VALID_VALUES as $value) {
276
            $this->updateWithDto($setter, $entity, $value);
277
            self::assertSame($value, $entity->$getter());
278
        }
279
    }
280
281
    /**
282
     * @test
283
     * @large
284
     * @dataProvider invalidValuesProvider
285
     */
286
    public function invalidValuesAreNotAccepted($invalidValue): void
287
    {
288
        if (false === static::VALIDATES) {
0 ignored issues
show
introduced by
The condition false === static::VALIDATES is always false.
Loading history...
289
            self::markTestSkipped('This field does has no validation');
290
        }
291
        if (false === static::HAS_SETTER) {
0 ignored issues
show
introduced by
The condition false === static::HAS_SETTER is always false.
Loading history...
292
            self::markTestSkipped('No setter for this field');
293
        }
294
        $entity = $this->getEntity();
295
        $setter = 'set' . static::TEST_FIELD_PROP;
296
        $this->expectException(ValidationException::class);
297
        try {
298
            $this->updateWithDto($setter, $entity, $invalidValue);
299
        } catch (\TypeError $e) {
300
            self::markTestSkipped(
301
                'You have set an INVALID_VALUE item of ' .
302
                $invalidValue .
303
                ' which has caused a TypeError as the setter does not accept this type of value.'
304
            );
305
        }
306
    }
307
308
    /**
309
     * Yield the invalid data, keyed by a namespace safe version of the value
310
     *
311
     * @return \Generator
312
     */
313
    public function invalidValuesProvider(): \Generator
314
    {
315
        if (false === static::VALIDATES) {
0 ignored issues
show
introduced by
The condition false === static::VALIDATES is always false.
Loading history...
316
            self::markTestSkipped('This field does not validate');
317
        }
318
        if ([] === static::INVALID_VALUES) {
319
            self::fail('You need to assign some invalid values to ' . static::class . '::INVALID_VALUES');
320
        }
321
        foreach (static::INVALID_VALUES as $invalidValue) {
322
            yield $invalidValue => [$invalidValue];
323
        }
324
    }
325
}
326