1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.myfaces.webapp;
20
21 import org.apache.myfaces.buildtools.maven2.plugin.builder.annotation.JSFWebConfigParam;
22 import org.apache.myfaces.config.annotation.LifecycleProviderFactory;
23 import org.apache.myfaces.shared.util.ClassUtils;
24
25 import javax.faces.FactoryFinder;
26 import javax.faces.context.ExternalContext;
27 import javax.faces.context.FacesContext;
28 import javax.servlet.ServletContext;
29 import javax.servlet.ServletContextAttributeEvent;
30 import javax.servlet.ServletContextAttributeListener;
31 import javax.servlet.ServletContextEvent;
32 import javax.servlet.ServletContextListener;
33 import javax.servlet.ServletRequestAttributeEvent;
34 import javax.servlet.ServletRequestAttributeListener;
35 import javax.servlet.ServletRequestEvent;
36 import javax.servlet.ServletRequestListener;
37 import javax.servlet.http.HttpSessionAttributeListener;
38 import javax.servlet.http.HttpSessionBindingEvent;
39 import javax.servlet.http.HttpSessionEvent;
40 import javax.servlet.http.HttpSessionListener;
41 import java.lang.reflect.InvocationTargetException;
42 import java.lang.reflect.Method;
43 import java.util.ArrayList;
44 import java.util.Iterator;
45 import java.util.LinkedList;
46 import java.util.List;
47 import java.util.Map;
48 import java.util.logging.Level;
49 import java.util.logging.Logger;
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69 public class StartupServletContextListener implements ServletContextListener,
70 HttpSessionAttributeListener, HttpSessionListener,
71 ServletRequestListener, ServletRequestAttributeListener,
72 ServletContextAttributeListener
73 {
74 static final String FACES_INIT_DONE = "org.apache.myfaces.webapp.StartupServletContextListener.FACES_INIT_DONE";
75
76
77
78
79 @JSFWebConfigParam(since="2.0")
80 static final String FACES_INIT_PLUGINS = "org.apache.myfaces.FACES_INIT_PLUGINS";
81
82 private static final byte FACES_INIT_PHASE_PREINIT = 0;
83 private static final byte FACES_INIT_PHASE_POSTINIT = 1;
84 private static final byte FACES_INIT_PHASE_PREDESTROY = 2;
85 private static final byte FACES_INIT_PHASE_POSTDESTROY = 3;
86
87
88 private static final Logger log = Logger.getLogger(StartupServletContextListener.class.getName());
89
90 private FacesInitializer _facesInitializer;
91 private ServletContext _servletContext;
92 private ManagedBeanDestroyerListener _detroyerListener = new ManagedBeanDestroyerListener();
93
94 public void contextInitialized(ServletContextEvent event)
95 {
96 if (_servletContext != null)
97 {
98 throw new IllegalStateException("context is already initialized");
99 }
100 _servletContext = event.getServletContext();
101
102 Boolean b = (Boolean) _servletContext.getAttribute(FACES_INIT_DONE);
103 if (b == null || b.booleanValue() == false)
104 {
105 if (_facesInitializer == null)
106 {
107 _facesInitializer = FacesInitializerFactory.getFacesInitializer(_servletContext);
108 }
109
110
111 FacesContext facesContext = _facesInitializer.initStartupFacesContext(_servletContext);
112
113
114 _publishManagedBeanDestroyerListener(facesContext);
115
116 dispatchInitializationEvent(event, FACES_INIT_PHASE_PREINIT);
117 _facesInitializer.initFaces(_servletContext);
118 dispatchInitializationEvent(event, FACES_INIT_PHASE_POSTINIT);
119 _servletContext.setAttribute(FACES_INIT_DONE, Boolean.TRUE);
120
121
122 _detroyerListener.contextInitialized(event);
123
124
125 _facesInitializer.destroyStartupFacesContext(facesContext);
126 }
127 else
128 {
129 log.info("MyFaces already initialized");
130 }
131 }
132
133
134
135
136
137
138
139
140 private void _publishManagedBeanDestroyerListener(FacesContext facesContext)
141 {
142 ExternalContext externalContext = facesContext.getExternalContext();
143 Map<String, Object> applicationMap = externalContext.getApplicationMap();
144
145 applicationMap.put(ManagedBeanDestroyerListener.APPLICATION_MAP_KEY, _detroyerListener);
146 }
147
148 public void contextDestroyed(ServletContextEvent event)
149 {
150 if (_facesInitializer != null && _servletContext != null)
151 {
152
153 FacesContext facesContext = _facesInitializer.initShutdownFacesContext(_servletContext);
154
155 dispatchInitializationEvent(event, FACES_INIT_PHASE_PREDESTROY);
156
157 _detroyerListener.contextDestroyed(event);
158
159 _facesInitializer.destroyFaces(_servletContext);
160
161 LifecycleProviderFactory.getLifecycleProviderFactory().release();
162
163
164
165 if (facesContext != null)
166 {
167 _facesInitializer.destroyShutdownFacesContext(facesContext);
168 }
169
170 FactoryFinder.releaseFactories();
171
172
173 dispatchInitializationEvent(event, FACES_INIT_PHASE_POSTDESTROY);
174 }
175
176 _servletContext = null;
177 }
178
179
180
181
182
183
184 public void setFacesInitializer(FacesInitializer facesInitializer)
185 {
186 if (_facesInitializer != null && _facesInitializer != facesInitializer && _servletContext != null)
187 {
188 _facesInitializer.destroyFaces(_servletContext);
189 }
190 _facesInitializer = facesInitializer;
191 if (_servletContext != null)
192 {
193 facesInitializer.initFaces(_servletContext);
194 }
195 }
196
197
198
199
200
201
202
203
204 private boolean loadFacesInitPluginsJDK6()
205 {
206 String[] pluginEntries = null;
207 try
208 {
209 Class serviceLoader = ClassUtils.getContextClassLoader().loadClass("java.util.ServiceLoader");
210 Method m = serviceLoader.getDeclaredMethod("load", Class.class, ClassLoader.class);
211 Object loader = m.invoke(serviceLoader, StartupListener.class, ClassUtils.getContextClassLoader());
212 m = loader.getClass().getDeclaredMethod("iterator");
213 Iterator<StartupListener> it = (Iterator<StartupListener>) m.invoke(loader);
214 List<StartupListener> listeners = new LinkedList<StartupListener>();
215 if (!it.hasNext())
216 {
217 return false;
218 }
219 while (it.hasNext())
220 {
221 listeners.add(it.next());
222 }
223
224 _servletContext.setAttribute(FACES_INIT_PLUGINS, listeners);
225 return true;
226 }
227 catch (ClassNotFoundException e)
228 {
229
230 }
231 catch (NoSuchMethodException e)
232 {
233 log.log(Level.SEVERE, e.getMessage(), e);
234 }
235 catch (InvocationTargetException e)
236 {
237 log.log(Level.SEVERE, e.getMessage(), e);
238 }
239 catch (IllegalAccessException e)
240 {
241 log.log(Level.SEVERE, e.getMessage(), e);
242 }
243 return false;
244 }
245
246
247
248
249
250 private void loadFacesInitPluginsJDK5()
251 {
252
253 String plugins = (String) _servletContext.getInitParameter(FACES_INIT_PLUGINS);
254 if (plugins == null)
255 {
256 return;
257 }
258 log.info("MyFaces Plugins found");
259 String[] pluginEntries = plugins.split(",");
260 List<StartupListener> listeners = new ArrayList<StartupListener>(pluginEntries.length);
261 for (String pluginEntry : pluginEntries)
262 {
263 try
264 {
265 Class pluginClass = null;
266 pluginClass = ClassUtils.getContextClassLoader().loadClass(pluginEntry);
267 if (pluginClass == null)
268 {
269 pluginClass = this.getClass().getClassLoader().loadClass(pluginEntry);
270 }
271 listeners.add((StartupListener) pluginClass.newInstance());
272 }
273 catch (ClassNotFoundException e)
274 {
275 log.log(Level.SEVERE, e.getMessage(), e);
276 }
277 catch (InstantiationException e)
278 {
279 log.log(Level.SEVERE, e.getMessage(), e);
280 }
281 catch (IllegalAccessException e)
282 {
283 log.log(Level.SEVERE, e.getMessage(), e);
284 }
285 }
286
287 _servletContext.setAttribute(FACES_INIT_PLUGINS, listeners);
288
289 }
290
291
292
293
294
295
296
297
298
299 private void dispatchInitializationEvent(ServletContextEvent event, int operation)
300 {
301
302 if (operation == FACES_INIT_PHASE_PREINIT)
303 {
304 if (!loadFacesInitPluginsJDK6())
305 {
306 loadFacesInitPluginsJDK5();
307 }
308 }
309
310 List<StartupListener> pluginEntries = (List<StartupListener>) _servletContext.getAttribute(FACES_INIT_PLUGINS);
311 if (pluginEntries == null)
312 {
313 return;
314 }
315
316
317 for (StartupListener initializer : pluginEntries)
318 {
319 log.info("Processing plugin");
320
321
322
323
324 switch (operation)
325 {
326 case FACES_INIT_PHASE_PREINIT:
327 initializer.preInit(event);
328 break;
329 case FACES_INIT_PHASE_POSTINIT:
330 initializer.postInit(event);
331 break;
332 case FACES_INIT_PHASE_PREDESTROY:
333 initializer.preDestroy(event);
334 break;
335 default:
336 initializer.postDestroy(event);
337 break;
338 }
339 }
340 log.info("Processing MyFaces plugins done");
341 }
342
343
344
345
346 public void attributeAdded(HttpSessionBindingEvent event)
347 {
348 _detroyerListener.attributeAdded(event);
349 }
350
351 public void attributeRemoved(HttpSessionBindingEvent event)
352 {
353 _detroyerListener.attributeRemoved(event);
354 }
355
356 public void attributeReplaced(HttpSessionBindingEvent event)
357 {
358 _detroyerListener.attributeReplaced(event);
359 }
360
361 public void sessionCreated(HttpSessionEvent event)
362 {
363 _detroyerListener.sessionCreated(event);
364 }
365
366 public void sessionDestroyed(HttpSessionEvent event)
367 {
368 _detroyerListener.sessionDestroyed(event);
369 }
370
371
372
373 public void attributeAdded(ServletContextAttributeEvent event)
374 {
375 _detroyerListener.attributeAdded(event);
376 }
377
378 public void attributeRemoved(ServletContextAttributeEvent event)
379 {
380 _detroyerListener.attributeRemoved(event);
381 }
382
383 public void attributeReplaced(ServletContextAttributeEvent event)
384 {
385 _detroyerListener.attributeReplaced(event);
386 }
387
388
389
390 public void attributeAdded(ServletRequestAttributeEvent event)
391 {
392 _detroyerListener.attributeAdded(event);
393 }
394
395 public void attributeRemoved(ServletRequestAttributeEvent event)
396 {
397 _detroyerListener.attributeRemoved(event);
398 }
399
400 public void attributeReplaced(ServletRequestAttributeEvent event)
401 {
402 _detroyerListener.attributeReplaced(event);
403 }
404
405 public void requestInitialized(ServletRequestEvent event)
406 {
407 _detroyerListener.requestInitialized(event);
408 }
409
410 public void requestDestroyed(ServletRequestEvent event)
411 {
412 _detroyerListener.requestDestroyed(event);
413 }
414
415 }