Completed
Push — master ( 3cf394...e14e62 )
by Kamil
17:12 queued 16:56
created

ProductVariantApiTest::getVariantUrl()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 4
rs 10
c 0
b 0
f 0
cc 1
eloc 2
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\Tests\Controller;
13
14
use Lakion\ApiTestCase\JsonApiTestCase;
15
use Sylius\Bundle\ApiBundle\Form\Type\ProductVariantType;
16
use Sylius\Component\Core\Model\ProductInterface;
17
use Sylius\Component\Core\Model\ProductVariantInterface;
18
use Symfony\Component\HttpFoundation\Response;
19
20
/**
21
 * @author Anna Walasek <[email protected]>
22
 */
23
final class ProductVariantApiTest extends JsonApiTestCase
24
{
25
    /**
26
     * @var array
27
     */
28
    private static $authorizedHeaderWithContentType = [
29
        'HTTP_Authorization' => 'Bearer SampleTokenNjZkNjY2MDEwMTAzMDkxMGE0OTlhYzU3NzYyMTE0ZGQ3ODcyMDAwM2EwMDZjNDI5NDlhMDdlMQ',
30
        'CONTENT_TYPE' => 'application/json',
31
    ];
32
    
33
    /**
34
     * @var array
35
     */
36
    private static $authorizedHeaderWithAccept = [
37
        'HTTP_Authorization' => 'Bearer SampleTokenNjZkNjY2MDEwMTAzMDkxMGE0OTlhYzU3NzYyMTE0ZGQ3ODcyMDAwM2EwMDZjNDI5NDlhMDdlMQ',
38
        'ACCEPT' => 'application/json',
39
    ];
40
    
41
    /**
42
     * @test
43
     */
44
    public function it_does_not_allow_to_show_product_variant_list_when_access_is_denied()
45
    {
46
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
47
48
        /** @var ProductInterface $product */
49
        $product = $productVariantsData['product1'];
50
51
        $this->client->request('GET', $this->getVariantListUrl($product));
52
        $response = $this->client->getResponse();
53
54
        $this->assertResponse($response, 'authentication/access_denied_response', Response::HTTP_UNAUTHORIZED);
55
    }
56
57
    /**
58
     * @test
59
     */
60
    public function it_does_not_allow_to_show_product_variant_when_it_does_not_exist()
61
    {
62
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
63
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
64
65
        /** @var ProductInterface $product */
66
        $product = $productVariantsData['product1'];
67
68
        $this->client->request('GET', $this->getVariantListUrl($product) . 'code', [], [], static::$authorizedHeaderWithAccept);
69
        $response = $this->client->getResponse();
70
71
        $this->assertResponse($response, 'error/not_found_response', Response::HTTP_NOT_FOUND);
72
    }
73
74
    /**
75
     * @test
76
     */
77
    public function it_allows_showing_product_variant()
78
    {
79
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
80
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
81
82
        /** @var ProductInterface $product */
83
        $product = $productVariantsData['product1'];
84
85
        /** @var ProductVariantInterface $productVariant */
86
        $productVariant = $productVariantsData['productVariant2'];
87
88
        $this->client->request('GET', $this->getVariantUrl($product, $productVariant), [], [], static::$authorizedHeaderWithAccept);
89
        $response = $this->client->getResponse();
90
91
        $this->assertResponse($response, 'product_variant/show_response', Response::HTTP_OK);
92
    }
93
94
    /**
95
     * @test
96
     */
97
    public function it_allows_indexing_product_variants()
98
    {
99
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
100
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
101
102
        /** @var ProductInterface $product */
103
        $product = $productVariantsData['product1'];
104
105
        $this->client->request('GET', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithAccept);
106
        $response = $this->client->getResponse();
107
108
        $this->assertResponse($response, 'product_variant/index_response', Response::HTTP_OK);
109
    }
110
111
    /**
112
     * @test
113
     */
114
    public function it_allows_paginating_the_index_of_product_variant()
115
    {
116
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
117
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
118
119
        /** @var ProductInterface $product */
120
        $product = $productVariantsData['product1'];
121
122
        $this->client->request('GET', $this->getVariantListUrl($product), ['page' => 2], [], static::$authorizedHeaderWithAccept);
123
        $response = $this->client->getResponse();
124
125
        $this->assertResponse($response, 'product_variant/paginated_index_response', Response::HTTP_OK);
126
    }
127
128
    /**
129
     * @test
130
     */
131
    public function it_allows_sorting_the_index_of_product_variants()
132
    {
133
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
134
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
135
136
        /** @var ProductInterface $product */
137
        $product = $productVariantsData['product1'];
138
139
        $this->client->request('GET', $this->getVariantListUrl($product), ['sorting' => ['position' => 'desc']], [], static::$authorizedHeaderWithAccept);
140
        $response = $this->client->getResponse();
141
        
142
        $this->assertResponse($response, 'product_variant/sorted_index_response');
143
    }
144
145
    /**
146
     * @test
147
     */
148
    public function it_allows_create_product_variant()
149
    {
150
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
151
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
152
153
        /** @var ProductInterface $product */
154
        $product = $productVariantsData['product1'];
155
156
        $data =
157
<<<EOT
158
        {
159
            "code": "MONSTER_MUG"
160
        }
161
EOT;
162
163
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, $data);
164
        $response = $this->client->getResponse();
165
166
        $this->assertResponse($response, 'product_variant/create_response', Response::HTTP_CREATED);
167
    }
