1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 package org.jumpmind.symmetric;
22
23 import javax.servlet.ServletContext;
24 import javax.servlet.ServletContextEvent;
25
26 import org.apache.commons.logging.Log;
27 import org.apache.commons.logging.LogFactory;
28 import org.springframework.beans.BeanUtils;
29 import org.springframework.beans.BeansException;
30 import org.springframework.context.ApplicationContext;
31 import org.springframework.context.ApplicationContextException;
32 import org.springframework.util.StringUtils;
33 import org.springframework.web.context.ConfigurableWebApplicationContext;
34 import org.springframework.web.context.ContextLoader;
35 import org.springframework.web.context.ContextLoaderListener;
36 import org.springframework.web.context.WebApplicationContext;
37 import org.springframework.web.context.support.WebApplicationContextUtils;
38
39 /***
40 * This is the standard way to bootstrap Symmetric in a web container. Symmetric
41 * uses Spring's WebApplicationContext for access to symmetric from its
42 * Servlets. This servlet context listener forces the contextConfigLocation for
43 * Spring to be load symmetric.xml. <p/> Developers have the option to subclass
44 * off of this listener and override the createConfigureAndStartEngine() method.
45 */
46 public class SymmetricEngineContextLoaderListener extends ContextLoaderListener {
47
48 static final String SYMMETRIC_SPRING_LOCATION = "classpath:/symmetric.xml";
49
50 static final Log logger = LogFactory.getLog(SymmetricEngineContextLoaderListener.class);
51
52 SymmetricEngine engine = null;
53
54 public SymmetricEngineContextLoaderListener() {
55 }
56
57 public SymmetricEngineContextLoaderListener(SymmetricEngine engine) {
58 this.engine = engine;
59 }
60
61 @Override
62 final public void contextInitialized(ServletContextEvent event) {
63 try {
64 super.contextInitialized(event);
65 ApplicationContext ctx = WebApplicationContextUtils.getWebApplicationContext(event.getServletContext());
66 createConfigureAndStartEngine(ctx);
67 } catch (Exception ex) {
68 logger.error("Failed to initialize the web server context.", ex);
69 if (ex instanceof RuntimeException) {
70 throw (RuntimeException) ex;
71 } else {
72 throw new RuntimeException(ex);
73 }
74 }
75 }
76
77 @Override
78 public void contextDestroyed(ServletContextEvent event) {
79 if (engine != null) {
80 engine.stop();
81 engine = null;
82 }
83 }
84
85 protected void createConfigureAndStartEngine(ApplicationContext ctx) {
86 if (this.engine == null) {
87 this.engine = new SymmetricEngine(ctx);
88 }
89 engine.start();
90 }
91
92 @Override
93 protected ContextLoader createContextLoader() {
94 return new ContextLoader() {
95 @SuppressWarnings("unchecked")
96 protected WebApplicationContext createWebApplicationContext(ServletContext servletContext,
97 ApplicationContext parent) throws BeansException {
98
99 Class contextClass = determineContextClass(servletContext);
100 if (!ConfigurableWebApplicationContext.class.isAssignableFrom(contextClass)) {
101 throw new ApplicationContextException("Custom context class [" + contextClass.getName()
102 + "] is not of type ConfigurableWebApplicationContext");
103 }
104
105 ConfigurableWebApplicationContext wac = (ConfigurableWebApplicationContext) BeanUtils
106 .instantiateClass(contextClass);
107 wac.setParent(parent);
108 wac.setServletContext(servletContext);
109 String configLocation = servletContext.getInitParameter(CONFIG_LOCATION_PARAM);
110 if (configLocation == null) {
111 configLocation = SYMMETRIC_SPRING_LOCATION;
112 } else if (!configLocation.contains(SYMMETRIC_SPRING_LOCATION)) {
113 configLocation = SYMMETRIC_SPRING_LOCATION + "," + configLocation;
114 }
115 wac.setConfigLocations(StringUtils.tokenizeToStringArray(configLocation,
116 ConfigurableWebApplicationContext.CONFIG_LOCATION_DELIMITERS));
117
118 wac.refresh();
119 return wac;
120 }
121 };
122 }
123
124 public SymmetricEngine getEngine() {
125 return engine;
126 }
127
128 }