Passed
Pull Request — master (#1696)
by Nico
49:43 queued 22:34
created

PlanetFieldRepository::getMaxShieldsOfColony()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 27
Code Lines 23

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
cc 1
eloc 23
c 0
b 0
f 0
nc 1
nop 1
dl 0
loc 27
ccs 0
cts 17
cp 0
crap 2
rs 9.552
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Stu\Orm\Repository;
6
7
use Doctrine\ORM\EntityRepository;
8
use Doctrine\ORM\Query\ResultSetMapping;
9
use Stu\Component\Building\BuildingEnum;
10
use Stu\Lib\Colony\PlanetFieldHostInterface;
11
use Stu\Orm\Entity\Building;
12
use Stu\Orm\Entity\BuildingCommodity;
13
use Stu\Orm\Entity\BuildingFunction;
14
use Stu\Orm\Entity\Colony;
15
use Stu\Orm\Entity\ColonyInterface;
16
use Stu\Orm\Entity\PlanetField;
17
use Stu\Orm\Entity\PlanetFieldInterface;
18
19
/**
20
 * @extends EntityRepository<PlanetField>
21
 */
22
final class PlanetFieldRepository extends EntityRepository implements PlanetFieldRepositoryInterface
23
{
24
    public function prototype(): PlanetFieldInterface
25
    {
26
        return new PlanetField();
27
    }
28
29
    public function save(PlanetFieldInterface $planetField): void
30
    {
31
        $em = $this->getEntityManager();
32
33
        $em->persist($planetField);
34
    }
35
36
    public function delete(PlanetFieldInterface $planetField): void
37
    {
38
        $em = $this->getEntityManager();
39
40
        $em->remove($planetField);
41
        $em->flush();
42
    }
43
44
    public function getByColonyAndFieldId(int $colonyId, int $fieldId): ?PlanetFieldInterface
45
    {
46
        return $this->findOneBy([
47
            'colonies_id' => $colonyId,
48
            'id' => $fieldId
49
        ]);
50
    }
51
52
    public function getByColonyAndFieldIndex(int $colonyId, int $fieldIndex): ?PlanetFieldInterface
53
    {
54
        return $this->findOneBy([
55
            'colonies_id' => $colonyId,
56
            'field_id' => $fieldIndex
57
        ]);
58
    }
59
60
    public function getByColonyAndType(int $colonyId, int $planetFieldTypeId): array
61
    {
62
        return $this->findBy([
63
            'colonies_id' => $colonyId,
64
            'type_id' => $planetFieldTypeId,
65
        ]);
66
    }
67
68
    public function getEnergyConsumingByHost(
69
        PlanetFieldHostInterface $host,
70
        array $state = [0, 1],
71
        ?int $limit = null,
72
        array $excludedFields = [-1]
73
    ): array {
74
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...ts($limit)->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
75
            sprintf(
76
                'SELECT f FROM %s f
77
                WHERE f.%s = :hostId
78
                AND f.aktiv IN (:state)
79
                AND f.field_id NOT IN (:excluded)
80
                AND f.buildings_id IN (
81
                    SELECT b.id FROM %s b WHERE b.eps_proc < 0
82
                )',
83
                PlanetField::class,
84
                $host->getPlanetFieldHostColumnIdentifier(),
85
                Building::class
86
            )
87
        )->setParameters([
88
            'hostId' => $host->getId(),
89
            'state' => $state,
90
            'excluded' => $excludedFields
91
        ])
92
            ->setMaxResults($limit)
93
            ->getResult();
94
    }
95
96
    public function getEnergyProducingByHost(PlanetFieldHostInterface $host): array
97
    {
98
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...>getId()))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
99
            sprintf(
100
                'SELECT f FROM %s f
101
                WHERE f.%s = :hostId AND f.buildings_id IN (
102
                    SELECT b.id FROM %s b WHERE b.eps_proc > 0
103
                )',
104
                PlanetField::class,
105
                $host->getPlanetFieldHostColumnIdentifier(),
106
                Building::class
107
            )
