คำถามแบบสั้น
มันอยู่ในแนวปฏิบัติที่ดีที่สุดของ DDD และ OOP ในการฉีดบริการกับการเรียกเมธอดเอนทิตีหรือไม่?
ตัวอย่างรูปแบบยาว
สมมติว่าเรามีกรณี Order-LineItems แบบคลาสสิกใน DDD ที่เรามี Domain Entity ชื่อ Order ซึ่งยังทำหน้าที่เป็น Aggregate Root และ Entity นั้นไม่เพียง แต่ประกอบไปด้วย Value Objects แต่ยังเป็นคอลเลกชันของรายการโฆษณา หน่วยงาน
สมมติว่าเราต้องการไวยากรณ์ที่คล่องแคล่วในแอปพลิเคชันของเราเพื่อให้เราสามารถทำสิ่งนี้ (สังเกตไวยากรณ์ในบรรทัดที่ 2 ซึ่งเราเรียกgetLineItems
เมธอด)
$order = $orderService->getOrderByID($orderID);
foreach($order->getLineItems($orderService) as $lineItem) {
...
}
เราไม่ต้องการฉีด LineItemRepository ใด ๆ ลงใน OrderEntity เนื่องจากเป็นการละเมิดหลักการหลายอย่างที่ฉันสามารถนึกได้ แต่ความคล่องแคล่วของวากยสัมพันธ์เป็นสิ่งที่เราต้องการจริงๆเพราะมันง่ายต่อการอ่านและบำรุงรักษารวมถึงการทดสอบ
พิจารณาโค้ดต่อไปนี้โดยสังเกตวิธีgetLineItems
ในOrderEntity
:
interface IOrderService {
public function getOrderByID($orderID) : OrderEntity;
public function getLineItems(OrderEntity $orderEntity) : LineItemCollection;
}
class OrderService implements IOrderService {
private $orderRepository;
private $lineItemRepository;
public function __construct(IOrderRepository $orderRepository, ILineItemRepository $lineItemRepository) {
$this->orderRepository = $orderRepository;
$this->lineItemRepository = $lineItemRepository;
}
public function getOrderByID($orderID) : OrderEntity {
return $this->orderRepository->getByID($orderID);
}
public function getLineItems(OrderEntity $orderEntity) : LineItemCollection {
return $this->lineItemRepository->getLineItemsByOrderID($orderEntity->ID());
}
}
class OrderEntity {
private $ID;
private $lineItems;
public function getLineItems(IOrderServiceInternal $orderService) {
if(!is_null($this->lineItems)) {
$this->lineItems = $orderService->getLineItems($this);
}
return $this->lineItems;
}
}
นั่นเป็นวิธีที่ได้รับการยอมรับในการใช้งานไวยากรณ์ได้อย่างคล่องแคล่วในกิจการโดยไม่ละเมิดหลักการหลักของ DDD และ OOP หรือไม่? สำหรับฉันดูเหมือนว่าใช้ได้เพราะเราเปิดเผยเฉพาะเลเยอร์บริการไม่ใช่เลเยอร์โครงสร้างพื้นฐาน (ที่ซ้อนอยู่ภายในบริการ)