KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > caucho > jsp > JspCompilerInstance


1 /*
2  * Copyright (c) 1998-2006 Caucho Technology -- all rights reserved
3  *
4  * This file is part of Resin(R) Open Source
5  *
6  * Each copy or derived work must preserve the copyright notice and this
7  * notice unmodified.
8  *
9  * Resin Open Source is free software; you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 2 of the License, or
12  * (at your option) any later version.
13  *
14  * Resin Open Source is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or any warranty
17  * of NON-INFRINGEMENT. See the GNU General Public License for more
18  * details.
19  *
20  * You should have received a copy of the GNU General Public License
21  * along with Resin Open Source; if not, write to the
22  *
23  * Free Software Foundation, Inc.
24  * 59 Temple Place, Suite 330
25  * Boston, MA 02111-1307 USA
26  *
27  * @author Scott Ferguson
28  */

29
30 package com.caucho.jsp;
31
32 import com.caucho.java.JavaCompiler;
33 import com.caucho.java.LineMap;
34 import com.caucho.jsp.cfg.JspConfig;
35 import com.caucho.jsp.cfg.JspPropertyGroup;
36 import com.caucho.jsp.java.JspTagSupport;
37 import com.caucho.jsp.java.TagTaglib;
38 import com.caucho.log.Log;
39 import com.caucho.server.webapp.WebApp;
40 import com.caucho.vfs.Path;
41 import com.caucho.vfs.PersistentDependency;
42 import com.caucho.xml.Xml;
43
44 import org.xml.sax.SAXException JavaDoc;
45
46 import javax.servlet.jsp.tagext.TagInfo JavaDoc;
47 import javax.servlet.jsp.tagext.TagLibraryInfo JavaDoc;
48 import java.io.FileNotFoundException JavaDoc;
49 import java.io.IOException JavaDoc;
50 import java.io.InputStream JavaDoc;
51 import java.util.ArrayList JavaDoc;
52 import java.util.logging.Level JavaDoc;
53 import java.util.logging.Logger JavaDoc;
54
55 /**
56  * Compilation interface for JSP pages.
57  */