108
        )->setParameters([
109
            'hostId' => $host->getId()
110
        ])->getResult();
111
    }
112
113
    public function getHousingProvidingByHost(PlanetFieldHostInterface $host): array
114
    {
115
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...>getId()))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
116
            sprintf(
117
                'SELECT f FROM %s f
118
                WHERE f.%s = :hostId AND f.buildings_id IN (
119
                    SELECT b.id FROM %s b WHERE b.bev_pro > 0
120
                )',
121
                PlanetField::class,
122
                $host->getPlanetFieldHostColumnIdentifier(),
123
                Building::class
124
            )
125
        )->setParameters([
126
            'hostId' => $host->getId()
127
        ])->getResult();
128
    }
129
130
    public function getWorkerConsumingByHost(PlanetFieldHostInterface $host): array
131
    {
132
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...>getId()))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
133
            sprintf(
134
                'SELECT f FROM %s f
135
                WHERE f.%s = :hostId AND f.buildings_id IN (
136
                    SELECT b.id FROM %s b WHERE b.bev_use > 0
137
                )',
138
                PlanetField::class,
139
                $host->getPlanetFieldHostColumnIdentifier(),
140
                Building::class
141
            )
142
        )->setParameters([
143
            'hostId' => $host->getId(),
144
        ])->getResult();
145
    }
146
147
    public function getWorkerConsumingByColonyAndState(
148
        int $colonyId,
149
        array $state = [0, 1],
150
        ?int $limit = null,
151
        array $excludedFields = [-1]
152
    ): array {
153
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...ts($limit)->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
154
            sprintf(
155
                'SELECT f FROM %s f
156
                WHERE f.colonies_id = :colonyId
157
                AND f.aktiv IN (:state)
158
                AND f.field_id NOT IN (:excluded)
159
                AND f.buildings_id IN (
160
                    SELECT b.id FROM %s b WHERE b.bev_use > 0
161
                )',
162
                PlanetField::class,
163
                Building::class
164
            )
165
        )->setParameters([
166
            'colonyId' => $colonyId,
167
            'state' => $state,
168
            'excluded' => $excludedFields
169
        ])
170
            ->setMaxResults($limit)
171
            ->getResult();
172
    }
173
174
    public function getCommodityConsumingByHostAndCommodity(
175
        PlanetFieldHostInterface $host,
176
        int $commodityId,
177
        array $state = [0, 1],
178
        ?int $limit = null,
179
        array $excludedFields = [-1]
180
    ): array {
181
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...ts($limit)->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
182
            sprintf(
183
                'SELECT f FROM %s f
184
                WHERE f.%s = :hostId
185
                AND f.field_id NOT IN (:excluded)
186
                AND f.buildings_id IN (
187
                    SELECT bg.buildings_id FROM %s bg WHERE bg.commodity_id = :commodityId AND bg.count < 0
188
                ) AND f.aktiv IN (:state)',
189
                PlanetField::class,
190
                $host->getPlanetFieldHostColumnIdentifier(),
191
                BuildingCommodity::class
192
            )
193
        )->setParameters([
194
            'hostId' => $host->getId(),
195
            'commodityId' => $commodityId,
196
            'state' => $state,
197
            'excluded' => $excludedFields
198
        ])
199
            ->setMaxResults($limit)
200
            ->getResult();
201
    }
202
203
    public function getCommodityProducingByHostAndCommodity(PlanetFieldHostInterface $host, int $commodityId): array
204
    {
205
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...modityId))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
206
            sprintf(
207
                'SELECT f FROM %s f
208
                WHERE f.%s = :hostId AND f.buildings_id IN (
209
                    SELECT bg.buildings_id FROM %s bg WHERE bg.commodity_id = :commodityId AND bg.count > 0
210
                )',
211
                PlanetField::class,
212
                $host->getPlanetFieldHostColumnIdentifier(),
213
                BuildingCommodity::class
214
            )
