Completed
Push — symfony3 ( a82edd...ec9673 )
by Kamil
17:27
created

CreatePage::nameIt()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 7
rs 9.4285
cc 1
eloc 4
nc 1
nop 2
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\Behat\Page\Admin\Taxon;
13
14
use Behat\Mink\Driver\Selenium2Driver;
15
use Behat\Mink\Element\NodeElement;
16
use Behat\Mink\Exception\ElementNotFoundException;
17
use Behat\Mink\Exception\UnsupportedDriverActionException;
18
use Sylius\Behat\Behaviour\SpecifiesItsCode;
19
use Sylius\Behat\Page\Admin\Crud\CreatePage as BaseCreatePage;
20
use Sylius\Component\Core\Model\TaxonInterface;
21
use Webmozart\Assert\Assert;
22
23
/**
24
 * @author Arkadiusz Krakowiak <[email protected]>
25
 */
26
class CreatePage extends BaseCreatePage implements CreatePageInterface
27
{
28
    use SpecifiesItsCode;
29
30
    /**
31
     * {@inheritdoc}
32
     */
33
    public function countTaxons()
34
    {
35
        return count($this->getLeaves());
36
    }
37
38
    /**
39
     * {@inheritdoc}
40
     */
41
    public function countTaxonsByName($name)
42
    {
43
        $matchedLeavesCounter = 0;
44
        $leaves = $this->getLeaves();
45
        foreach ($leaves as $leaf) {
0 ignored issues
show
Bug introduced by
The expression $leaves of type array<integer,object<Beh...ment\NodeElement>>|null is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
46
            if (strpos($leaf->getText(), $name) !== false) {
47
                $matchedLeavesCounter++;
48
            }
49
        }
50
51
        return $matchedLeavesCounter;
52
    }
53
54
    /**
55
     * {@inheritdoc}
56
     */
57
    public function chooseParent(TaxonInterface $taxon)
58
    {
59
        $this->getElement('parent')->selectOption($taxon->getName(), false);
60
    }
61
62
    /**
63
     * {@inheritdoc}
64
     */
65
    public function deleteTaxonOnPageByName($name)
66
    {
67
        $leaves = $this->getLeaves();
68
        foreach ($leaves as $leaf) {
0 ignored issues
show
Bug introduced by
The expression $leaves of type array<integer,object<Beh...ment\NodeElement>>|null is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
69
            if ($leaf->getText() === $name) {
70
                $leaf->getParent()->find('css', '.ui.red.button')->press();
71
72
                return;
73
            }
74
        }
75
76
        throw new ElementNotFoundException($this->getDriver(), 'Delete button');
77
    }
78
79
    /**
80
     * {@inheritdoc}
81
     */
82
    public function describeItAs($description, $languageCode)
83
    {
84
        $this->getDocument()->fillField(sprintf('sylius_taxon_translations_%s_description', $languageCode), $description);
85
    }
86
87
    /**
88
     * {@inheritdoc}
89
     */
90
    public function hasTaxonWithName($name)
91
    {
92
        return 0 !== $this->countTaxonsByName($name);
93
    }
94
95
    /**
96
     * {@inheritdoc}
97
     */
98
    public function nameIt($name, $languageCode)
99
    {
100
        $this->activateLanguageTab($languageCode);
101
        $this->getElement('name', ['%language%' => $languageCode])->setValue($name);
102
103
        $this->waitForSlugGenerationIfNecessary($languageCode);
104
    }
105
106
    /**
107
     * {@inheritdoc}
108
     */
109
    public function specifySlug($slug, $languageCode)
110
    {
111
        $this->getDocument()->fillField(sprintf('sylius_taxon_translations_%s_slug', $languageCode), $slug);
112
    }
113
114
    /**
115
     * {@inheritdoc}
116
     */
117
    public function attachImage($path, $code = null)
118
    {
119
        $filesPath = $this->getParameter('files_path');
120
121
        $this->getDocument()->find('css', '[data-form-collection="add"]')->click();
122
123
        $imageForm = $this->getLastImageElement();
124
        $imageForm->fillField('Code', $code);
125
        $imageForm->find('css', 'input[type="file"]')->attachFile($filesPath.$path);
126
    }
127
128
    /**
129
     * {@inheritDoc}
130
     */
131
    public function moveUp(TaxonInterface $taxon)
132
    {
133
        $this->moveLeaf($taxon, self::MOVE_DIRECTION_UP);
134
    }
135
136
    /**
137
     * {@inheritDoc}
138
     */
139
    public function moveDown(TaxonInterface $taxon)
140
    {
141
        $this->moveLeaf($taxon, self::MOVE_DIRECTION_DOWN);
142
    }
143
144
    /**
145
     * {@inheritDoc}
146
     */
147
    public function getLeafNameFromPosition($position, TaxonInterface $parentTaxon = null)
148
    {
149
        $firstTaxonElement = $this->getLeaves($parentTaxon)[0];
150
151
        return $firstTaxonElement->getText();
152
    }
153
154
    /**
155
     * {@inheritdoc}
156
     */
157
    public function getLeaves(TaxonInterface $parentTaxon = null)
158
    {
159
        $tree = $this->getElement('tree');
160
        Assert::notNull($tree);
161
        /** @var NodeElement[] $leaves */
162
        $leaves = $tree->findAll('css', '.item > .content > .header > a');
163
164
        if (null === $parentTaxon) {
165
            return $leaves;
166
        }
167
168
        foreach ($leaves as $leaf) {
169
            if ($leaf->getText() === $parentTaxon->getName()) {
170
                return $leaf->findAll('css', '.item > .content > .header');
171
            }
172
        }
173
    }
174
175
    /**
176
     * {@inheritdoc}
177
     */
178
    public function waitForTaxonRelocation(TaxonInterface $taxon, $expectedPosition)
179
    {
180
        $this->getDocument()->waitFor(5, function () use ($taxon, $expectedPosition) {
181
            return $this->getLeafNameFromPosition($expectedPosition) === $taxon->getName();
182
        });
183
    }
184
185
    /**
186
     * {@inheritdoc}
187
     */
188
    public function activateLanguageTab($locale)
189
    {
190
        if (!$this->getDriver() instanceof Selenium2Driver) {
191
            return;
192
        }
193
194
        $languageTabTitle = $this->getElement('language_tab', ['%locale%' => $locale]);
195
        if (!$languageTabTitle->hasClass('active')) {
196
            $languageTabTitle->click();
197
        }
198
    }
199
200
    /**
201
     * {@inheritdoc}
202
     */
203
    protected function getElement($name, array $parameters = [])
204
    {
205
        if (!isset($parameters['%language%'])) {
206
            $parameters['%language%'] = 'en_US';
207
        }
208
209
        return parent::getElement($name, $parameters);
210
    }
211
212
    /**
213
     * {@inheritdoc}
214
     */
215
    protected function getDefinedElements()
216
    {
217
        return array_merge(parent::getDefinedElements(), [
218
            'code' => '#sylius_taxon_code',
219
            'description' => '#sylius_taxon_translations_en_US_description',
220
            'images' => '#sylius_taxon_images',
221
            'language_tab' => '[data-locale="%locale%"] .title',
222
            'name' => '#sylius_taxon_translations_%language%_name',
223
            'parent' => '#sylius_taxon_parent',
224
            'slug' => '#sylius_taxon_translations_%language%_slug',
225
            'tree' => '.ui.list',
226
        ]);
227
    }
228
229
    /**
230
     * @param TaxonInterface $taxon
231
     * @param string $direction
232
     *
233
     * @throws ElementNotFoundException
234
     */
235
    private function moveLeaf(TaxonInterface $taxon, $direction)
236
    {
237
        Assert::oneOf($direction, [self::MOVE_DIRECTION_UP, self::MOVE_DIRECTION_DOWN]);
238
239
        $leaves = $this->getLeaves();
240
        foreach ($leaves as $leaf) {
0 ignored issues
show
Bug introduced by
The expression $leaves of type array<integer,object<Beh...ment\NodeElement>>|null is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
241
            if ($leaf->getText() === $taxon->getName()) {
242
                $moveButton = $leaf->getParent()->find('css', sprintf('.sylius-taxon-move-%s', $direction));
243
                $moveButton->click();
244
245
                return;
246
            }
247
        }
248
249
        throw new ElementNotFoundException(
250
            $this->getDriver(),
251
            sprintf('Move %s button for %s taxon', $direction, $taxon->getName())
252
        );
253
    }
254
255
    /**
256
     * @return NodeElement
257
     */
258
    private function getLastImageElement()
259
    {
260
        $images = $this->getElement('images');
261
        $items = $images->findAll('css', 'div[data-form-collection="item"]');
262
263
        Assert::notEmpty($items);
264
265
        return end($items);
266
    }
267
268
    /**
269
     * @param string $languageCode
270
     */
271
    private function waitForSlugGenerationIfNecessary($languageCode)
272
    {
273
        if ($this->getDriver() instanceof Selenium2Driver) {
274
            $this->getDocument()->waitFor(10, function () use ($languageCode) {
275
                return '' !== $this->getElement('slug', ['%language%' => $languageCode])->getValue();
276
            });
277
        }
278
    }
279
}
280