1
2
3
4
5
6
7
8
9
10
11
12
13
14 package org.eclipse.jetty.webapp;
15
16 import java.io.IOException;
17 import java.net.URL;
18 import java.util.ArrayList;
19 import java.util.Collection;
20 import java.util.EventListener;
21 import java.util.HashSet;
22 import java.util.Iterator;
23 import java.util.List;
24 import java.util.Set;
25
26 import javax.servlet.Servlet;
27 import javax.servlet.ServletContextEvent;
28 import javax.servlet.ServletContextListener;
29
30 import org.eclipse.jetty.util.Loader;
31 import org.eclipse.jetty.util.log.Log;
32 import org.eclipse.jetty.util.log.Logger;
33 import org.eclipse.jetty.util.resource.Resource;
34 import org.eclipse.jetty.xml.XmlParser;
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55 public class TagLibConfiguration extends AbstractConfiguration
56 {
57 private static final Logger LOG = Log.getLogger(TagLibConfiguration.class);
58
59 public static final String TLD_RESOURCES = "org.eclipse.jetty.tlds";
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76 public class TagLibListener implements ServletContextListener {
77 private List<EventListener> _tldListeners;
78 private WebAppContext _context;
79
80 public TagLibListener (WebAppContext context) {
81 _context = context;
82 }
83
84 public void contextDestroyed(ServletContextEvent sce)
85 {
86 if (_tldListeners == null)
87 return;
88
89 for (int i=_tldListeners.size()-1; i>=0; i--) {
90 EventListener l = _tldListeners.get(i);
91 if (l instanceof ServletContextListener) {
92 ((ServletContextListener)l).contextDestroyed(sce);
93 }
94 }
95 }
96
97 public void contextInitialized(ServletContextEvent sce)
98 {
99 try {
100
101
102 Set<Resource> tlds = findTldResources();
103 List<TldDescriptor> descriptors = parseTlds(tlds);
104 processTlds(descriptors);
105
106 if (_tldListeners == null)
107 return;
108
109
110
111
112 for (EventListener l:_tldListeners) {
113 if (l instanceof ServletContextListener) {
114 ((ServletContextListener)l).contextInitialized(sce);
115 } else {
116 _context.addEventListener(l);
117 }
118 }
119
120 } catch (Exception e) {
121 LOG.warn(e);
122 }
123 }
124
125
126
127
128
129
130
131
132
133
134 private Set<Resource> findTldResources () throws IOException {
135
136 Set<Resource> tlds = new HashSet<Resource>();
137
138
139
140
141 if (_context.getResourceAliases()!=null &&
142 _context.getBaseResource()!=null &&
143 _context.getBaseResource().exists())
144 {
145 Iterator<String> iter=_context.getResourceAliases().values().iterator();
146 while(iter.hasNext())
147 {
148 String location = iter.next();
149 if (location!=null && location.toLowerCase().endsWith(".tld"))
150 {
151 if (!location.startsWith("/"))
152 location="/WEB-INF/"+location;
153 Resource l=_context.getBaseResource().addPath(location);
154 tlds.add(l);
155 }
156 }
157 }
158
159
160 Resource web_inf = _context.getWebInf();
161 if (web_inf!=null)
162 {
163 String[] contents = web_inf.list();
164 for (int i=0;contents!=null && i<contents.length;i++)
165 {
166 if (contents[i]!=null && contents[i].toLowerCase().endsWith(".tld"))
167 {
168 Resource l=web_inf.addPath(contents[i]);
169 tlds.add(l);
170 }
171 }
172 }
173
174
175 if (web_inf != null) {
176 Resource web_inf_tlds = _context.getWebInf().addPath("/tlds/");
177 if (web_inf_tlds.exists() && web_inf_tlds.isDirectory()) {
178 String[] contents = web_inf_tlds.list();
179 for (int i=0;contents!=null && i<contents.length;i++)
180 {
181 if (contents[i]!=null && contents[i].toLowerCase().endsWith(".tld"))
182 {
183 Resource l=web_inf_tlds.addPath(contents[i]);
184 tlds.add(l);
185 }
186 }
187 }
188 }
189
190
191
192
193 @SuppressWarnings("unchecked")
194 Collection<Resource> tld_resources=(Collection<Resource>)_context.getAttribute(TLD_RESOURCES);
195 if (tld_resources!=null)
196 tlds.addAll(tld_resources);
197
198 return tlds;
199 }
200
201
202
203
204
205
206
207 private List<TldDescriptor> parseTlds (Set<Resource> tlds) {
208 List<TldDescriptor> descriptors = new ArrayList<TldDescriptor>();
209
210 Resource tld = null;
211 Iterator<Resource> iter = tlds.iterator();
212 while (iter.hasNext())
213 {
214 try
215 {
216 tld = iter.next();
217 if (LOG.isDebugEnabled()) LOG.debug("TLD="+tld);
218
219 TldDescriptor d = new TldDescriptor(tld);
220 d.parse();
221 descriptors.add(d);
222 }
223 catch(Exception e)
224 {
225 LOG.warn("Unable to parse TLD: " + tld,e);
226 }
227 }
228 return descriptors;
229 }
230
231
232
233
234
235
236
237 private void processTlds (List<TldDescriptor> descriptors) throws Exception {
238
239 TldProcessor processor = new TldProcessor();
240 for (TldDescriptor d:descriptors)
241 processor.process(_context, d);
242
243 _tldListeners = new ArrayList<EventListener>(processor.getListeners());
244 }
245 }
246
247
248
249
250
251
252
253
254
255 public static class TldDescriptor extends Descriptor
256 {
257 protected static XmlParser __parserSingleton;
258
259 public TldDescriptor(Resource xml)
260 {
261 super(xml);
262 }
263
264 @Override
265 public void ensureParser() throws ClassNotFoundException
266 {
267 if (__parserSingleton == null)
268 __parserSingleton = newParser();
269 _parser = __parserSingleton;
270 }
271
272 @Override
273 public XmlParser newParser() throws ClassNotFoundException
274 {
275
276 XmlParser parser = new XmlParser(false);
277
278 URL taglib11=null;
279 URL taglib12=null;
280 URL taglib20=null;
281 URL taglib21=null;
282
283 try
284 {
285 Class<?> jsp_page = Loader.loadClass(WebXmlConfiguration.class,"javax.servlet.jsp.JspPage");
286 taglib11=jsp_page.getResource("javax/servlet/jsp/resources/web-jsptaglibrary_1_1.dtd");
287 taglib12=jsp_page.getResource("javax/servlet/jsp/resources/web-jsptaglibrary_1_2.dtd");
288 taglib20=jsp_page.getResource("javax/servlet/jsp/resources/web-jsptaglibrary_2_0.xsd");
289 taglib21=jsp_page.getResource("javax/servlet/jsp/resources/web-jsptaglibrary_2_1.xsd");
290 }
291 catch(Exception e)
292 {
293 LOG.ignore(e);
294 }
295 finally
296 {
297 if(taglib11==null)
298 taglib11=Loader.getResource(Servlet.class,"javax/servlet/jsp/resources/web-jsptaglibrary_1_1.dtd",true);
299 if(taglib12==null)
300 taglib12=Loader.getResource(Servlet.class,"javax/servlet/jsp/resources/web-jsptaglibrary_1_2.dtd",true);
301 if(taglib20==null)
302 taglib20=Loader.getResource(Servlet.class,"javax/servlet/jsp/resources/web-jsptaglibrary_2_0.xsd",true);
303 if(taglib21==null)
304 taglib21=Loader.getResource(Servlet.class,"javax/servlet/jsp/resources/web-jsptaglibrary_2_1.xsd",true);
305 }
306
307
308 if(taglib11!=null)
309 {
310 redirect(parser, "web-jsptaglib_1_1.dtd",taglib11);
311 redirect(parser, "web-jsptaglibrary_1_1.dtd",taglib11);
312 }
313 if(taglib12!=null)
314 {
315 redirect(parser, "web-jsptaglib_1_2.dtd",taglib12);
316 redirect(parser, "web-jsptaglibrary_1_2.dtd",taglib12);
317 }
318 if(taglib20!=null)
319 {
320 redirect(parser, "web-jsptaglib_2_0.xsd",taglib20);
321 redirect(parser, "web-jsptaglibrary_2_0.xsd",taglib20);
322 }
323 if(taglib21!=null)
324 {
325 redirect(parser, "web-jsptaglib_2_1.xsd",taglib21);
326 redirect(parser, "web-jsptaglibrary_2_1.xsd",taglib21);
327 }
328
329 parser.setXpath("/taglib/listener/listener-class");
330 return parser;
331 }
332
333 public void parse ()
334 throws Exception
335 {
336 ensureParser();
337 try
338 {
339
340
341
342 _root = _parser.parse(_xml.getInputStream());
343 }
344 catch (Exception e)
345 {
346 _root = _parser.parse(_xml.getURL().toString());
347 }
348
349 if (_root==null)
350 {
351 LOG.warn("No TLD root in {}",_xml);
352 }
353 }
354 }
355
356
357
358
359
360
361
362 public class TldProcessor extends IterativeDescriptorProcessor
363 {
364 public static final String TAGLIB_PROCESSOR = "org.eclipse.jetty.tagLibProcessor";
365 XmlParser _parser;
366 List<XmlParser.Node> _roots = new ArrayList<XmlParser.Node>();
367 List<EventListener> _listeners;
368
369
370 public TldProcessor ()
371 throws Exception
372 {
373 _listeners = new ArrayList<EventListener>();
374 registerVisitor("listener", this.getClass().getDeclaredMethod("visitListener", __signature));
375 }
376
377
378 public void visitListener (WebAppContext context, Descriptor descriptor, XmlParser.Node node)
379 {
380 String className=node.getString("listener-class",false,true);
381 if (LOG.isDebugEnabled()) LOG.debug("listener="+className);
382
383 try
384 {
385 Class<?> listenerClass = context.loadClass(className);
386 EventListener l = (EventListener)listenerClass.newInstance();
387 _listeners.add(l);
388 }
389 catch(Exception e)
390 {
391 LOG.warn("Could not instantiate listener "+className+": "+e);
392 LOG.debug(e);
393 }
394 catch(Error e)
395 {
396 LOG.warn("Could not instantiate listener "+className+": "+e);
397 LOG.debug(e);
398 }
399
400 }
401
402 @Override
403 public void end(WebAppContext context, Descriptor descriptor)
404 {
405 }
406
407 @Override
408 public void start(WebAppContext context, Descriptor descriptor)
409 {
410 }
411
412 public List<EventListener> getListeners() {
413 return _listeners;
414 }
415 }
416
417
418 @Override
419 public void preConfigure(WebAppContext context) throws Exception
420 {
421 try
422 {
423 Class<?> jsp_page = Loader.loadClass(WebXmlConfiguration.class,"javax.servlet.jsp.JspPage");
424 }
425 catch (Exception e)
426 {
427
428 return;
429 }
430
431 TagLibListener tagLibListener = new TagLibListener(context);
432 context.addEventListener(tagLibListener);
433 }
434
435
436 @Override
437 public void configure (WebAppContext context) throws Exception
438 {
439 }
440
441 @Override
442 public void postConfigure(WebAppContext context) throws Exception
443 {
444 }
445
446
447 @Override
448 public void cloneConfigure(WebAppContext template, WebAppContext context) throws Exception
449 {
450 }
451
452
453 @Override
454 public void deconfigure(WebAppContext context) throws Exception
455 {
456 }
457 }