Skip to content

Commit d037181

Browse files
committed
chore(api) add delete discount & list endpoint
1 parent 451d58d commit d037181

File tree

3 files changed

+157
-1
lines changed

3 files changed

+157
-1
lines changed

src/ApiPlatform/Resources/Discount/Discount.php

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,10 +24,12 @@
2424
use ApiPlatform\Metadata\ApiResource;
2525
use PrestaShop\Decimal\DecimalNumber;
2626
use PrestaShop\PrestaShop\Core\Domain\Discount\Command\AddDiscountCommand;
27+
use PrestaShop\PrestaShop\Core\Domain\Discount\Command\DeleteDiscountCommand;
2728
use PrestaShop\PrestaShop\Core\Domain\Discount\Exception\DiscountConstraintException;
2829
use PrestaShop\PrestaShop\Core\Domain\Discount\Exception\DiscountNotFoundException;
2930
use PrestaShop\PrestaShop\Core\Domain\Discount\Query\GetDiscountForEditing;
3031
use PrestaShopBundle\ApiPlatform\Metadata\CQRSCreate;
32+
use PrestaShopBundle\ApiPlatform\Metadata\CQRSDelete;
3133
use PrestaShopBundle\ApiPlatform\Metadata\CQRSGet;
3234
use PrestaShopBundle\ApiPlatform\Metadata\LocalizedValue;
3335
use Symfony\Component\HttpFoundation\Response;
@@ -50,6 +52,13 @@
5052
'[names]' => '[localizedNames]',
5153
],
5254
),
55+
new CQRSDelete(
56+
uriTemplate: '/discount/{discountId}',
57+
CQRSQuery: DeleteDiscountCommand::class,
58+
scopes: [
59+
'discount_write',
60+
],
61+
),
5362
],
5463
exceptionToStatus: [
5564
DiscountNotFoundException::class => Response::HTTP_NOT_FOUND,
Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
<?php
2+
/**
3+
* Copyright since 2007 PrestaShop SA and Contributors
4+
* PrestaShop is an International Registered Trademark & Property of PrestaShop SA
5+
*
6+
* NOTICE OF LICENSE
7+
*
8+
* This source file is subject to the Academic Free License version 3.0
9+
* that is bundled with this package in the file LICENSE.md.
10+
* It is also available through the world-wide-web at this URL:
11+
* https://opensource.org/licenses/AFL-3.0
12+
* If you did not receive a copy of the license and are unable to
13+
* obtain it through the world-wide-web, please send an email
14+
* to license@prestashop.com so we can send you a copy immediately.
15+
*
16+
* @author PrestaShop SA and Contributors <contact@prestashop.com>
17+
* @copyright Since 2007 PrestaShop SA and Contributors
18+
* @license https://opensource.org/licenses/AFL-3.0 Academic Free License version 3.0
19+
*/
20+
21+
namespace PrestaShop\Module\APIResources\ApiPlatform\Resources\Discount;
22+
23+
use ApiPlatform\Metadata\ApiProperty;
24+
use ApiPlatform\Metadata\ApiResource;
25+
use DateTimeImmutable;
26+
use PrestaShop\Decimal\DecimalNumber;
27+
use PrestaShop\PrestaShop\Adapter\Discount\Grid\Data\Factory\DiscountGridDataFactoryDecorator;
28+
use PrestaShop\PrestaShop\Core\Domain\Discount\Exception\DiscountNotFoundException;
29+
use PrestaShop\PrestaShop\Core\Search\Filters\DiscountFilters;
30+
use PrestaShopBundle\ApiPlatform\Metadata\LocalizedValue;
31+
use PrestaShopBundle\ApiPlatform\Metadata\PaginatedList;
32+
use PrestaShopBundle\ApiPlatform\Provider\QueryListProvider;
33+
use Symfony\Component\HttpFoundation\Response;
34+
35+
#[ApiResource(
36+
operations: [
37+
new PaginatedList(
38+
uriTemplate: '/discounts',
39+
provider: QueryListProvider::class,
40+
scopes: ['discount_read'],
41+
ApiResourceMapping: [
42+
'[id_discount]' => '[discountId]',
43+
],
44+
gridDataFactory: DiscountGridDataFactoryDecorator::class,
45+
filtersClass: DiscountFilters::class,
46+
),
47+
],
48+
exceptionToStatus: [
49+
DiscountNotFoundException::class => Response::HTTP_NOT_FOUND,
50+
],
51+
)]
52+
class DiscountList
53+
{
54+
#[ApiProperty(identifier: true)]
55+
public int $discountId;
56+
#[LocalizedValue]
57+
public array $names;
58+
public int $priority;
59+
public bool $active;
60+
public DateTimeImmutable $validFrom;
61+
public DateTimeImmutable $validTo;
62+
public int $totalQuantity;
63+
public int $quantityPerUser;
64+
public string $description;
65+
public string $code;
66+
public int $customerId;
67+
public bool $highlightInCart;
68+
public bool $allowPartialUse;
69+
public string $type;
70+
public ?DecimalNumber $percentDiscount;
71+
public ?DecimalNumber $amountDiscount;
72+
public int $currencyId;
73+
public bool $isTaxIncluded;
74+
public int $productId;
75+
public array $combinations;
76+
public int $reductionProduct;
77+
}