58 public class JspCompilerInstance {
59   private static final Logger JavaDoc log = Log.open(JspCompilerInstance.class);
60
61   // The underlying compiler
62
private JspCompiler _jspCompiler;
63
64   // The path to the JSP source
65
private Path _jspPath;
66
67   // The JSP uri (user-name)
68
private String JavaDoc _uri;
69
70   // The JSP class name
71
private String JavaDoc _className;
72
73   private JspPropertyGroup _jspPropertyGroup;
74
75   // The builder
76
private JspBuilder _jspBuilder;
77
78   // true for XML parsing
79
private boolean _isXml;
80
81   // true for prototype parsing.
82
private boolean _isPrototype;
83
84   // true for generated source (like XTP)
85
private boolean _isGeneratedSource;
86
87   // The parse state
88
private ParseState _parseState;
89
90   // The tag manager
91
private ParseTagManager _tagManager;
92
93   // The parser
94
private JspParser _parser;
95
96   // The compiled page
97
private Page _page;
98
99   // The generator
100
private JspGenerator _generator;
101
102   private ArrayList JavaDoc<String JavaDoc> _preludeList = new ArrayList JavaDoc<String JavaDoc>();
103   private ArrayList JavaDoc<String JavaDoc> _codaList = new ArrayList JavaDoc<String JavaDoc>();
104
105   private ArrayList JavaDoc<PersistentDependency> _dependList =
106     new ArrayList JavaDoc<PersistentDependency>();
107
108   /**
109    * Creates a JSP compiler instance.
110    */

111   JspCompilerInstance(JspCompiler compiler)
112   {
113     _jspCompiler = compiler;
114
115     _isXml = _jspCompiler.isXml();
116   }
117
118   /**
119    * Sets the builder.
120    */

121   void setJspBuilder(JspBuilder builder)
122   {
123     _jspBuilder = builder;
124   }
125
126   /**
127    * Sets the path.
128    */

129   void setJspPath(Path path)
130   {
131     _jspPath = path;
132   }
133
134   /**
135    * Sets the uri
136    */

137   void setURI(String JavaDoc uri)
138   {
139     _uri = uri;
140   }
141
142   /**
143    * Sets true for xml
144    */

145   void setXML(boolean isXml)
146   {
147     _isXml = isXml;
148   }
149
150   /*
151    * Sets true for generated source
152    */

153   void setGeneratedSource(boolean isGeneratedSource)
154   {
155     _isGeneratedSource = isGeneratedSource;
156   }
157
158   /*
159    * Sets true for generated source
160    */

161   public boolean isGeneratedSource()
162   {
163     return _isGeneratedSource;
164   }
165
166   /**
167    * Sets the class name.
168    */

169   void setClassName(String JavaDoc className)
170   {
171     _className = className;
172   }
173
174   /**
175    * Adds a dependency.
176    */

177   public void addDepend(PersistentDependency depend)
178   {
179     _dependList.add(depend);
180   }
181
182   /**
183    * Adds a dependency.
184    */

185   public void addDependList(ArrayList JavaDoc<PersistentDependency> dependList)
186   {
187     if (dependList != null)
188       _dependList.addAll(dependList);
189   }
190
191   /**
192    * Returns the jsp configuration.
193    */

194   public JspPropertyGroup getJspPropertyGroup()
195   {
196     return _jspPropertyGroup;
197   }
198
199   /**
200    * Returns true for prototype compilation.
201    */

202   public boolean isPrototype()
203   {
204     return _isPrototype;
205   }
206
207   /**
208    * Set true for prototype compilation.
209    */

210   public void setPrototype(boolean prototype)
211   {
212     _isPrototype = prototype;
213   }
214
215   /**
216    * Initialize the instance.
217    */

218   void init()
219     throws Exception JavaDoc
220   {
221     _parseState = new ParseState();
222
223     String JavaDoc uriPwd;
224     if (_uri != null) {
225       int p = _uri.lastIndexOf('/');
226       uriPwd = p <= 0 ? "/" : _uri.substring(0, p + 1);
227     }
228     else {
229       uriPwd = "/";
230     }
231     
232     _parseState.setUriPwd(uriPwd);
233
234     if (_className == null)
235       _className = JavaCompiler.mangleName("jsp/" + _uri);
236
237     // default to true if ends with x
238
if (_uri.endsWith("x"))
239       _parseState.setXml(true);
240
241     WebApp app = _jspCompiler.getWebApp();
242     Path appDir = _jspCompiler.getAppDir();
243     if (appDir == null && app != null)
244       appDir = app.getAppDir();
245
246     if (app != null && app.has23Config())
247       _parseState.setELIgnoredDefault(true);
248
249     JspConfig jspConfig = null;
250
251     if (jspConfig == null && app != null)
252       jspConfig = (JspConfig) app.getExtension("jsp-config");
253
254     ArrayList JavaDoc<JspPropertyGroup> jspList = new ArrayList JavaDoc<JspPropertyGroup>();
255     _jspPropertyGroup = null;
256
257     if (_jspPropertyGroup == null) {
258       _jspPropertyGroup = _jspCompiler.getJspPropertyGroup();
259
260       if (_jspPropertyGroup != null) {
261     jspList.add(_jspPropertyGroup);
262       }
263     }
264
265     if (_jspPropertyGroup == null && app != null) {
266       _jspPropertyGroup = app.getJsp();
267       
268       if (_jspPropertyGroup != null)
269     jspList.add(_jspPropertyGroup);
270     }
271
272     if (_jspPropertyGroup == null) {
273       _jspPropertyGroup = _jspCompiler.getJspPropertyGroup();
274       
275       if (_jspPropertyGroup != null)
276     jspList.add(_jspPropertyGroup);
277     }
278
279     if (jspConfig != null) {
280       jspList.addAll(jspConfig.findJspPropertyGroupList(_uri));
281
282       _parseState.setELIgnoredDefault(false);
283     }
284
285     JspResourceManager resourceManager = _jspCompiler.getResourceManager();
286     if (resourceManager != null) {
287     }
288     else if (app != null)
289       resourceManager = new AppResourceManager(app);
290     else {
291       resourceManager = new AppDirResourceManager(appDir);
292     }
293
294     TagFileManager tagFileManager = _jspCompiler.getTagFileManager();
295
296     TaglibManager taglibManager = _jspCompiler.getTaglibManager();
297
298     JspPageConfig pageConfig = new JspPageConfig();
299
300     for (JspPropertyGroup jspPropertyGroup : jspList) {
301       ArrayList JavaDoc<String JavaDoc> preludeList = jspPropertyGroup.getIncludePreludeList();
302       for (int i = 0; preludeList != null && i < preludeList.size(); i++) {
303         String JavaDoc prelude = preludeList.get(i);
304         _preludeList.add(prelude);
305       }
306
307       ArrayList JavaDoc<String JavaDoc> codaList = jspPropertyGroup.getIncludeCodaList();
308       for (int i = 0; codaList != null && i < codaList.size(); i++) {
309         String JavaDoc coda = codaList.get(i);
310         _codaList.add(coda);
311       }
312
313       _parseState.setJspPropertyGroup(jspPropertyGroup);
314       _parseState.setSession(jspPropertyGroup.isSession());
315       _parseState.setScriptingInvalid(jspPropertyGroup.isScriptingInvalid());
316       
317       if (jspPropertyGroup.isELIgnored() != null)
318     _parseState.setELIgnored(Boolean.TRUE.equals(jspPropertyGroup.isELIgnored()))
319       ;
320       _parseState.setVelocityEnabled(jspPropertyGroup.isVelocityEnabled());
321       _parseState.setPageEncoding(jspPropertyGroup.getPageEncoding());
322       
323       if (Boolean.TRUE.equals(jspPropertyGroup.isXml()))
324     _parseState.setXml(true);
325       
326       if (Boolean.FALSE.equals(jspPropertyGroup.isXml()))
327     _parseState.setForbidXml(true);
328       
329       if (jspPropertyGroup.getPageEncoding() != null) {
330     try {
331       _parseState.setPageEncoding(jspPropertyGroup.getPageEncoding());
332     } catch (JspParseException e) {
333     }
334       }
335
336       pageConfig.setStaticEncoding(jspPropertyGroup.isStaticEncoding());
337
338       _parseState.setRecycleTags(jspPropertyGroup.isRecycleTags());
339       
340       _parseState.setTrimWhitespace(jspPropertyGroup.isTrimDirectiveWhitespaces());
341       _parseState.setDeferredSyntaxAllowedAsLiteral(jspPropertyGroup.isDeferredSyntaxAllowedAsLiteral());
342
343       if (jspPropertyGroup.getTldFileSet() != null)
344         taglibManager.setTldFileSet(jspPropertyGroup.getTldFileSet());
345     }
346     
347     _parseState.setResourceManager(resourceManager);
348     LineMap lineMap = null;
349
350     _tagManager = new ParseTagManager(resourceManager,
351                                       taglibManager,
352                                       tagFileManager);
353
354     _jspBuilder = new com.caucho.jsp.java.JavaJspBuilder();
355     _jspBuilder.setParseState(_parseState);
356     _jspBuilder.setJspCompiler(_jspCompiler);
357     _jspBuilder.setJspPropertyGroup(_jspPropertyGroup);
358     _jspBuilder.setTagManager(_tagManager);
359     _jspBuilder.setPageConfig(pageConfig);
360     _jspBuilder.setPrototype(_isPrototype);
361
362     _parser = new JspParser();
363     _parser.setJspBuilder(_jspBuilder);
364     _parser.setParseState(_parseState);
365     _parser.setTagManager(_tagManager);
366
367     _jspBuilder.setJspParser(_parser);
368
369     /*
370     for (int i = 0; i < _preludeList.size(); i++)
371       _parser.addPrelude(_preludeList.get(i));
372
373     for (int i = 0; i < _codaList.size(); i++)
374       _parser.addCoda(_codaList.get(i));
375     */

376   }
377
378   public Page compile()
379     throws Exception JavaDoc
380   {
381     LineMap lineMap = null;
382     if (_page != null)
383       throw new IllegalStateException JavaDoc("JspCompilerInstance cannot be reused");
384
385     try {
386       JspGenerator generator = generate();
387
388       lineMap = generator.getLineMap();
389
390       String JavaDoc encoding = _parseState.getCharEncoding();
391
392       _jspCompiler.compilePending();
393
394       boolean isAutoCompile = true;
395       if (_jspPropertyGroup != null)
396     isAutoCompile = _jspPropertyGroup.isAutoCompile();
397
398       Page page;
399       if (! generator.isStatic()) {
400         compileJava(_jspPath, _className, lineMap, encoding);
401
402         page = _jspCompiler.loadPage(_className, isAutoCompile);
403       }
404       else {
405         page = _jspCompiler.loadStatic(_className,
406                                        _parseState.isOptionalSession());
407         page._caucho_addDepend(generator.getDependList());
408         page._caucho_setContentType(_parseState.getContentType());
409       }
410
411       return page;
412     } catch (JspParseException e) {
413       e.setLineMap(lineMap);
414       e.setErrorPage(_parseState.getErrorPage());
415       throw e;
416     } catch (SAXException JavaDoc e) {
417       if (e.getCause() instanceof JspParseException) {
418     JspParseException subE = (JspParseException) e.getCause();
419
420     subE.setLineMap(lineMap);
421     subE.setErrorPage(_parseState.getErrorPage());
422     throw subE;
423       }
424       else {
425     JspParseException exn = new JspParseException(e);
426     exn.setErrorPage(_parseState.getErrorPage());
427     exn.setLineMap(lineMap);
428
429     throw exn;
430       }
431     } catch (FileNotFoundException JavaDoc e) {
432       throw e;
433     } catch (IOException JavaDoc e) {
434       JspParseException exn = new JspParseException(e);
435       exn.setLineMap(lineMap);
436       exn.setErrorPage(_parseState.getErrorPage());
437
438       throw exn;
439     } catch (Throwable JavaDoc e) {
440       JspParseException exn = new JspParseException(e);
441       exn.setLineMap(lineMap);
442       exn.setErrorPage(_parseState.getErrorPage());
443
444       throw exn;
445     }
446   }
447
448   public JspGenerator generate()
449     throws Exception JavaDoc
450   {
451     if (_page != null)
452       throw new IllegalStateException JavaDoc("JspCompilerInstance cannot be reused");
453
454     boolean isXml = _parseState.isXml();
455     boolean isForbidXml = _parseState.isForbidXml();
456
457     ParseState parseState = _parser.getParseState();
458     
459     try {
460       _parser.getParseState().setBuilder(_jspBuilder);
461
462       for (String JavaDoc prelude : _preludeList) {
463     parseState.setXml(false);
464     parseState.setForbidXml(false);
465     _parser.parse(parseState.getResourceManager().resolvePath(prelude),
466               prelude);
467       }
468       
469       _parser.getParseState().setXml(isXml);
470       _parser.getParseState().setForbidXml(isForbidXml);
471
472       if (isXml) {
473     _parseState.setELIgnoredDefault(false);
474     
475     Xml xml = new Xml();
476     xml.setContentHandler(new JspContentHandler(_jspBuilder));
477     _jspPath.setUserPath(_uri);
478     xml.setNamespaceAware(true);
479     xml.parse(_jspPath);
480       }
481       else {
482     WebApp app = _jspCompiler.getWebApp();
483
484     /*
485     if (_jspPropertyGroup == null && app != null && app.isJsp1())
486       _parseState.setELIgnored(true);
487     */

488     
489     _parser.parse(_jspPath, _uri);
490       }
491
492       for (String JavaDoc coda : _codaList) {
493     parseState.setXml(false);
494     parseState.setForbidXml(false);
495     _parser.parse(parseState.getResourceManager().resolvePath(coda),
496               coda);
497       }
498
499       JspGenerator generator = _jspBuilder.getGenerator();
500       generator.setJspCompilerInstance(this);
501
502       for (int i = 0; i < _dependList.size(); i++)
503     generator.addDepend(_dependList.get(i));
504
505       generator.validate();
506
507       generator.generate(_jspPath, _className);
508
509       return generator;
510     } catch (JspParseException e) {
511       e.setErrorPage(_parseState.getErrorPage());
512       throw e;
513     } catch (SAXException JavaDoc e) {
514       if (e.getCause() instanceof JspParseException) {
515     JspParseException subE = (JspParseException) e.getCause();
516
517     subE.setErrorPage(_parseState.getErrorPage());
518     throw subE;
519       }
520       else {
521     JspParseException exn = new JspParseException(e);
522     exn.setErrorPage(_parseState.getErrorPage());
523
524     throw exn;
525       }
526     } catch (FileNotFoundException JavaDoc e) {
527       throw e;
528     } catch (IOException JavaDoc e) {
529       JspParseException exn = new JspParseException(e);
530       exn.setErrorPage(_parseState.getErrorPage());
531
532       throw exn;
533     }
534   }
535
536   public TagInfo JavaDoc compileTag(TagLibraryInfo JavaDoc taglib)
537     throws Exception JavaDoc
538   {
539     TagInfo JavaDoc preloadTag = preloadTag(taglib);
540
541     if (preloadTag != null)
542       return preloadTag;
543
544     return generateTag(taglib );
545   }
546
547   private TagInfo JavaDoc preloadTag(TagLibraryInfo JavaDoc taglib)
548   {
549     try {
550       JspTagSupport tag = (JspTagSupport) _jspCompiler.loadClass(_className, true);
551
552       if (tag == null)
553     return null;
554
555       tag.init(_jspCompiler.getAppDir());
556
557       if (tag._caucho_isModified())
558     return null;
559
560       return tag._caucho_getTagInfo(taglib);
561     } catch (Throwable JavaDoc e) {
562       return null;
563     }
564   }
565
566   private TagInfo JavaDoc generateTag(TagLibraryInfo JavaDoc taglib)
567     throws Exception JavaDoc
568   {
569     LineMap lineMap = null;
570     if (_page != null)
571       throw new IllegalStateException JavaDoc("JspCompilerInstance cannot be reused");
572
573     try {
574       boolean isXml = _isXml;
575       
576       if (_jspPropertyGroup != null && ! isXml
577       && _jspPropertyGroup.isXml() != null)
578     isXml = Boolean.TRUE.equals(_jspPropertyGroup.isXml());
579
580       if (_jspPropertyGroup != null
581       && Boolean.FALSE.equals(_jspPropertyGroup.isXml()))
582     _parseState.setForbidXml(true);
583
584       _parseState.setXml(isXml);
585
586       if (_jspCompiler.addTag(_className)) {
587     _isPrototype = true;
588     _jspBuilder.setPrototype(true);
589       }
590
591       _parseState.setTag(true);
592       _isXml = isXml;
593       
594       if (isXml) {
595     _parseState.setELIgnoredDefault(false);
596     
597     Xml xml = new Xml();
598     xml.setContentHandler(new JspContentHandler(_jspBuilder));
599     _jspPath.setUserPath(_uri);
600     xml.setNamespaceAware(true);
601     xml.parse(_jspPath);
602       }
603       else
604     _parser.parseTag(_jspPath, _uri);
605
606       _generator = _jspBuilder.getGenerator();
607
608       if (_isPrototype) {
609     return _generator.generateTagInfo(_className, taglib);
610       }
611
612       _generator.validate();
613       
614       _generator.generate(_jspPath, _className);
615
616       if (_jspCompiler.hasRecursiveCompile()) {
617     _jspCompiler.addPending(this);
618
619     return _generator.generateTagInfo(_className, taglib);
620       }
621
622       return completeTag(taglib);
623     } catch (JspParseException e) {
624       e.setLineMap(lineMap);
625       e.setErrorPage(_parseState.getErrorPage());
626       throw e;
627     } catch (FileNotFoundException JavaDoc e) {
628       throw e;
629     } catch (IOException JavaDoc e) {
630       JspParseException exn = new JspParseException(e);
631       exn.setErrorPage(_parseState.getErrorPage());
632       exn.setLineMap(lineMap);
633       throw exn;
634     }
635   }
636
637   TagInfo JavaDoc completeTag()
638     throws Exception JavaDoc
639   {
640     return completeTag(new TagTaglib("x", "uri"));
641   }
642
643   TagInfo JavaDoc completeTag(TagLibraryInfo JavaDoc taglib)
644     throws Exception JavaDoc
645   {
646     LineMap lineMap = null;
647
648     try {
649       lineMap = _generator.getLineMap();
650
651       String JavaDoc encoding = _parseState.getCharEncoding();
652
653       compileJava(_jspPath, _className, lineMap, encoding);
654
655       JspTagSupport tag = (JspTagSupport) _jspCompiler.loadClass(_className, true);
656
657       tag.init(_jspCompiler.getAppDir());
658
659       return tag._caucho_getTagInfo(taglib);
660       // Page page = _jspCompiler.loadClass(_className);
661
} catch (JspParseException e) {
662       e.setLineMap(lineMap);
663       e.setErrorPage(_parseState.getErrorPage());
664       throw e;
665     } catch (FileNotFoundException JavaDoc e) {
666       throw e;
667     } catch (IOException JavaDoc e) {
668       JspParseException exn = new JspParseException(e);
669       exn.setErrorPage(_parseState.getErrorPage());
670       exn.setLineMap(lineMap);
671       throw exn;
672     } catch (Throwable JavaDoc e) {
673       JspParseException exn = new JspParseException(e);
674       exn.setErrorPage(_parseState.getErrorPage());
675       exn.setLineMap(lineMap);
676       throw exn;
677     }
678   }
679
680   private void compileJava(Path path, String JavaDoc className,
681                            LineMap lineMap, String JavaDoc charEncoding)
682     throws Exception JavaDoc
683   {
684     JavaCompiler compiler = JavaCompiler.create(null);
685     compiler.setClassDir(_jspCompiler.getClassDir());
686     // compiler.setEncoding(charEncoding);
687
String JavaDoc fileName = className.replace('.', '/') + ".java";
688
689     compiler.compile(fileName, lineMap);
690
691     /*
692     boolean remove = true;
693     try {
694       compiler.compile(fileName, lineMap);
695       remove = false;
696     } finally {
697       if (remove)
698         Vfs.lookup(fileName).remove();
699     }
700     */

701
702     Path classDir = _jspCompiler.getClassDir();
703     Path classPath = classDir.lookup(className.replace('.', '/') + ".class");
704     Path smapPath = classDir.lookup(fileName + ".smap");
705
706     // jsp/18p1
707
// compiler.mergeSmap(classPath, smapPath);
708
}
709
710   private void readSmap(ClassLoader JavaDoc loader, String JavaDoc className)
711   {
712     if (loader == null)
713       return;
714
715     String JavaDoc smapName = className.replace('.', '/') + ".java.smap";
716
717     InputStream JavaDoc is = null;
718     try {
719       is = loader.getResourceAsStream(smapName);
720     } catch (Exception JavaDoc e) {
721       log.log(Level.FINE, e.toString(), e);
722     } finally {
723       if (is != null) {
724         try {
725           is.close();
726         } catch (IOException JavaDoc e) {
727         }
728       }
729     }
730   }
731 }
732
Popular Tags