|
1 | | -How to Define Relationships with Abstract Classes and Interfaces |
2 | | -================================================================ |
| 1 | +Referencing Entities with Abstract Classes and Interfaces |
| 2 | +========================================================= |
3 | 3 |
|
4 | | -One of the goals of bundles is to create discrete bundles of functionality |
5 | | -that do not have many (if any) dependencies, allowing you to use that |
6 | | -functionality in other applications without including unnecessary items. |
| 4 | +In applications where functionality is segregated with minimal concrete dependencies |
| 5 | +between the various layers, such as monoliths which are split into multiple modules, |
| 6 | +it might be hard to prevent hard dependencies on entities between modules. |
7 | 7 |
|
8 | 8 | Doctrine 2.2 includes a new utility called the ``ResolveTargetEntityListener``, |
9 | 9 | that functions by intercepting certain calls inside Doctrine and rewriting |
10 | 10 | ``targetEntity`` parameters in your metadata mapping at runtime. It means that |
11 | | -in your bundle you are able to use an interface or abstract class in your |
12 | | -mappings and expect correct mapping to a concrete entity at runtime. |
| 11 | +you are able to use an interface or abstract class in your mappings and expect |
| 12 | +correct mapping to a concrete entity at runtime. |
13 | 13 |
|
14 | 14 | This functionality allows you to define relationships between different entities |
15 | 15 | without making them hard dependencies. |
16 | 16 |
|
| 17 | +.. tip:: |
| 18 | + |
| 19 | + Starting with Symfony 7.3, this functionality also works with the ``EntityValueResolver``. |
| 20 | + See :ref:`doctrine-entity-value-resolver-resolve-target-entities` for more details. |
| 21 | + |
17 | 22 | Background |
18 | 23 | ---------- |
19 | 24 |
|
20 | | -Suppose you have an InvoiceBundle which provides invoicing functionality |
21 | | -and a CustomerBundle that contains customer management tools. You want |
22 | | -to keep these separated, because they can be used in other systems without |
23 | | -each other, but for your application you want to use them together. |
| 25 | +Suppose you have an application which provides two modules; an Invoice module which |
| 26 | +provides invoicing functionality, and a Customer module that contains customer management |
| 27 | +tools. You want to keep dependencies between these modules separated, because they should |
| 28 | +not be aware of the other module's implementation details. |
24 | 29 |
|
25 | | -In this case, you have an ``Invoice`` entity with a relationship to a |
26 | | -non-existent object, an ``InvoiceSubjectInterface``. The goal is to get |
27 | | -the ``ResolveTargetEntityListener`` to replace any mention of the interface |
| 30 | +In this case, you have an ``Invoice`` entity with a relationship to the interface |
| 31 | +``InvoiceSubjectInterface``. This is not recognized as a valid entity by Doctrine. |
| 32 | +The goal is to get the ``ResolveTargetEntityListener`` to replace any mention of the interface |
28 | 33 | with a real object that implements that interface. |
29 | 34 |
|
30 | 35 | Set up |
@@ -89,7 +94,7 @@ An InvoiceSubjectInterface:: |
89 | 94 | public function getName(): string; |
90 | 95 | } |
91 | 96 |
|
92 | | -Next, you need to configure the listener, which tells the DoctrineBundle |
| 97 | +Next, you need to configure the ``resolve_target_entities`` option, which tells the DoctrineBundle |
93 | 98 | about the replacement: |
94 | 99 |
|
95 | 100 | .. configuration-block:: |
@@ -141,6 +146,6 @@ Final Thoughts |
141 | 146 | -------------- |
142 | 147 |
|
143 | 148 | With the ``ResolveTargetEntityListener``, you are able to decouple your |
144 | | -bundles, keeping them usable by themselves, but still being able to |
| 149 | +modules, keeping them usable by themselves, but still being able to |
145 | 150 | define relationships between different objects. By using this method, |
146 | | -your bundles will end up being easier to maintain independently. |
| 151 | +your modules will end up being easier to maintain independently. |
0 commit comments