215
        )->setParameters([
216
            'hostId' => $host->getId(),
217
            'commodityId' => $commodityId,
218
        ])->getResult();
219
    }
220
221
    public function getCountByHostAndBuilding(PlanetFieldHostInterface $host, int $buildingId): int
222
    {
223
        return $this->count([
224
            $host->getPlanetFieldHostColumnIdentifier() => $host->getId(),
225
            'buildings_id' => $buildingId,
226
        ]);
227
    }
228
229
    public function getCountByBuildingAndUser(int $buildingId, int $userId): int
230
    {
231
        return (int) $this->getEntityManager()->createQuery(
232
            sprintf(
233
                'SELECT COUNT(f) FROM %s f WHERE f.buildings_id = :buildingId AND f.colonies_id IN (
234
                    SELECT c.id FROM %s c WHERE c.user_id = :userId
235
                )',
236
                PlanetField::class,
237
                Colony::class
238
            )
239
        )->setParameters([
240
            'buildingId' => $buildingId,
241
            'userId' => $userId,
242
        ])->getSingleScalarResult();
243
    }
244
245
    public function getCountByColonyAndBuildingFunctionAndState(
246
        PlanetFieldHostInterface $host,
247
        array $buildingFunctionIds,
248
        array $state
249
    ): int {
250
        return (int) $this->getEntityManager()->createQuery(
251
            sprintf(
252
                'SELECT COUNT(f) FROM %s f
253
                WHERE f.%s = :host AND f.aktiv IN(:state) AND f.buildings_id IN (
254
                    SELECT bf.buildings_id FROM %s bf WHERE bf.function IN (:buildingFunctionIds)
255
                )',
256
                PlanetField::class,
257
                $host->getPlanetFieldHostIdentifier(),
258
                BuildingFunction::class
259
            )
260
        )->setParameters([
261
            'host' => $host,
262
            'buildingFunctionIds' => $buildingFunctionIds,
263
            'state' => $state,
264
        ])->getSingleScalarResult();
265
    }
266
267
    public function getByColonyAndBuildingFunction(
268
        int $colonyId,
269
        array $buildingFunctionIds
270
    ): array {
271
        return $this->getEntityManager()
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...ctionIds))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
272
            ->createQuery(
273
                sprintf(
274
                    'SELECT f FROM %s f WHERE f.colonies_id = :colonyId AND f.buildings_id IN (
275
                        SELECT bf.buildings_id FROM %s bf WHERE bf.function IN (:buildingFunctionId)
276
                    )',
277
                    PlanetField::class,
278
                    BuildingFunction::class
279
                )
280
            )
281
            ->setParameters([
282
                'colonyId' => $colonyId,
283
                'buildingFunctionId' => $buildingFunctionIds
284
            ])
285
            ->getResult();
286
    }
287
288
    public function getMaxShieldsOfHost(PlanetFieldHostInterface $host): int
289
    {
290
        $rsm = new ResultSetMapping();
291
        $rsm->addScalarResult('capacity', 'capacity');
292
293
        return (int) $this->getEntityManager()->createNativeQuery(
294
            sprintf(
295
                'SELECT COUNT(distinct f1.id) * :generatorCapacity + COUNT(distinct f2.id) * :batteryCapacity as capacity
296
            FROM stu_colonies_fielddata f1
297
            LEFT JOIN stu_colonies_fielddata f2
298
            ON f1.colonies_id = f2.colonies_id
299
            AND f2.aktiv = 1 AND f2.buildings_id IN (
300
                SELECT bf2.buildings_id FROM stu_buildings_functions bf2 WHERE bf2.function = :shieldBattery
301
            )
302
            WHERE f1.%s = :hostId AND f1.aktiv = 1 AND f1.buildings_id IN (
303
                SELECT bf1.buildings_id FROM stu_buildings_functions bf1 WHERE bf1.function = :shieldGenerator
304
            )',
305
                $host->getPlanetFieldHostColumnIdentifier()
306
            ),
307
            $rsm
308
        )->setParameters([
309
            'hostId' => $host->getId(),
310
            'shieldGenerator' => BuildingEnum::BUILDING_FUNCTION_SHIELD_GENERATOR,
311
            'shieldBattery' => BuildingEnum::BUILDING_FUNCTION_SHIELD_BATTERY,
312
            'generatorCapacity' => BuildingEnum::SHIELD_GENERATOR_CAPACITY,
313
            'batteryCapacity' => BuildingEnum::SHIELD_BATTERY_CAPACITY
314
        ])->getSingleScalarResult();
315
    }