tests/Integration/ApiPlatform/DiscountEndpointTest.php

Lines changed: 71 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,9 @@
2323
namespace PsApiResourcesTest\Integration\ApiPlatform;
2424

2525
use PrestaShop\PrestaShop\Core\Domain\Discount\Command\AddDiscountCommand;
26+
use PrestaShop\PrestaShop\Core\Domain\Discount\Command\DeleteDiscountCommand;
2627
use PrestaShop\PrestaShop\Core\Domain\Discount\Query\GetDiscountForEditing;
28+
use Tests\Resources\DatabaseDump;
2729
use Tests\Resources\Resetter\LanguageResetter;
2830

2931
class DiscountEndpointTest extends ApiTestCase
@@ -39,6 +41,20 @@ public static function setUpBeforeClass(): void
3941
parent::setUpBeforeClass();
4042

4143
LanguageResetter::resetLanguages();
44+
DatabaseDump::restoreTables([
45+
'cart_cart_rule',
46+
'cart_rule',
47+
'cart_rule_carrier',
48+
'cart_rule_combination',
49+
'cart_rule_country',
50+
'cart_rule_group',
51+
'cart_rule_lang',
52+
'cart_rule_product_rule',
53+
'cart_rule_product_rule_group',
54+
'cart_rule_product_rule_value',
55+
'cart_rule_shop',
56+
]);
57+
4258
self::addLanguageByLocale('fr-FR');
4359
self::createApiClient(['discount_write', 'discount_read']);
4460
}
@@ -162,16 +178,60 @@ public function testGetDiscount(): void
162178
self::assertResponseStatusCodeSame(200);
163179

164180
$decodedResponse = json_decode($response->getContent(), true);
165-
166181
$this->assertNotFalse($decodedResponse);
167182
$this->assertArrayHasKey('discountId', $decodedResponse);
183+
$this->assertEquals(1, $decodedResponse['priority']);
184+
$this->assertFalse($decodedResponse['active']);
185+
$this->assertArrayHasKey('validFrom', $decodedResponse);
186+
$this->assertArrayHasKey('validTo', $decodedResponse);
187+
$this->assertEquals(1, $decodedResponse['totalQuantity']);
188+
$this->assertEquals(1, $decodedResponse['quantityPerUser']);
189+
$this->assertEquals('', $decodedResponse['description']);
190+
$this->assertEquals('', $decodedResponse['code']);
191+
$this->assertEquals('0', $decodedResponse['customerId']);
192+
$this->assertFalse($decodedResponse['highlightInCart']);
193+
$this->assertTrue($decodedResponse['allowPartialUse']);
194+
$this->assertEquals(1, $decodedResponse['currencyId']);
195+
$this->assertEquals(0, $decodedResponse['reductionProduct']);
168196
$this->assertArrayHasKey(
169197
'type',
170198
$decodedResponse
171199
);
172200
$this->assertEquals('cart_level', $decodedResponse['type']);
173201
}
174202

203+
public function testListDiscount(): void
204+
{
205+
// skip test if class does not exist
206+
if (!class_exists(GetDiscountForEditing::class)) {
207+
$this->markTestSkipped('GetDiscountForEditing class does not exist');
208+
}
209+
210+
$bearerToken = $this->getBearerToken(['discount_read']);
211+
$response = static::createClient()->request('GET', '/discounts', [
212+
'auth_bearer' => $bearerToken,
213+
]);
214+
self::assertResponseStatusCodeSame(200);
215+
216+
$decodedResponse = json_decode($response->getContent(), true);
217+
218+
$this->assertCount(6, $decodedResponse);
219+
}
220+
221+
public function testDeleteDiscount(): void
222+
{
223+
// skip test if class does not exist
224+
if (!class_exists(DeleteDiscountCommand::class)) {
225+
$this->markTestSkipped('GetDiscountForEditing class does not exist');
226+
}
227+
228+
$bearerToken = $this->getBearerToken(['discount_write']);
229+
static::createClient()->request('DELETE', '/discount/1', [
230+
'auth_bearer' => $bearerToken,
231+
]);
232+
self::assertResponseStatusCodeSame(204);
233+
}
234+
175235
public function getProtectedEndpoints(): iterable
176236
{
177237
yield 'get endpoint' => [
@@ -183,5 +243,15 @@ public function getProtectedEndpoints(): iterable
183243
'POST',
184244
'/discount',
185245
];
246+
247+
yield 'list endpoint' => [
248+
'GET',
249+
'/discounts'
250+
];
251+
252+
yield 'delete endpoint' => [
253+
'DELETE',
254+
'/discount/1',
255+
];
186256
}
187257
}

0 commit comments

Comments
 (0)