1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
namespace Happyr\SimpleBusBundle\DependencyInjection\CompilerPass; |
4
|
|
|
|
5
|
|
|
use Happyr\SimpleBusBundle\Message\Publisher\RabbitMQPublisher; |
6
|
|
|
use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface; |
7
|
|
|
use Symfony\Component\DependencyInjection\ContainerBuilder; |
8
|
|
|
use Symfony\Component\DependencyInjection\ContainerInterface; |
9
|
|
|
use Symfony\Component\DependencyInjection\Reference; |
10
|
|
|
|
11
|
|
|
/** |
12
|
|
|
* @author Tobias Nyholm |
13
|
|
|
*/ |
14
|
|
|
class CompilerPasses implements CompilerPassInterface |
15
|
|
|
{ |
16
|
1 |
|
public function process(ContainerBuilder $container) |
17
|
|
|
{ |
18
|
1 |
|
$this->removeCommandHandlerDuplicates($container); |
19
|
1 |
|
$this->handleEventSubscriberDuplicates($container); |
20
|
1 |
|
$this->processMessageHandlers($container); |
21
|
1 |
|
$this->replaceSimpleBusPublisher($container); |
22
|
1 |
|
} |
23
|
|
|
|
24
|
|
|
/** |
25
|
|
|
* If we find to command handler services that are registered on the same command, make sure we remove the one with '.auto' on the end. |
26
|
|
|
* |
27
|
|
|
* @param ContainerBuilder $container |
28
|
|
|
*/ |
29
|
1 |
|
private function removeCommandHandlerDuplicates(ContainerBuilder $container) |
30
|
|
|
{ |
31
|
1 |
|
$taggedServices = array_merge($container->findTaggedServiceIds('command_handler'), $container->findTaggedServiceIds('asynchronous_command_handler')); |
32
|
|
|
|
33
|
1 |
|
$commands = []; |
34
|
|
|
|
35
|
1 |
|
foreach ($taggedServices as $id => $tags) { |
36
|
1 |
|
foreach ($tags as $tag) { |
37
|
1 |
|
if (isset($commands[$tag['handles']])) { |
38
|
|
|
// Find the one that ends with '.auto' |
39
|
|
|
$removeServiceId = null; |
40
|
|
|
|
41
|
|
|
if (substr($id, -5) === '.auto') { |
42
|
|
|
$removeServiceId = $id; |
43
|
|
|
} |
44
|
|
|
|
45
|
|
|
if (substr($commands[$tag['handles']], -5) === '.auto') { |
46
|
|
|
$removeServiceId = $commands[$tag['handles']]; |
47
|
|
|
$commands[$tag['handles']] = $id; |
48
|
|
|
} |
49
|
|
|
|
50
|
|
|
if ($removeServiceId !== null) { |
51
|
|
|
// Remove the definition |
52
|
|
|
$container->removeDefinition($removeServiceId); |
53
|
|
|
continue; |
54
|
|
|
} |
55
|
|
|
} |
56
|
1 |
|
$commands[$tag['handles']] = $id; |
57
|
|
|
} |
58
|
|
|
} |
59
|
1 |
|
} |
60
|
|
|
|
61
|
|
|
/** |
62
|
|
|
* @param ContainerBuilder $container |
63
|
|
|
*/ |
64
|
1 |
|
private function handleEventSubscriberDuplicates(ContainerBuilder $container) |
65
|
|
|
{ |
66
|
1 |
|
$taggedServices = array_merge($container->findTaggedServiceIds('event_subscriber'), $container->findTaggedServiceIds('asynchronous_event_subscriber')); |
67
|
|
|
|
68
|
|
|
// Keys are event class names |
69
|
1 |
|
$events = []; |
70
|
|
|
|
71
|
1 |
|
foreach ($taggedServices as $id => $tags) { |
72
|
1 |
|
foreach ($tags as $tag) { |
73
|
1 |
|
if (isset($tag['subscribes_to'])) { |
74
|
1 |
|
$events[$tag['subscribes_to']][] = $id; |
75
|
|
|
} |
76
|
|
|
} |
77
|
|
|
} |
78
|
|
|
|
79
|
1 |
|
foreach ($events as $eventClass => $subscribersIds) { |
80
|
1 |
|
if (count($subscribersIds) <= 1) { |
81
|
1 |
|
continue; |
82
|
|
|
} |
83
|
|
|
|
84
|
|
|
// Get services |
85
|
|
|
$subscriberClassNames = []; |
86
|
|
|
foreach ($subscribersIds as $subscribersId) { |
87
|
|
|
$service = $container->getDefinition($subscribersId); |
88
|
|
|
$subscriberClassNames[$service->getClass()][] = $subscribersId; |
89
|
|
|
} |
90
|
|
|
|
91
|
|
|
foreach ($subscriberClassNames as $className => $services) { |
92
|
|
|
if (count($services) <= 1) { |
93
|
|
|
continue; |
94
|
|
|
} |
95
|
|
|
|
96
|
|
|
// IF we have multiple services registed to the same event subscriber, remove the auto added ones. |
97
|
|
|
foreach ($services as $serviceId) { |
98
|
|
|
if (substr($serviceId, -5) === '.auto') { |
99
|
|
|
$container->removeDefinition($serviceId); |
100
|
|
|
} |
101
|
|
|
} |
102
|
|
|
} |
103
|
|
|
} |
104
|
1 |
|
} |
105
|
|
|
|
106
|
|
|
/** |
107
|
|
|
* @param ContainerBuilder $container |
108
|
|
|
*/ |
109
|
1 |
|
private function processMessageHandlers(ContainerBuilder $container) |
110
|
|
|
{ |
111
|
1 |
|
$taggedServices = array_merge( |
112
|
1 |
|
$container->findTaggedServiceIds('command_handler'), |
113
|
1 |
|
$container->findTaggedServiceIds('event_subscriber'), |
114
|
1 |
|
$container->findTaggedServiceIds('asynchronous_command_handler'), |
115
|
1 |
|
$container->findTaggedServiceIds('asynchronous_event_subscriber') |
116
|
|
|
); |
117
|
1 |
|
$doctrine = $this->hasDoctrine($container); |
118
|
|
|
|
119
|
1 |
|
foreach ($taggedServices as $id => $tags) { |
120
|
1 |
|
$def = $container->findDefinition($id); |
121
|
1 |
|
$class = $def->getClass(); |
122
|
|
|
|
123
|
1 |
|
if (method_exists($class, 'setEventRecorder')) { |
124
|
|
|
$def->addMethodCall('setEventRecorder', [new Reference('event_recorder')]); |
125
|
|
|
} |
126
|
|
|
|
127
|
1 |
|
if (method_exists($class, 'setCommandBus')) { |
128
|
|
|
$def->addMethodCall('setCommandBus', [new Reference('command_bus')]); |
129
|
|
|
} |
130
|
|
|
|
131
|
1 |
|
if (method_exists($class, 'setEventBus')) { |
132
|
|
|
$def->addMethodCall('setEventBus', [new Reference('event_bus')]); |
133
|
|
|
} |
134
|
|
|
|
135
|
1 |
|
if ($doctrine && method_exists($class, 'setEntityManager')) { |
136
|
|
|
$def->addMethodCall('setEntityManager', [new Reference('doctrine.orm.entity_manager')]); |
137
|
|
|
} |
138
|
|
|
|
139
|
1 |
|
if (in_array('Psr\Log\LoggerAwareInterface', class_implements($class))) { |
140
|
1 |
|
$def->addMethodCall('setLogger', [new Reference('logger', ContainerInterface::NULL_ON_INVALID_REFERENCE)]); |
141
|
|
|
} |
142
|
|
|
} |
143
|
1 |
|
} |
144
|
|
|
|
145
|
|
|
/** |
146
|
|
|
* @param ContainerBuilder $container |
147
|
|
|
*/ |
148
|
1 |
|
private function replaceSimpleBusPublisher(ContainerBuilder $container) |
149
|
|
|
{ |
150
|
1 |
|
if ($container->has('simple_bus.rabbit_mq_bundle_bridge.event_publisher')) { |
151
|
1 |
|
$container->getDefinition('simple_bus.rabbit_mq_bundle_bridge.event_publisher') |
152
|
1 |
|
->setClass(RabbitMQPublisher::class) |
153
|
1 |
|
->setLazy(true); |
154
|
1 |
|
$container->getDefinition('simple_bus.rabbit_mq_bundle_bridge.command_publisher') |
155
|
1 |
|
->setClass(RabbitMQPublisher::class) |
156
|
1 |
|
->setLazy(true); |
157
|
|
|
} |
158
|
1 |
|
} |
159
|
|
|
|
160
|
|
|
/** |
161
|
|
|
* @param ContainerBuilder $container |
162
|
|
|
* |
163
|
|
|
* @return bool |
164
|
|
|
*/ |
165
|
1 |
|
private function hasDoctrine(ContainerBuilder $container) |
166
|
|
|
{ |
167
|
1 |
|
return $container->hasDefinition('doctrine.orm.entity_manager') || |
168
|
1 |
|
$container->hasAlias('doctrine.orm.entity_manager'); |
169
|
|
|
} |
170
|
|
|
} |
171
|
|
|
|