316
317
    public function getInConstructionByUser(int $userId): array
318
    {
319
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM... $userId))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
320
            sprintf(
321
                'SELECT f FROM %s f WHERE f.aktiv > 1 AND f.colonies_id IN (
322
                    SELECT c.id FROM %s c WHERE c.user_id = :userId
323
                ) ORDER BY f.aktiv',
324
                PlanetField::class,
325
                Colony::class
326
            )
327
        )->setParameters([
328
            'userId' => $userId,
329
        ])->getResult();
330
    }
331
332
    public function getByConstructionFinish(int $finishTime): array
333
    {
334
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...nishTime))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
335
            sprintf(
336
                'SELECT f FROM %s f WHERE f.aktiv BETWEEN 2 AND :finishTime',
337
                PlanetField::class
338
            )
339
        )->setParameters([
340
            'finishTime' => $finishTime,
341
        ])->getResult();
342
    }
343
344
    public function getByColonyWithBuilding(PlanetFieldHostInterface $host): array
345
    {
346
        return $this->getEntityManager()->createQuery(
1 ignored issue
show
Bug Best Practice introduced by
The expression return $this->getEntityM...>getId()))->getResult() could return the type integer which is incompatible with the type-hinted return array. Consider adding an additional type-check to rule them out.
Loading history...
347
            sprintf(
348
                'SELECT f FROM %s f
349
                JOIN %s b
350
                WITH f.buildings_id = b.id
351
                WHERE f.%s = :hostId
352
                AND f.buildings_id > 0
353
                ORDER BY b.name ASC',
354
                PlanetField::class,
355
                Building::class,
356
                $host->getPlanetFieldHostColumnIdentifier(),
357
            )
358
        )->setParameters([
359
            'hostId' => $host->getId(),
360
        ])->getResult();
361
    }
362
363
    public function getEnergyProductionByHost(
364
        PlanetFieldHostInterface $host,
365
        array $excludedFields = [-1]
366
    ): int {
367
        return (int) $this->getEntityManager()->createQuery(
368
            sprintf(
369
                'SELECT SUM(b.eps_proc)
370
                FROM %s cfd
371
                LEFT JOIN %s b WITH b.id = cfd.buildings_id
372
                WHERE cfd.aktiv = :state
373
                AND cfd.field_id NOT IN (:excluded)
374
                AND cfd.%s = :host',
375
                PlanetField::class,
376
                Building::class,
377
                $host->getPlanetFieldHostIdentifier()
378
            )
379
        )->setParameters([
380
            'state' => 1,
381
            'host' => $host,
382
            'excluded' => $excludedFields
383
        ])->getSingleScalarResult();
384
    }
385
386
    public function truncateByColony(ColonyInterface $colony): void
387
    {
388
        $this->getEntityManager()->createQuery(
389
            sprintf(
390
                'DELETE FROM %s pf WHERE pf.colonies_id = :colonyId',
391
                PlanetField::class
392
            )
393
        )
394
            ->setParameters(['colonyId' => $colony])
395
            ->execute();
396
    }
397
}
398