AssociationFactory   A
last analyzed

Complexity

Total Complexity 10

Size/Duplication

Total Lines 75
Duplicated Lines 0 %

Importance

Changes 3
Bugs 0 Features 1
Metric Value
wmc 10
eloc 31
c 3
b 0
f 1
dl 0
loc 75
rs 10

4 Methods

Rating   Name   Duplication   Size   Complexity  
A getAssocationFromStubs() 0 6 2
A buildAssociationFromStubs() 0 16 3
A checkAssociations() 0 12 4
A marshalPolyToMono() 0 18 1
1
<?php
2
3
declare(strict_types=1);
4
5
6
namespace AlgoWeb\PODataLaravel\Models\ObjectMap\Entities\Associations;
7
8
use Illuminate\Support\Str;
9
10
abstract class AssociationFactory
11
{
12
    /** @var bool */
13
    public static $marshalPolymorphics = true;
14
15
    /**
16
     * @param  AssociationStubBase $stubOne
17
     * @param  AssociationStubBase $stubTwo
18
     * @throws \Exception
19
     * @return Association
20
     */
21
    public static function getAssocationFromStubs(
22
        AssociationStubBase $stubOne,
23
        AssociationStubBase $stubTwo
24
    ): Association {
25
        $checkAssociation = self::checkAssociations($stubOne, $stubTwo);
26
        return null === $checkAssociation ? self::buildAssociationFromStubs($stubOne, $stubTwo) : $checkAssociation;
27
    }
28
29
    /**
30
     * @param  AssociationStubBase $stubOne
31
     * @param  AssociationStubBase $stubTwo
32
     * @throws \Exception
33
     * @return Association
34
     */
35
    private static function buildAssociationFromStubs(
36
        AssociationStubBase $stubOne,
37
        AssociationStubBase $stubTwo
38
    ): Association {
39
        $first = -1 === $stubOne->compare($stubTwo);
40
41
        $association = new AssociationMonomorphic();
42
        if (null === $stubOne->getTargType() && self::$marshalPolymorphics) {
43
            $stubOne->addAssociation($association);
44
            $stubOne = self::marshalPolyToMono($stubOne, $stubTwo);
45
        }
46
47
        $input = [intval(!$first) => $stubOne, intval($first) => $stubTwo];
48
        $association->setFirst($input[0]);
49
        $association->setLast($input[1]);
50
        return $association;
51
    }
52
53
    private static function marshalPolyToMono(
54
        AssociationStubBase $stub,
55
        AssociationStubBase $stubTwo
56
    ): AssociationStubBase {
57
        $stubNew         = clone $stub;
58
        /** @var string $baseTwo */
59
        $baseTwo = $stubTwo->getBaseType();
60
        $relPolyTypeName = substr($baseTwo, strrpos($baseTwo, '\\')+1);
61
        $relPolyTypeName = Str::plural($relPolyTypeName, 1);
62
        $stubNew->setRelationName($stub->getRelationName() . '_' . $relPolyTypeName);
63
        $stubNew->setTargType($baseTwo);
64
        $stubNew->setForeignFieldName($stubTwo->getKeyFieldName());
65
        $entity = $stub->getEntity();
66
        $stubs  = $entity->getStubs();
67
68
        $stubs[$stubNew->getRelationName()] = $stubNew;
69
        $entity->setStubs($stubs);
70
        return $stubNew;
71
    }
72
73
    private static function checkAssociations(
74
        AssociationStubBase $stubOne,
75
        AssociationStubBase $stubTwo
76
    ): ?Association {
77
        $assocOne = $stubOne->getAssociations();
78
        foreach ($assocOne as $association) {
79
            $isFirst = $association->getFirst() === $stubOne;
80
            if ($association->{$isFirst ? 'getLast' : 'getFirst'}() == $stubTwo) {
81
                return $association;
82
            }
83
        }
84
        return null;
85
    }
86
}
87