1final class OrderShipmentController
2{
3 public function store(Order $order): RedirectResponse
4 {
5 $this->warehouse->reserve($order->items, $order->warehouseId);
6
7 $waybill = $this->novaPoshta->createWaybill([
8 'CityRecipient' => $order->cityRef,
9 'RecipientAddress' => $order->branchRef,
10 'Weight' => $order->weight,
11 'Cost' => $order->total / 100,
12 'PaymentMethod' => 'Cash',
13 ]);
14
15 $order->update(['ttn' => $waybill->number, 'status' => 'shipped']);
16 $this->mailer->send(new ShippedMail($order, $waybill->number));
17
18 return back();
19 }
20}
1<?php
2
3final readonly class Order
4{
5 public function __construct(public string $number, public string $email, public string $branch, public int $total) {}
6}
7
81// Підсистема: три незалежні сервіси, кожен зі своїм API.
9final class Warehouse
10{
11 public function reserve(string $order): void
12 {
13 echo " склад: товар для {$order} відкладено\n";
14 }
15}
16
17final class NovaPoshtaClient
18{
19 /** @param array<string, string|int|float> $params */
20 public function createWaybill(array $params): string
21 {
22 echo " Нова пошта: накладна на {$params['RecipientAddress']}, оголошена вартість {$params['Cost']} грн\n";
23
24 return '2045' . str_pad((string) crc32((string) $params['RecipientAddress']), 10, '0', STR_PAD_LEFT);
25 }
26}
27
28final class Mailer
29{
30 public function send(string $to, string $text): void
31 {
32 echo " лист на {$to}: {$text}\n";
33 }
34}
35
362final readonly class Shipping
37{
38 public function __construct(
39 private Warehouse $warehouse,
40 private NovaPoshtaClient $novaPoshta,
41 private Mailer $mailer,
42 ) {}
43
443 public function ship(Order $order): string
45 {
46 $this->warehouse->reserve($order->number);
47
48 $ttn = $this->novaPoshta->createWaybill([
49 'RecipientAddress' => $order->branch,
50 'Cost' => $order->total / 100,
51 ]);
52
53 $this->mailer->send($order->email, "замовлення {$order->number} їде, ТТН {$ttn}");
54
55 return $ttn;
56 }
57}
58
594$shipping = new Shipping(new Warehouse(), new NovaPoshtaClient(), new Mailer());
60
61echo "Контролер:\n";
62$shipping->ship(new Order('UA-1042', 'olena@example.com', 'Київ, відділення 25', 185000));
63
64echo "Telegram-бот:\n";
65$shipping->ship(new Order('UA-1043', 'taras@example.com', 'Львів, відділення 3', 42000));