168
169
    /**
170
     * @test
171
     */
172
    public function it_does_not_allow_to_create_product_variant_without_required_fields()
173
    {
174
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
175
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
176
177
        /** @var ProductInterface $product */
178
        $product = $productVariantsData['product1'];
179
180
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, []);
181
        $response = $this->client->getResponse();
182
183
        $this->assertResponse($response, 'product_variant/create_validation_fail_response', Response::HTTP_BAD_REQUEST);
184
    }
185
186
    /**
187
     * @test
188
     */
189
    public function it_allows_create_product_variant_with_multiple_translations()
190
    {
191
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
192
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
193
        $this->loadFixturesFromFile('resources/locales.yml');
194
195
        /** @var ProductInterface $product */
196
        $product = $productVariantsData['product1'];
197
198
        $data =
199
<<<EOT
200
        {
201
            "code": "MONSTER_MUG",
202
            "translations": {
203
                "de_CH": {
204
                    "name": "Monsterbecher"
205
                },
206
                "en_US": {
207
                    "name": "Monster Mug"
208
                }
209
            }
210
        }
211
EOT;
212
213
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, $data);
214
        $response = $this->client->getResponse();
215
216
        $this->assertResponse($response, 'product_variant/create_with_translations_response', Response::HTTP_CREATED);
217
    }
218
219
    /**
220
     * @test
221
     */
222
    public function it_allows_create_product_variant_with_channel_pricings()
223
    {
224
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
225
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
226
        $this->loadFixturesFromFile('resources/channels.yml');
227
228
        /** @var ProductInterface $product */
229
        $product = $productVariantsData['product1'];
230
231
232
        $data =
233
<<<EOT
234
        {
235
            "code": "MONSTER_MUG",
236
            "channelPricings": [
237
                {
238
                    "price": "1243"
239
                },
240
                {
241
                    "price": "342"
242
                }
243
            ]
244
        }
245
EOT;
246
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, $data);
247
        $response = $this->client->getResponse();
248
249
        $this->assertResponse($response, 'product_variant/create_with_channel_pricings_response', Response::HTTP_CREATED);
250
    }
251
252
    /**
253
     * @test
254
     */
255
    public function it_allows_create_tracked_product_variant()
256
    {
257
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
258
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
259
260
        /** @var ProductInterface $product */
261
        $product = $productVariantsData['product1'];
262
263
        $data =
264
<<<EOT
265
        {
266
            "code": "MONSTER_MUG",
267
            "tracked": true,
268
            "onHand": 5
269
        }
270
EOT;
271
272
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, $data);
273
        $response = $this->client->getResponse();
