diff --git a/composer.json b/composer.json index cfa5aa0..7a6e90b 100644 --- a/composer.json +++ b/composer.json @@ -25,6 +25,7 @@ "symfony/http-foundation": "^5.4 || ^6.0", "symfony/http-kernel": "^5.4 || ^6.0", "symfony/intl": "^5.4 || ^6.0", + "symfony/mailer": "^5.4 || ^6.0", "symfony/messenger": "^5.4 || ^6.0", "symfony/options-resolver": "^5.4 || ^6.0", "symfony/routing": "^5.4 || ^6.0", @@ -55,7 +56,8 @@ "setono/coolrunner-bundle": "^1.0", "setono/dao-bundle": "^1.1", "setono/gls-webservice-bundle": "^1.3", - "setono/post-nord-bundle": "^1.0", + "setono/post-nord-bundle": "^2.0@alpha", + "setono/post-nord-php-sdk": "^2.0@alpha", "setono/sylius-behat-pack": "^0.2", "sylius/sylius": "~1.12.13", "symfony/debug-bundle": "^5.4 || ^6.4", @@ -89,10 +91,10 @@ }, "config": { "allow-plugins": { - "ergebnis/composer-normalize": true, - "symfony/thanks": false, "dealerdirect/phpcodesniffer-composer-installer": false, - "php-http/discovery": true + "ergebnis/composer-normalize": true, + "php-http/discovery": true, + "symfony/thanks": false }, "sort-packages": true }, diff --git a/psalm.xml b/psalm.xml index 3529aca..b9d44f8 100644 --- a/psalm.xml +++ b/psalm.xml @@ -15,6 +15,7 @@ + diff --git a/src/Provider/PostNordProvider.php b/src/Provider/PostNordProvider.php index bd8cda2..f60aea7 100644 --- a/src/Provider/PostNordProvider.php +++ b/src/Provider/PostNordProvider.php @@ -4,9 +4,11 @@ namespace Setono\SyliusPickupPointPlugin\Provider; -use function preg_replace; use Psr\Http\Client\NetworkExceptionInterface; use Setono\PostNord\Client\ClientInterface; +use Setono\PostNord\Request\Query\ServicePoints\ByIdsQuery; +use Setono\PostNord\Request\Query\ServicePoints\NearestByAddressQuery; +use Setono\PostNord\Response\ServicePoints\ServicePoint; use Setono\SyliusPickupPointPlugin\Exception\TimeoutException; use Setono\SyliusPickupPointPlugin\Model\PickupPointCode; use Setono\SyliusPickupPointPlugin\Model\PickupPointInterface; @@ -19,14 +21,10 @@ */ final class PostNordProvider extends Provider { - private ClientInterface $client; - - private FactoryInterface $pickupPointFactory; - - public function __construct(ClientInterface $client, FactoryInterface $pickupPointFactory) - { - $this->client = $client; - $this->pickupPointFactory = $pickupPointFactory; + public function __construct( + private readonly ClientInterface $client, + private readonly FactoryInterface $pickupPointFactory, + ) { } public function findPickupPoints(OrderInterface $order): iterable @@ -37,30 +35,43 @@ public function findPickupPoints(OrderInterface $order): iterable } $street = $shippingAddress->getStreet(); + if (null === $street) { + return []; + } + + $streetParts = explode(' ', $street); + if (count($streetParts) < 2) { + return []; + } + + $streetNumber = array_pop($streetParts); + $street = implode(' ', $streetParts); + $postCode = $shippingAddress->getPostcode(); + $city = $shippingAddress->getCity(); $countryCode = $shippingAddress->getCountryCode(); - if (null === $street || null === $postCode || null === $countryCode) { + if (null === $postCode || null === $city || null === $countryCode) { return []; } try { - $result = $this->client->get('/rest/businesslocation/v1/servicepoint/findNearestByAddress.json', [ - 'countryCode' => $countryCode, - 'postalCode' => preg_replace('/\s+/', '', $postCode), - 'streetName' => $street, - 'numberOfServicePoints' => 10, - ]); + $result = $this->client->servicePoints()->getNearestByAddress(NearestByAddressQuery::create( + streetName: $street, + streetNumber: $streetNumber, + postalCode: $postCode, + city: $city, + countryCode: $countryCode, + )); } catch (NetworkExceptionInterface $e) { throw new TimeoutException($e); } - $servicePoints = $result['servicePointInformationResponse']['servicePoints'] ?? []; - if (!is_array($servicePoints)) { + if ([] === $result->servicePoints) { return []; } $pickupPoints = []; - foreach ($servicePoints as $servicePoint) { + foreach ($result->servicePoints as $servicePoint) { $pickupPoints[] = $this->transform($servicePoint); } @@ -70,42 +81,25 @@ public function findPickupPoints(OrderInterface $order): iterable public function findPickupPoint(PickupPointCode $code): ?PickupPointInterface { try { - $result = $this->client->get('/rest/businesslocation/v1/servicepoint/findByServicePointId.json', [ - 'countryCode' => $code->getCountryPart(), - 'servicePointId' => $code->getIdPart(), - ]); + $result = $this->client->servicePoints()->getByIds(ByIdsQuery::create( + ids: [$code->getIdPart()], + countryCode: $code->getCountryPart(), + )); } catch (NetworkExceptionInterface $e) { throw new TimeoutException($e); } - $servicePoints = $result['servicePointInformationResponse']['servicePoints'] ?? null; - if (!is_array($servicePoints) || count($servicePoints) < 1) { + if ([] === $result->servicePoints) { return null; } - return $this->transform($servicePoints[0]); + return $this->transform($result->servicePoints[0]); } public function findAllPickupPoints(): iterable { - try { - $result = $this->client->get('/rest/businesslocation/v1/servicepoint/getServicePointInformation.json'); - } catch (NetworkExceptionInterface $e) { - throw new TimeoutException($e); - } - - $servicePoints = $result['servicePointInformationResponse']['servicePoints'] ?? []; - if (!is_array($servicePoints)) { - return []; - } - - foreach ($servicePoints as $servicePoint) { - if (!self::isValidServicePoint($servicePoint)) { - continue; - } - - yield $this->transform($servicePoint); - } + // todo implement this + return []; } public function getCode(): string @@ -118,43 +112,25 @@ public function getName(): string return 'PostNord'; } - private function transform(array $servicePoint): PickupPointInterface + private function transform(ServicePoint $servicePoint): PickupPointInterface { $id = new PickupPointCode( - $servicePoint['servicePointId'], + $servicePoint->servicePointId, $this->getCode(), - $servicePoint['visitingAddress']['countryCode'], + $servicePoint->visitingAddress->countryCode, ); - $address = ''; - - if (isset($servicePoint['visitingAddress']['streetName'])) { - $address .= $servicePoint['visitingAddress']['streetName']; - } - - if (isset($servicePoint['visitingAddress']['streetNumber'])) { - $address .= ('' !== $address ? ' ' : '') . $servicePoint['visitingAddress']['streetNumber']; - } - - $latitude = $longitude = null; - if (isset($servicePoint['coordinates'][0])) { - $latitude = (float) $servicePoint['coordinates'][0]['northing']; - $longitude = (float) $servicePoint['coordinates'][0]['easting']; - } - /** @var PickupPointInterface|object $pickupPoint */ $pickupPoint = $this->pickupPointFactory->createNew(); Assert::isInstanceOf($pickupPoint, PickupPointInterface::class); $pickupPoint->setCode($id); - $pickupPoint->setName($servicePoint['name']); - $pickupPoint->setAddress($address); - $pickupPoint->setZipCode((string) $servicePoint['visitingAddress']['postalCode']); - $pickupPoint->setCity($servicePoint['visitingAddress']['city']); - $pickupPoint->setCountry((string) $servicePoint['visitingAddress']['countryCode']); - $pickupPoint->setLatitude($latitude); - $pickupPoint->setLongitude($longitude); + $pickupPoint->setName($servicePoint->name); + $pickupPoint->setAddress($servicePoint->visitingAddress->streetName . ' ' . $servicePoint->visitingAddress->streetNumber); + $pickupPoint->setZipCode($servicePoint->visitingAddress->postalCode); + $pickupPoint->setCity($servicePoint->visitingAddress->city); + $pickupPoint->setCountry($servicePoint->visitingAddress->countryCode); return $pickupPoint; } @@ -162,7 +138,7 @@ private function transform(array $servicePoint): PickupPointInterface private static function isValidServicePoint(array $servicePoint): bool { // some service points will not have a city because they are special internal service points - // we exclude these service points since they doesn't make any sense for the end user + // we exclude these service points since they don't make any sense for the end user if (!isset($servicePoint['visitingAddress']['city'])) { return false; } diff --git a/src/Resources/config/app/fixtures.yaml b/src/Resources/config/app/fixtures.yaml index 96f6670..1ab6ebf 100644 --- a/src/Resources/config/app/fixtures.yaml +++ b/src/Resources/config/app/fixtures.yaml @@ -20,7 +20,6 @@ sylius_fixtures: - 'PT' - 'ES' - 'CN' - - 'UK' zones: WORLD: name: 'World' @@ -38,7 +37,6 @@ sylius_fixtures: - 'PT' - 'ES' - 'CN' - - 'UK' DAO_PP_COUNTRIES: name: 'Denmark' countries: @@ -60,7 +58,6 @@ sylius_fixtures: - 'DE' - 'PT' - 'ES' - - 'UK' setono_sylius_pickup_point_shipping_method: options: diff --git a/tests/Application/Kernel.php b/tests/Application/Kernel.php index da0de16..10aa299 100644 --- a/tests/Application/Kernel.php +++ b/tests/Application/Kernel.php @@ -4,11 +4,11 @@ namespace Setono\SyliusPickupPointPlugin\Tests\Application; +use PSS\SymfonyMockerContainer\DependencyInjection\MockerContainer; use Symfony\Bundle\FrameworkBundle\Kernel\MicroKernelTrait; use Symfony\Component\HttpKernel\Bundle\BundleInterface; use Symfony\Component\HttpKernel\Kernel as BaseKernel; use Symfony\Component\Routing\Loader\Configurator\RoutingConfigurator; -use PSS\SymfonyMockerContainer\DependencyInjection\MockerContainer; final class Kernel extends BaseKernel { diff --git a/tests/Application/config/routes/sylius_admin_api.yaml b/tests/Application/config/routes/sylius_admin_api.yaml deleted file mode 100644 index 80aed45..0000000 --- a/tests/Application/config/routes/sylius_admin_api.yaml +++ /dev/null @@ -1,3 +0,0 @@ -sylius_admin_api: - resource: "@SyliusAdminApiBundle/Resources/config/routing.yml" - prefix: /api diff --git a/tests/Application/public/media/image/.gitignore b/tests/Application/public/media/image/.gitignore deleted file mode 100644 index e69de29..0000000