Skip to content

Commit 11e84eb

Browse files
author
Ivan Lutokhin
committed
Added validators
1 parent db9e8d7 commit 11e84eb

File tree

12 files changed

+424
-3
lines changed

12 files changed

+424
-3
lines changed
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
<?php
2+
3+
namespace RetailCrm\DeliveryModuleBundle\Exception;
4+
5+
class RetailCrmApiException extends \Exception
6+
{
7+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
integration_module_access:
2+
server_unreachable_exception: 'Failed to connect to the integration server'
3+
module_access_exception: 'Invalid login or password'
4+
5+
retailcrm_access:
6+
access_denied: 'Access to the method "%method%" is denied'
7+
curl_exception: 'Failed to connect to API'
8+
service_unavailable: 'Service is temporarily unavailable'
9+
invalid_json: 'API returned a response in an unsupported format'
10+
requires_https: 'API address must start with https'
11+
wrong_api_key: 'Invalid API key'
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
integration_module_access:
2+
server_unreachable_exception: 'No se ha podido conectar al servidor de integración'
3+
module_access_exception: 'El Usuario o la contraseña no es correcta'
4+
5+
retailcrm_access:
6+
access_denied: 'Acceso al método "%method%" está prohibido'
7+
curl_exception: 'No se ha podido conectar al API'
8+
service_unavailable: 'Servicio no está disponible temporalmente'
9+
invalid_json: 'API ha devuelto la respuesta en el formato no soportado'
10+
requires_https: 'Dirección del API tiene que comenzar con https'
11+
wrong_api_key: 'El API-key no es correcto'
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
integration_module_access:
2+
server_unreachable_exception: 'Не удалось подключиться к интеграционному серверу'
3+
module_access_exception: 'Не верный логин или пароль'
4+
5+
retailcrm_access:
6+
access_denied: 'Доступ к методу "%method%" запрещен'
7+
curl_exception: 'Не удалось подключиться к API'
8+
service_unavailable: 'Сервис временно недоступен'
9+
invalid_json: 'API вернуло ответ в неподдерживаемом формате'
10+
requires_https: 'Адрес API должен начинаться с https'
11+
wrong_api_key: 'Неверный API-ключ'

Service/ModuleManager.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -132,6 +132,11 @@ public function setAccount(Account $account): ModuleManagerInterface
132132
return $this;
133133
}
134134