274
275
        $this->assertResponse($response, 'product_variant/create_tracked_response', Response::HTTP_CREATED);
276
    }
277
278
    /**
279
     * @test
280
     */
281
    public function it_allows_create_product_variant_with_tax_category()
282
    {
283
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
284
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
285
        $this->loadFixturesFromFile('resources/tax_categories.yml');
286
287
        /** @var ProductInterface $product */
288
        $product = $productVariantsData['product1'];
289
290
        $data =
291
<<<EOT
292
        {
293
            "code": "MONSTER_MUG",
294
            "tax_category": "TC1"
295
        }
296
EOT;
297
298
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, $data);
299
        $response = $this->client->getResponse();
300
301
        $this->assertResponse($response, 'product_variant/create_with_tax_category_response', Response::HTTP_CREATED);
302
    }
303
304
    /**
305
     * @test
306
     */
307
    public function it_allows_create_product_variant_with_shipping_category()
308
    {
309
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
310
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
311
        $this->loadFixturesFromFile('resources/shipping_categories.yml');
312
313
        /** @var ProductInterface $product */
314
        $product = $productVariantsData['product1'];
315
316
        $data =
317
<<<EOT
318
        {
319
            "code": "MONSTER_MUG",
320
            "shipping_category": "SC1"
321
        }
322
EOT;
323
324
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, $data);
325
        $response = $this->client->getResponse();
326
327
        $this->assertResponse($response, 'product_variant/create_with_shipping_category_response', Response::HTTP_CREATED);
328
    }
329
330
    /**
331
     * @test
332
     */
333
    public function it_allows_create_product_variant_with_product_option()
334
    {
335
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
336
        $this->loadFixturesFromFile('resources/locales.yml');
337
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
338
339
        /** @var ProductInterface $product */
340
        $product = $productVariantsData['product1'];
341
342
        $data =
343
<<<EOT
344
        {
345
            "code": "MONSTER_MUG",
346
            "option_values": { 
347
                "MUG__TYPE": "MUG_TYPE_MEDIUM" 
348
            }
349
        }
350
EOT;
351
352
        $this->client->request('POST', $this->getVariantListUrl($product), [], [], static::$authorizedHeaderWithContentType, $data);
353
        $response = $this->client->getResponse();
354
355
        $this->assertResponse($response, 'product_variant/create_with_product_option_response', Response::HTTP_CREATED);
356
    }
357
    
358
    /**
359
     * @test
360
     */
361
    public function it_does_not_allow_delete_product_variant_if_it_does_not_exist()
362
    {
363
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
364
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
365
366
        /** @var ProductInterface $product */
367
        $product = $productVariantsData['product1'];
368
369
        $this->client->request('DELETE', $this->getVariantListUrl($product) . 'code', [], [], static::$authorizedHeaderWithAccept);
370
        $response = $this->client->getResponse();
371
372
        $this->assertResponse($response, 'error/not_found_response', Response::HTTP_NOT_FOUND);
373
    }
374
375
    /**
376
     * @test
377
     */
378
    public function it_allows_delete_product_variant()
379
    {
380
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
381
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
382
383
        /** @var ProductInterface $product */
384
        $product = $productVariantsData['product1'];
385
386
        /** @var ProductVariantInterface $productVariant */
387
        $productVariant = $productVariantsData['productVariant1'];
388
389
        $this->client->request('DELETE', $this->getVariantUrl($product, $productVariant), [], [], static::$authorizedHeaderWithContentType, []);
390
391
        $response = $this->client->getResponse();
392
        $this->assertResponseCode($response, Response::HTTP_NO_CONTENT);
393
394
        /** @var ProductInterface $product */
395
        $product = $productVariantsData['product1'];
396
397
        $this->client->request('GET', $this->getVariantUrl($product, $productVariant), [], [], static::$authorizedHeaderWithAccept);
398
        $response = $this->client->getResponse();
399
400
        $this->assertResponse($response, 'error/not_found_response', Response::HTTP_NOT_FOUND);
401
    }
