Completed
Pull Request — master (#20)
by Eric
02:44
created

AbstractAliceContext::getLoader()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 4
rs 10
cc 1
eloc 2
nc 1
nop 0
1
<?php
2
3
/*
4
 * This file is part of the Fidry\AliceBundleExtension package.
5
 *
6
 * (c) Théo FIDRY <[email protected]>
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 Fidry\AliceBundleExtension\Context\Doctrine;
13
14
use Behat\Gherkin\Node\TableNode;
15
use Behat\Symfony2Extension\Context\KernelAwareContext;
16
use Doctrine\Common\Persistence\ObjectManager;
17
use Fidry\AliceBundleExtension\Context\AliceContextInterface;
18
use Hautelook\AliceBundle\Alice\DataFixtures\LoaderInterface;
19
use Hautelook\AliceBundle\Finder\FixturesFinderInterface;
20
use Nelmio\Alice\Persister\Doctrine;
21
use Nelmio\Alice\PersisterInterface;
22
use Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException;
23
use Symfony\Component\HttpKernel\KernelInterface;
24
25
/**
26
 * Context to load fixtures files with Alice loader.
27
 *
28
 * @author Théo FIDRY <[email protected]>
29
 */
30
abstract class AbstractAliceContext implements KernelAwareContext, AliceContextInterface
31
{
32
    /**
33
     * @var string
34
     */
35
    protected $basePath;
36
37
    /**
38
     * @var KernelInterface
39
     */
40
    protected $kernel;
41
42
    /**
43
     * @param string|null $basePath
44
     */
45
    public function __construct($basePath = null)
46
    {
47
        $this->basePath = $basePath;
48
    }
49
50
    /**
51
     * {@inheritdoc}
52
     */
53
    public function setKernel(KernelInterface $kernel)
54
    {
55
        $this->kernel = $kernel;
56
    }
57
58
    /**
59
     * {@inheritdoc}
60
     */
61
    final public function setBasePath($basePath)
62
    {
63
        $this->basePath = $basePath;
64
65
        return $this;
66
    }
67
68
    /**
69
     * {@inheritdoc}
70
     */
71
    final public function getBasePath()
72
    {
73
        return $this->basePath;
74
    }
75
76
    /**
77
     * @Transform /^service$/
78
     *
79
     * @throws ServiceNotFoundException
80
     */
81
    public function castServiceIdToService($serviceId)
82
    {
83
        return $this->kernel->getContainer()->get($serviceId);
84
    }
85
86
    /**
87
     * @Transform /^persister$/
88
     *
89
     * @throws ServiceNotFoundException
90
     */
91
    public function castServiceIdToPersister($serviceId)
92
    {
93
        $service = $this->castServiceIdToService($serviceId);
94
95
        return $this->resolvePersister($service);
96
    }
97
98
    /**
99
     * {@inheritdoc}
100
     */
101
    public function thereAreFixtures($fixturesFile, $persister = null)
102
    {
103
        $this->loadFixtures([$fixturesFile], $persister);
104
    }
105
106
    /**
107
     * {@inheritdoc}
108
     */
109
    public function thereAreSeveralFixtures(TableNode $fixturesFileRows, $persister = null)
110
    {
111
        $fixturesFiles = [];
112
113
        foreach ($fixturesFileRows->getRows() as $fixturesFileRow) {
114
            $fixturesFiles[] = $fixturesFileRow[0];
115
        }
116
117
        $this->loadFixtures($fixturesFiles, $persister);
118
    }
119
120
    /**
121
     * @param array              $fixturesFiles
122
     * @param PersisterInterface $persister
123
     */
124
    private function loadFixtures($fixturesFiles, $persister = null)
125
    {
126
        if (null === $persister) {
127
            $persister = $this->getPersister();
0 ignored issues
show
Coding Style introduced by
Consider using a different name than the parameter $persister. This often makes code more readable.
Loading history...
128
        }
129
130
        if (true === is_string($persister)) {
131
            $persister = $this->castServiceIdToPersister($persister);
0 ignored issues
show
Coding Style introduced by
Consider using a different name than the parameter $persister. This often makes code more readable.
Loading history...
132
        }
133
134
        $fixtureBundles = [];
135
        $fixtureDirectories = [];
136
137
        foreach ($fixturesFiles as $key => $fixturesFile) {
138
            if (0 === strpos($fixturesFile, '/')) {
139
                if (is_dir($fixturesFile)) {
140
                    $fixtureDirectories[] = $fixturesFile;
141
                    unset($fixturesFiles[$key]);
142
                }
143
144
                continue;
145
            }
146
147
            if (0 === strpos($fixturesFile, '@')) {
148
                if (false === strpos($fixturesFile, '.')) {
149
                    $fixtureBundles[] = $this->kernel->getBundle(substr($fixturesFile, 1));
150
                    unset($fixturesFiles[$key]);
151
                }
152
153
                continue;
154
            }
155
156
            $fixturesFiles[$key] = sprintf('%s/%s', $this->basePath, $fixturesFile);
157
        }
158
159
        if (false === empty($fixtureBundles)) {
160
            $fixturesFiles = array_merge(
0 ignored issues
show
Coding Style introduced by
Consider using a different name than the parameter $fixturesFiles. This often makes code more readable.
Loading history...
161
                $fixturesFiles,
162
                $this->getFixturesFinder()->getFixtures($this->kernel, $fixtureBundles, $this->kernel->getEnvironment())
163
            );
164
        }
165
166
        if (false === empty($fixtureDirectories)) {
167
            $fixturesFiles = array_merge(
0 ignored issues
show
Coding Style introduced by
Consider using a different name than the parameter $fixturesFiles. This often makes code more readable.
Loading history...
168
                $fixturesFiles,
169
                $this->getFixturesFinder()->getFixturesFromDirectory($fixtureDirectories)
0 ignored issues
show
Documentation introduced by
$fixtureDirectories is of type array, but the function expects a string.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
170
            );
171
        }
172
173
        $this->getLoader()->load(
174
            $persister,
175
            $this->getFixturesFinder()->resolveFixtures($this->kernel, $fixturesFiles)
176
        );
177
    }
178
179
    /**
180
     * @param Doctrine|PersisterInterface|null $persister
181
     *
182
     * @return PersisterInterface
183
     *
184
     * @throws \InvalidArgumentException
185
     */
186
    final protected function resolvePersister($persister)
187
    {
188
        if (null === $persister) {
189
            return $this->getPersister();
190
        }
191
192
        switch (true) {
193
            case $persister instanceof PersisterInterface:
194
                return $persister;
195
            case $persister instanceof ObjectManager:
196
                return new Doctrine($persister);
197
198
            default:
199
                throw new \InvalidArgumentException(sprintf(
200
                    'Invalid persister type, expected Nelmio\Alice\PersisterInterface or Doctrine\Common\Persistence\ObjectManager. Got %s instead.',
201
                    get_class($persister)
202
                ));
203
        }
204
    }
205
206
    /**
207
     * @return LoaderInterface
208
     */
209
    protected function getLoader()
210
    {
211
        return $this->kernel->getContainer()->get('hautelook_alice.fixtures.loader');
212
    }
213
214
    /**
215
     * @return PersisterInterface
216
     */
217
    abstract protected function getPersister();
218
219
    /**
220
     * @return FixturesFinderInterface
221
     */
222
    abstract protected function getFixturesFinder();
223
}
224