Completed
Push — symfony3-wololo ( ab614e )
by Kamil
65:18 queued 29:29
created

AbstractDriver::addRepository()

Size

Total Lines 1

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 1
c 0
b 0
f 0
nc 1
1
<?php
2
3
/*
4
 * This file is part of the Sylius package.
5
 *
6
 * (c) Paweł Jędrzejewski
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
namespace Sylius\Bundle\ResourceBundle\DependencyInjection\Driver;
13
14
use Sylius\Component\Resource\Factory\Factory;
15
use Sylius\Component\Resource\Factory\TranslatableFactoryInterface;
16
use Sylius\Component\Resource\Metadata\Metadata;
17
use Sylius\Component\Resource\Metadata\MetadataInterface;
18
use Symfony\Component\DependencyInjection\ContainerBuilder;
19
use Symfony\Component\DependencyInjection\Definition;
20
use Symfony\Component\DependencyInjection\Parameter;
21
use Symfony\Component\DependencyInjection\Reference;
22
23
/**
24
 * @author Paweł Jędrzejewski <[email protected]>
25
 * @author Arnaud Langlade <[email protected]>
26
 */
27
abstract class AbstractDriver implements DriverInterface
28
{
29
    /**
30
     * {@inheritdoc}
31
     */
32
    public function load(ContainerBuilder $container, MetadataInterface $metadata)
33
    {
34
        $this->setClassesParameters($container, $metadata);
35
36
        if ($metadata->hasClass('controller')) {
37
            $this->addController($container, $metadata);
38
        }
39
40
        $this->addManager($container, $metadata);
41
        $this->addRepository($container, $metadata);
42
43
        if ($metadata->hasClass('factory')) {
44
            $this->addFactory($container, $metadata);
45
        }
46
    }
47
48
    /**
49
     * @param ContainerBuilder $container
50
     * @param MetadataInterface $metadata
51
     */
52
    protected function setClassesParameters(ContainerBuilder $container, MetadataInterface $metadata)
53
    {
54
        if ($metadata->hasClass('model')) {
55
            $container->setParameter(sprintf('%s.model.%s.class', $metadata->getApplicationName(), $metadata->getName()), $metadata->getClass('model'));
56
        }
57
        if ($metadata->hasClass('controller')) {
58
            $container->setParameter(sprintf('%s.controller.%s.class', $metadata->getApplicationName(), $metadata->getName()), $metadata->getClass('controller'));
59
        }
60
        if ($metadata->hasClass('factory')) {
61
            $container->setParameter(sprintf('%s.factory.%s.class', $metadata->getApplicationName(), $metadata->getName()), $metadata->getClass('factory'));
62
        }
63
        if ($metadata->hasClass('repository')) {
64
            $container->setParameter(sprintf('%s.repository.%s.class', $metadata->getApplicationName(), $metadata->getName()), $metadata->getClass('repository'));
65
        }
66
    }
67
68
    /**
69
     * @param ContainerBuilder $container
70
     * @param MetadataInterface $metadata
71
     */
72
    protected function addController(ContainerBuilder $container, MetadataInterface $metadata)
73
    {
74
        $definition = new Definition($metadata->getClass('controller'));
0 ignored issues
show
Bug introduced by
It seems like $metadata->getClass('controller') targeting Sylius\Component\Resourc...taInterface::getClass() can also be of type array; however, Symfony\Component\Depend...finition::__construct() does only seem to accept string|null, maybe add an additional type check?

This check looks at variables that are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
75
        $definition
76
            ->setArguments([
77
                $this->getMetadataDefinition($metadata),
78
                new Reference('sylius.resource_controller.request_configuration_factory'),
79
                new Reference('sylius.resource_controller.view_handler'),
80
                new Reference($metadata->getServiceId('repository')),
81
                new Reference($metadata->getServiceId('factory')),
82
                new Reference('sylius.resource_controller.new_resource_factory'),
83
                new Reference($metadata->getServiceId('manager')),
84
                new Reference('sylius.resource_controller.single_resource_provider'),
85
                new Reference('sylius.resource_controller.resources_collection_provider'),
86
                new Reference('sylius.resource_controller.form_factory'),
87
                new Reference('sylius.resource_controller.redirect_handler'),
88
                new Reference('sylius.resource_controller.flash_helper'),
89
                new Reference('sylius.resource_controller.authorization_checker'),
90
                new Reference('sylius.resource_controller.event_dispatcher'),
91
                new Reference('sylius.resource_controller.state_machine'),
92
            ])
93
            ->addMethodCall('setContainer', [new Reference('service_container')])
94
        ;
95
96
        $container->setDefinition($metadata->getServiceId('controller'), $definition);
97
    }
98
99
    /**
100
     * @param ContainerBuilder $container
101
     * @param MetadataInterface $metadata
102
     */
103
    protected function addFactory(ContainerBuilder $container, MetadataInterface $metadata)
104
    {
105
        $factoryClass = $metadata->getClass('factory');
106
        $modelClass = $metadata->getClass('model');
107
108
        $definition = new Definition($factoryClass);
0 ignored issues
show
Bug introduced by
It seems like $factoryClass defined by $metadata->getClass('factory') on line 105 can also be of type array; however, Symfony\Component\Depend...finition::__construct() does only seem to accept string|null, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
109
110
        $definitionArgs = [$modelClass];
111
        if (in_array(TranslatableFactoryInterface::class, class_implements($factoryClass))) {
112
            $decoratedDefinition = new Definition(Factory::class);
113
            $decoratedDefinition->setArguments($definitionArgs);
114
115
            $definitionArgs = [$decoratedDefinition, new Reference('sylius_resource.translation.locale_provider')];
116
        }
117
118
        $definition->setArguments($definitionArgs);
119
120
        $container->setDefinition($metadata->getServiceId('factory'), $definition);
121
    }
122
123
    /**
124
     * @param MetadataInterface $metadata
125
     *
126
     * @return Definition
127
     */
128
    protected function getMetadataDefinition(MetadataInterface $metadata)
129
    {
130
        $definition = new Definition(Metadata::class);
131
        $definition
132
            ->setFactory([new Reference('sylius.resource_registry'), 'get'])
133
            ->setArguments([$metadata->getAlias()])
134
        ;
135
136
        return $definition;
137
    }
138
139
    /**
140
     * @param ContainerBuilder $container
141
     * @param MetadataInterface $metadata
142
     */
143
    abstract protected function addManager(ContainerBuilder $container, MetadataInterface $metadata);
0 ignored issues
show
Documentation introduced by
For interfaces and abstract methods it is generally a good practice to add a @return annotation even if it is just @return void or @return null, so that implementors know what to do in the overridden method.

For interface and abstract methods, it is impossible to infer the return type from the immediate code. In these cases, it is generally advisible to explicitly annotate these methods with a @return doc comment to communicate to implementors of these methods what they are expected to return.

Loading history...
144
145
    /**
146
     * @param ContainerBuilder $container
147
     * @param MetadataInterface $metadata
148
     */
149
    abstract protected function addRepository(ContainerBuilder $container, MetadataInterface $metadata);
0 ignored issues
show
Documentation introduced by
For interfaces and abstract methods it is generally a good practice to add a @return annotation even if it is just @return void or @return null, so that implementors know what to do in the overridden method.

For interface and abstract methods, it is impossible to infer the return type from the immediate code. In these cases, it is generally advisible to explicitly annotate these methods with a @return doc comment to communicate to implementors of these methods what they are expected to return.

Loading history...
150
}
151