135+
public function checkAccess(): bool
136+
{
137+
throw new \LogicException('Method should be implemented');
138+
}
139+
135140
public function updateModuleConfiguration(): bool
136141
{
137142
if (null === $this->account) {

Service/ModuleManagerInterface.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,8 @@ public function getAccount(): ?Account;
2525

2626
public function setAccount(Account $account): self;
2727

28+
public function checkAccess(): bool;
29+
2830
public function updateModuleConfiguration(): bool;
2931

3032
public function calculateDelivery(RequestCalculate $data): array;
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
<?php
2+
3+
namespace RetailCrm\DeliveryModuleBundle\Validator\Constraints;
4+
5+
use Symfony\Component\Validator\Constraint;
6+
7+
/**
8+
* @Annotation
9+
* @Target({"CLASS"})
10+
*/
11+
class IntegrationModuleAccess extends Constraint
12+
{
13+
/** @var string */
14+
public $path = 'login';
15+
16+
/**
17+
* {@inheritdoc}
18+
*/
19+
public function getTargets()
20+
{
21+
return self::CLASS_CONSTRAINT;
22+
}
23+
}
Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
<?php
2+
3+
namespace RetailCrm\DeliveryModuleBundle\Validator\Constraints;
4+
5+
use RetailCrm\DeliveryModuleBundle\Exception\AbstractModuleException;
6+
use RetailCrm\DeliveryModuleBundle\Exception\ServerUnreachableException;
7+
use RetailCrm\DeliveryModuleBundle\Service\ModuleManagerInterface;
8+
use Symfony\Component\Validator\Constraint;
9+
use Symfony\Component\Validator\ConstraintValidator;
10+
use Symfony\Component\Validator\Exception\UnexpectedTypeException;
11+
12+
class IntegrationModuleAccessValidator extends ConstraintValidator
13+
{
14+
/** @var ModuleManagerInterface */
15+
private $moduleManager;
16+
17+
public function __construct(ModuleManagerInterface $moduleManager)
18+
{
19+
$this->moduleManager = $moduleManager;
20+
}
21+
22+
public function validate($account, Constraint $constraint)
23+
{
24+
if (!($constraint instanceof IntegrationModuleAccess)) {
25+
throw new UnexpectedTypeException($constraint, IntegrationModuleAccess::class);
26+
}
27+
28+
try {
29+
$this->moduleManager->checkAccess();
30+
} catch (ServerUnreachableException $e) {
31+
$this->context
32+
->buildViolation('integration_module_access.server_unreachable_exception')
33+
->atPath($constraint->path)
34+
->addViolation()
35+
;
36+
} catch (AbstractModuleException $e) {
37+
$this->context
38+
->buildViolation('integration_module_access.module_access_exception')
39+
->atPath($constraint->path)
40+
->addViolation()
41+
;
42+
}
43+
}
44+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
<?php
2+
3+
namespace App\Validator\Constraints;
4+
5+
use Symfony\Component\Validator\Constraint;
6+
7+
/**
8+
* @Annotation
9+
* @Target({"CLASS"})
10+
*/
11+
class RetailCrmAccess extends Constraint
12+
{
13+
/**
14+
* {@inheritdoc}
15+
*/
16+
public function getTargets()
17+
{
18+
return self::CLASS_CONSTRAINT;
19+
}
20+
}
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
<?php
2+
3+
namespace App\Validator\Constraints;
4+
5+
use RetailCrm\DeliveryModuleBundle\Exception\RetailCrmApiException;
6+
use RetailCrm\DeliveryModuleBundle\Service\ModuleManagerInterface;
7+
use RetailCrm\Exception\CurlException;
8+
use RetailCrm\Exception\InvalidJsonException;
9+
use RetailCrm\Exception\LimitException;
10+
use Symfony\Component\Validator\Constraint;
11+
use Symfony\Component\Validator\ConstraintValidator;
12+
use Symfony\Component\Validator\Exception\UnexpectedTypeException;
13+
14+
class RetailCrmAccessValidator extends ConstraintValidator
15+
{
16+
private const REQUIRED_METHODS = [
17+
'/api/integration-modules/{code}',
18+
'/api/integration-modules/{code}/edit',
19+
'/api/delivery/generic/setting/{code}',
20+
'/api/delivery/generic/setting/{code}/edit',
21+
'/api/delivery/generic/{code}/tracking',
22+
'/api/delivery/shipments',
23+
'/api/delivery/shipments/{id}',
24+
'/api/delivery/shipments/create',
25+
'/api/delivery/shipments/{id}/edit',
26+
'/api/reference/sites',
27+
'/api/reference/stores',
28+
'/api/reference/payment-types',
29+
'/api/reference/statuses',
30+
];
31+
32+
/** @var ModuleManagerInterface */
33+
private $moduleManager;
34+
35+
public function __construct(ModuleManagerInterface $moduleManager)
36+
{
37+
$this->moduleManager = $moduleManager;
38+
}
39+
40+
public function validate($account, Constraint $constraint)
41+
{
42+
if (!($constraint instanceof RetailCrmAccess)) {
43+
throw new UnexpectedTypeException($constraint, RetailCrmAccess::class);
44+
}
45+
46+
$client = $this->moduleManager->getRetailCrmClient();
47+
48+
try {
49+
$response = $client->request->credentials();
50+
if (!$response->isSuccessful()) {
51+
throw new RetailCrmApiException($response->offsetGet('errorMsg'));
52+
}
53+
54+
$credentials = $response->offsetGet('credentials');
55+
foreach (static::REQUIRED_METHODS as $method) {
56+
if (!in_array($method, $credentials)) {
57+
$this->context
58+
->buildViolation('retailcrm_access.access_denied', ['%method%' => $method])
59+
->atPath('crmApiKey')
60+
->addViolation()
61+
;
62+
}
63+
}
64+
} catch (CurlException $e) {
65+
$this->context
66+
->buildViolation('retailcrm_access.curl_exception')
67+
->atPath('crmUrl')
68+
->addViolation()
69+
;
70+
} catch (LimitException $e) {
71+
$this->context
72+
->buildViolation('retailcrm_access.service_unavailable')
73+
->atPath('crmUrl')
74+
->addViolation()
75+
;
76+
} catch (InvalidJsonException $e) {
77+
$this->context
78+
->buildViolation('retailcrm_access.invalid_json')
79+
->atPath('crmUrl')
80+
->addViolation()
81+
;
82+
} catch (\InvalidArgumentException $e) {
83+
$this->context
84+
->buildViolation('retailcrm_access.requires_https')
85+
->atPath('crmUrl')
86+
->addViolation()
87+
;
88+
} catch (RetailCrmApiException $e) {
89+
$this->context
90+
->buildViolation('retailcrm_access.wrong_api_key')
91+
->atPath('crmUrl')
92+
->addViolation()
93+
;
94+
}
95+
}
96+
}

0 commit comments

Comments
 (0)