1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package info.magnolia.objectfactory.guice;
35
36 import info.magnolia.cms.core.SystemProperty;
37 import info.magnolia.objectfactory.ComponentProvider;
38 import info.magnolia.objectfactory.Components;
39 import info.magnolia.objectfactory.configuration.ComponentConfigurer;
40 import info.magnolia.objectfactory.configuration.ComponentProviderConfiguration;
41
42 import java.util.ArrayList;
43 import java.util.List;
44
45 import org.slf4j.Logger;
46 import org.slf4j.LoggerFactory;
47
48 import com.google.inject.AbstractModule;
49 import com.google.inject.CreationException;
50 import com.google.inject.Guice;
51 import com.google.inject.Injector;
52 import com.google.inject.Module;
53 import com.google.inject.Stage;
54 import com.google.inject.util.Modules;
55 import com.mycila.inject.jsr250.Jsr250;
56
57
58
59
60 public class GuiceComponentProviderBuilder {
61
62 private static final Logger log = LoggerFactory.getLogger(GuiceComponentProviderBuilder.class);
63 private ComponentProviderConfiguration configuration;
64 private boolean exposeGlobally;
65 private GuiceComponentProvider parent;
66 private final List<Module> extraModules = new ArrayList<Module>();
67 private Stage stage;
68
69 public GuiceComponentProviderBuilder exposeGlobally() {
70 this.exposeGlobally = true;
71 return this;
72 }
73
74 public GuiceComponentProviderBuilder withConfiguration(ComponentProviderConfiguration configuration) {
75 this.configuration = configuration;
76 return this;
77 }
78
79 public GuiceComponentProviderBuilder withParent(GuiceComponentProvider parent) {
80 this.parent = parent;
81 return this;
82 }
83
84 public GuiceComponentProviderBuilder inStage(Stage stage) {
85 this.stage = stage;
86 return this;
87 }
88
89 public void addModule(Module module) {
90 this.extraModules.add(module);
91 }
92
93 public GuiceComponentProvider build(ComponentConfigurer... configurers) {
94
95 if (configuration == null) {
96 configuration = new ComponentProviderConfiguration();
97 }
98
99
100 for (ComponentConfigurer configurer : configurers) {
101 configuration.addConfigurer(configurer);
102 }
103
104
105 for (ComponentConfigurer configurer : configuration.getConfigurers()) {
106 configurer.doWithConfiguration(parent, configuration);
107 }
108
109
110 final GuiceComponentProvider componentProvider = new GuiceComponentProvider(configuration.getTypeMapping(), parent);
111 if (exposeGlobally) {
112 Components.setComponentProvider(componentProvider);
113 }
114
115 Module module = new AbstractModule() {
116 @Override
117 protected void configure() {
118
119
120 bind(ComponentProvider.class).toInstance(componentProvider);
121
122
123 if (Boolean.valueOf(SystemProperty.getProperty("magnolia.jsr250.enabled", "true"))) {
124
125 install(Jsr250.newJsr250Module());
126 }
127
128 install(new GuiceComponentConfigurationModule(configuration));
129
130 for (Module extraModule : extraModules) {
131 binder().install(extraModule);
132 }
133 }
134 };
135
136 if (parent != null) {
137 GuiceParentBindingsModule parentBindingsModule = new GuiceParentBindingsModule(parent.getInjector());
138 module = Modules.override(parentBindingsModule).with(module);
139 }
140
141 try {
142 Injector injector = Guice.createInjector(resolveStageToUse(), module);
143 return (GuiceComponentProvider) injector.getInstance(ComponentProvider.class);
144 } catch (CreationException e) {
145 log.error("Magnolia failed to load module configuration with types {} and components {}. Please ensure you don't have any legacy modules present in your web application.", configuration.getTypeMapping(), configuration.getComponents(), e);
146 throw e;
147 }
148
149 }
150
151 public GuiceComponentProvider build() {
152 return build(new GuiceContextAndScopesConfigurer(), new GuicePropertyConfigurer());
153 }
154
155 private Stage resolveStageToUse() {
156 if (stage != null) {
157 return stage;
158 }
159 if (parent != null) {
160 return parent.getInjector().getInstance(Stage.class);
161 }
162 return Stage.PRODUCTION;
163 }
164 }