402
403
    /**
404
     * @test
405
     */
406
    public function it_allows_updating_information_about_product_variant()
407
    {
408
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
409
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
410
411
        /** @var ProductInterface $product */
412
        $product = $productVariantsData['product1'];
413
414
        /** @var ProductVariantInterface $productVariant */
415
        $productVariant = $productVariantsData['productVariant1'];
416
417
        $data =
418
<<<EOT
419
        {
420
            "code": "NEW_MUG_CODE"
421
        }
422
EOT;
423
        $this->client->request('PUT', $this->getVariantUrl($product, $productVariant), [], [], static::$authorizedHeaderWithContentType, $data);
424
        $response = $this->client->getResponse();
425
426
        $this->assertResponseCode($response, Response::HTTP_NO_CONTENT);
427
    }
428
429
430
    /**
431
     * @test
432
     */
433
    public function it_allows_updating_partial_information_about_product_variant()
434
    {
435
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
436
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
437
        $this->loadFixturesFromFile('resources/locales.yml');
438
439
        /** @var ProductInterface $product */
440
        $product = $productVariantsData['product1'];
441
442
        /** @var ProductVariantInterface $productVariant */
443
        $productVariant = $productVariantsData['productVariant1'];
444
445
        $data =
446
<<<EOT
447
        {
448
            "translations": {
449
                "de_CH": {
450
                    "name": "Monsterbecher"
451
452
                }
453
            }
454
        }
455
EOT;
456
457
        $this->client->request('PATCH', $this->getVariantUrl($product, $productVariant), [], [], static::$authorizedHeaderWithContentType, $data);
458
        $response = $this->client->getResponse();
459
460
        $this->assertResponseCode($response, Response::HTTP_NO_CONTENT);
461
    }
462
463
    /**
464
     * @test
465
     */
466
    public function it_not_change_on_hand_after_updating_product_variant()
467
    {
468
        $this->loadFixturesFromFile('authentication/api_administrator.yml');
469
        $productVariantsData = $this->loadFixturesFromFile('resources/product_variants.yml');
470
        $this->loadFixturesFromFile('resources/locales.yml');
471
472
        /** @var ProductInterface $product */
473
        $product = $productVariantsData['product2'];
474
475
        /** @var ProductVariantInterface $productVariant */
476
        $productVariant = $productVariantsData['productVariant21'];
477
478
        $data =
479
<<<EOT
480
        {
481
            "tracked": false
482
        }
483
EOT;
484
        $this->client->request('PATCH', $this->getVariantUrl($product, $productVariant), [], [], static::$authorizedHeaderWithContentType, $data);
485
        $response = $this->client->getResponse();
486
487
        $this->assertResponseCode($response, Response::HTTP_NO_CONTENT);
488
489
        $this->client->request('GET', $this->getVariantUrl($product, $productVariant), [], [], static::$authorizedHeaderWithAccept);
490
        $response = $this->client->getResponse();
491
492
        $this->assertResponse($response, 'product_variant/not_changed_on_hand_response', Response::HTTP_OK);
493
    }
494
495
    /**
496
     * @param ProductInterface $product
497
     *
498
     * @return string
499
     */
500
    private function getVariantListUrl(ProductInterface $product)
501
    {
502
        return sprintf('/api/v1/products/%s/variants/', $product->getId());
503
    }
504
505
    /**
506
     * @param ProductInterface $product
507
     * @param ProductVariantInterface $productVariant
508
     *
509
     * @return string
510
     */
511
    private function getVariantUrl(ProductInterface $product, ProductVariantInterface $productVariant)
512
    {
513
        return sprintf('%s%s', $this->getVariantListUrl($product), $productVariant->getId());
514
    }
515
}
516