Passed
Pull Request — 1.x (#35)
by Marko
05:54
created

FormReader   A

Complexity

Total Complexity 18

Size/Duplication

Total Lines 141
Duplicated Lines 0 %

Importance

Changes 0
Metric Value
wmc 18
eloc 72
dl 0
loc 141
rs 10
c 0
b 0
f 0

6 Methods

Rating   Name   Duplication   Size   Complexity  
A fillTabsAndGroupsWithFields() 0 29 6
A configureFields() 0 26 2
A configureEditFields() 0 7 1
A configureCreateFields() 0 7 1
A renderTabCollection() 0 25 4
A findTabsAndGroups() 0 22 4
1
<?php
2
3
declare(strict_types=1);
4
5
namespace KunicMarko\SonataAnnotationBundle\Reader;
6
7
use Doctrine\Common\Annotations\Reader;
8
use KunicMarko\SonataAnnotationBundle\Annotation;
9
use KunicMarko\SonataAnnotationBundle\Grouping\Field;
10
use KunicMarko\SonataAnnotationBundle\Grouping\Group;
11
use KunicMarko\SonataAnnotationBundle\Grouping\GroupCollection;
12
use KunicMarko\SonataAnnotationBundle\Grouping\Tab;
13
use KunicMarko\SonataAnnotationBundle\Grouping\TabCollection;
14
use Sonata\AdminBundle\Form\FormMapper;
15
16
/**
17
 * @author Marko Kunic <[email protected]>
18
 */
19
final class FormReader
20
{
21
    use AnnotationReaderTrait;
22
23
    private const DEFAULT_GROUP_NAME = '-';
24
25
    private const DEFAULT_TAB_NAME = 'default';
26
27
    public function configureCreateFields(\ReflectionClass $class, FormMapper $formMapper, ?string $defaultGroup = self::DEFAULT_GROUP_NAME): void
28
    {
29
        $this->configureFields(
30
            $class,
31
            $formMapper,
32
            Annotation\FormField::ACTION_EDIT,
33
            Group::with($defaultGroup)
0 ignored issues
show
Bug introduced by
It seems like $defaultGroup can also be of type null; however, parameter $name of KunicMarko\SonataAnnotat...\Grouping\Group::with() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

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

33
            Group::with(/** @scrutinizer ignore-type */ $defaultGroup)
Loading history...
34
        );
35
    }
36
37
    public function configureEditFields(\ReflectionClass $class, FormMapper $formMapper, ?string $defaultGroup = self::DEFAULT_GROUP_NAME): void
38
    {
39
        $this->configureFields(
40
            $class,
41
            $formMapper,
42
            Annotation\FormField::ACTION_CREATE,
43
            Group::with($defaultGroup)
0 ignored issues
show
Bug introduced by
It seems like $defaultGroup can also be of type null; however, parameter $name of KunicMarko\SonataAnnotat...\Grouping\Group::with() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

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

43
            Group::with(/** @scrutinizer ignore-type */ $defaultGroup)
Loading history...
44
        );
45
    }
46
47
    private function configureFields(\ReflectionClass $class, FormMapper $formMapper, string $action, Group $defaultGroup): void
48
    {
49
        $tabCollection = TabCollection::create();
50
        $groupCollection = GroupCollection::create();
51
        $groupCollection->add($defaultGroup);
52
53
        $this->findTabsAndGroups(
54
            $this->getClassAnnotations($class),
55
            $tabCollection,
56
            $groupCollection
57
        );
58
59
        $this->fillTabsAndGroupsWithFields(
60
            $class->getProperties(),
61
            $action,
62
            $defaultGroup->getName(),
63
            $tabCollection,
64
            $groupCollection
65
        );
66
67
        if ($tabCollection->isEmpty()) {
68
            $groupCollection->render($formMapper);
69
            return;
70
        }
71
72
        $this->renderTabCollection($formMapper, $tabCollection, $groupCollection);
73
    }
74
75
    private function findTabsAndGroups(
76
        array $annotations,
77
        TabCollection $tabCollection,
78
        GroupCollection $groupCollection
79
    ): void {
80
81
        foreach ($annotations as $annotation) {
82
            if ($annotation instanceof Annotation\Tab) {
83
                $tabCollection->add(Tab::with(
84
                    $annotation->getName(),
85
                    $annotation->options,
86
                    $annotation->position
87
                ));
88
                continue;
89
            }
90
91
            if ($annotation instanceof Annotation\Group) {
92
                $groupCollection->add(Group::with(
93
                    $annotation->getName(),
94
                    $annotation->options,
95
                    $annotation->tab,
96
                    $annotation->position
97
                ));
98
            }
99
        }
100
    }
101
102
    private function fillTabsAndGroupsWithFields(
103
        array $properties,
104
        string $action,
105
        string $defaultGroupName,
106
        TabCollection $tabCollection,
107
        GroupCollection $groupCollection
108
    ): void {
109
        foreach ($properties as $property) {
110
            foreach ($this->getPropertyAnnotations($property) as $annotation) {
111
                if (!$annotation instanceof Annotation\FormField || $annotation->action === $action) {
112
                    continue;
113
                }
114
115
                $field = Field::with(
116
                    $property->getName(),
117
                    $annotation->getSettings(),
118
                    $annotation->position,
119
                    $annotation->getGroup(),
120
                    $annotation->getTab()
121
                );
122
123
                if ($annotation->hasTab()) {
124
                    $tabCollection->get($annotation->getTab())
125
                        ->addField($field);
126
                    continue;
127
                }
128
129
                $groupCollection->get($annotation->getGroup() ?? $defaultGroupName)
130
                    ->addField($field);
131
            }
132
        }
133
    }
134
135
    private function renderTabCollection(
136
        FormMapper $formMapper,
137
        TabCollection $tabCollection,
138
        GroupCollection $groupCollection
139
    ): void {
140
        $tabCollection->add(Tab::with(self::DEFAULT_TAB_NAME));
141
142
        foreach ($groupCollection->all() as $group) {
143
            if ($group->getTabName() === null) {
144
                continue;
145
            }
146
147
            if ($tabCollection->has($group->getTabName() ?? self::DEFAULT_TAB_NAME)) {
148
                throw new \InvalidArgumentException(sprintf(
149
                    'Tab "%s" was not found, but was included in "%s" Group annotation.',
150
                    $group->getTabName(),
151
                    $group->getName()
152
                ));
153
            }
154
155
            $tabCollection->get($group->getTabName())
156
                ->addGroup($group);
157
        }
158
159
        $tabCollection->render($formMapper);
160
    }
161
}
162