⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 jspcompiler.java

📁 用java开发的
💻 JAVA
📖 第 1 页 / 共 3 页
字号:
/*	GNUJSP - a free JSP implementation	Copyright (C) 1998-1999, Vincent Partington <vinny@klomp.org>	This program is free software; you can redistribute it and/or	modify it under the terms of the GNU General Public License	as published by the Free Software Foundation; either version 2	of the License, or (at your option) any later version.	This program is distributed in the hope that it will be useful,	but WITHOUT ANY WARRANTY; without even the implied warranty of	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the	GNU General Public License for more details.	You should have received a copy of the GNU General Public License	along with this program; if not, write to the Free Software	Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.*/package	org.gjt.jsp;import	java.io.BufferedReader;import	java.io.ByteArrayOutputStream;import	java.io.File;import	java.io.FileNotFoundException;import	java.io.FileReader;import	java.io.FileWriter;import	java.io.InputStreamReader;import	java.io.IOException;import	java.io.LineNumberReader;import	java.io.PrintStream;import	java.io.PrintWriter;import	java.io.StringReader;import	java.io.OutputStream;import	java.util.Enumeration;import	java.util.Hashtable;import	java.util.Properties;import	java.util.StringTokenizer;import	java.util.Vector;import  java.net.URLClassLoader;import  java.net.URL;import  java.net.URLDecoder;import	javax.servlet.http.HttpServletRequest;import	javax.servlet.http.HttpServletResponse;import Acme.Utils;/** * This JSP compiler class takes the quick&dirty approach to JSP parsing. * The whole JSP file is read into memory and an index is run through it * until a StringIndexOutOfBoundsException occurs. I was happily hacking * away at this until I discovered it had gotten more than 30K long. It * seems to work, but someday it might be a good idea to break this * all up into separate classes, like a JSPParser, JavaGenerator en * JavaCompiler class. * * A new JSPCompiler should be created every time a file is compiled. * The classfiles directory, the file and the classname are parameters * to the constructor. Call compile() to do the actual compiling. */public class JSPCompiler {	public static final int	COMPILER_VERSION_NR = 4;	private static final int	PARSE_NONE = 0,								PARSE_HTML = 1,								PARSE_DECLARATION = 2,								PARSE_SCRIPTLET = 3,								PARSE_EXPRESSION = 4;	private static final String	lineSeparator = System.getProperty("line.separator"),								encodedLineSeparator = javaStringEncode(System.getProperty("line.separator"));	private JSPServlet			jspServlet;	private File				jspFile, javaFile, classFile;	private String				className;	private HttpServletRequest	servletRequest;	private String				src;	private int					srcPos, lineNr;	private int					parseState = PARSE_NONE;	private boolean				justWroteNewline = false;	private Vector				dependencies = new Vector();	private boolean				createSession = false;	private String				content_typeDirective = null;	private StringBuffer		extendsDirective = new StringBuffer(),								implementsDirective = new StringBuffer(),								importDirective = new StringBuffer(),								methodDirective = new StringBuffer(),								declarationsCode = new StringBuffer(),								beanCode = new StringBuffer(),								scriptletsCode = new StringBuffer();	/**	 * Create a JSPCompiler object.	 */	public JSPCompiler(JSPServlet jspServlet, File jspFile, String className, HttpServletRequest servletRequest) {		this.jspServlet = jspServlet;		this.jspFile = jspFile;		this.javaFile = getFileForClass(jspServlet.repository, className, ".java");		this.classFile = getFileForClass(jspServlet.repository, className, ".class");		this.className = className;		this.servletRequest = servletRequest;	}	/**	 * Do the actual compilation. This is done in three phases:	 * <OL>	 * <LI>parse the JSP file	 * <LI>generate a <CODE>.java</CODE> file	 * <LI>compile the <CODE>.java</CODE> file into a <CODE>.class</CODE> file	 * </OL>	 *	 * @exception JSPException is thrown when a compilation error occurs	 */	public void compile() throws JSPException {		parseJspFile();		generateJavaFile();		compileJavaFile();	}	private void parseJspFile() throws JSPException {		parseOneJspFile();		changeParseState(PARSE_NONE);		if(content_typeDirective == null) {			content_typeDirective = jspServlet.defaultContentType;		}		if(extendsDirective.length() == 0) {			extendsDirective.append("javax.servlet.http.HttpServlet");		}		if(methodDirective.length() == 0) {			methodDirective.append("service");		}	}	private void parseOneJspFile() throws JSPException {		BufferedReader	in;		StringBuffer	srcBuf;		String			s;		int				i;		char			c, d;		// read jsp source		dependencies.addElement(jspFile);		dependencies.addElement(new Long(jspFile.lastModified()));		try {			in = new BufferedReader(new FileReader(jspFile));			try {				srcBuf = new StringBuffer((int) jspFile.length());				while((s = in.readLine()) != null) {					srcBuf.append(s).append((char) '\n');				}				src = srcBuf.toString();				srcBuf = null;			} finally {				in.close();			}		} catch(FileNotFoundException fnfexc) {			throw new JSPException(HttpServletResponse.SC_NOT_FOUND, "File " + jspFile + " could not be found");		} catch(IOException ioexc) {			throw new JSPException(ioexc.toString());		}		// parse jsp source		lineNr = 1;		srcPos = 0;		try {			PARSING: for(;;) {				c = src.charAt(srcPos);				// check for possible state change				if(c == '<') {					if(parseState == PARSE_NONE || parseState == PARSE_HTML) {						if(parseInNoneOrHtmlState()) {							continue PARSING;						}					} else if(parseState == PARSE_DECLARATION) {						if(parseInDeclarationState()) {							continue PARSING;						}					}				} else if(c == '%' &&					(parseState == PARSE_EXPRESSION || parseState == PARSE_SCRIPTLET) &&					(srcPos < src.length()-1 && src.charAt(srcPos+1) == '>'))				{					// end of expression or scriptlet					changeParseState(PARSE_NONE);					srcPos += 2;					continue PARSING;				}				// output character				switch(parseState) {				case PARSE_NONE:					changeParseState(PARSE_HTML);				case PARSE_HTML:					if(justWroteNewline && c != '\n') {						justWroteNewline = false;						scriptletsCode.append("\" +").append(lineSeparator).append("\t\t\t\"");					}					switch(c) {					case '\b':						scriptletsCode.append("\\b");						break;					case '\t':						scriptletsCode.append("\\t");						break;					case '\n':						scriptletsCode.append(encodedLineSeparator);						justWroteNewline = true;						lineNr++;						break;					case '\f':						scriptletsCode.append("\\f");						break;					case '\'':						scriptletsCode.append("\\\'");						break;					case '\"':						scriptletsCode.append("\\\"");						break;					case '\\':						scriptletsCode.append("\\\\");						break;					default:						if(c > 0xFF) {							s = "00" + Integer.toHexString(c);							scriptletsCode.append("\\u").append(s.substring(s.length() - 4));						} else if(c < ' ' || c >= 0x7F) {							s = "00" + Integer.toOctalString(c);							scriptletsCode.append((char) '\\').append(s.substring(s.length() - 3));						} else {							scriptletsCode.append((char) c);						}						break;					}					break;				case PARSE_DECLARATION:					if(c == '\n') {						declarationsCode.append(lineSeparator);						lineNr++;					} else {						declarationsCode.append((char) c);					}					break;				default:					if(c == '\n') {						scriptletsCode.append(lineSeparator);						lineNr++;					} else {						scriptletsCode.append((char) c);					}					break;				}				srcPos++;			}		} catch(StringIndexOutOfBoundsException sioobexc) {			// instead of checking for the end of the string ourselves			// we let java.lang.String find it. This makes the code			// simpeler and more efficient.		}	}	private boolean parseInNoneOrHtmlState() throws StringIndexOutOfBoundsException, JSPException {		String[]	keyAndValue;		char		d;		if(srcPos < src.length()-3 && src.charAt(srcPos+1) == '%') {			// directive or start of expression or scriptlet			d = src.charAt(srcPos+2);			if(d == '=') {				// start of expression				changeParseState(PARSE_EXPRESSION);				setSrcPos(srcPos+3);				return true;			} else if(d == '@') {				// directive				parseDirective();				return true;			} else {				// start of scriplet				changeParseState(PARSE_SCRIPTLET);				setSrcPos(srcPos+2);				return true;			}		} else if(srcPos < src.length()-20 &&					src.substring(srcPos+1, srcPos+12).equalsIgnoreCase("!--#INCLUDE") &&					Character.isWhitespace(src.charAt(srcPos+12)))		{			parseSSI();			return true;		} else if(srcPos < src.length()-20 &&					src.substring(srcPos+1, srcPos+7).equalsIgnoreCase("SCRIPT") &&					Character.isWhitespace(src.charAt(srcPos+7)))		{			// possible start of declaration			boolean	runatServer = false;			int		prevSrcPos = srcPos,					prevLineNr = lineNr;			srcPos += 7;			skipWhitespace();			for(;;) {				// check for end of tag				if(src.charAt(srcPos) == '>') {					if(runatServer) {						// start of declaration						changeParseState(PARSE_DECLARATION);						srcPos++;						return true;					} else {						srcPos = prevSrcPos;						lineNr = prevLineNr;						return false;					}				}				keyAndValue = parseKeyAndValue();				if(keyAndValue[0].equalsIgnoreCase("RUNAT") && keyAndValue[1].equalsIgnoreCase("SERVER")) {					runatServer = true;				}			}		} else if(srcPos < src.length()-10 &&					src.substring(srcPos+1, srcPos+5).equalsIgnoreCase("BEAN") &&					Character.isWhitespace(src.charAt(srcPos+5)))		{			// bean			parseBean();			return true;		}		return false;	}	private boolean parseInDeclarationState() throws StringIndexOutOfBoundsException, JSPException {		if(srcPos < src.length()-8 &&				src.substring(srcPos+1, srcPos+8).equalsIgnoreCase("/SCRIPT") &&				(Character.isWhitespace(src.charAt(srcPos+8)) || src.charAt(srcPos+8) == '>'))		{			// end of declaration			changeParseState(PARSE_NONE);			setSrcPos(src.indexOf('>', srcPos));			srcPos++;			return true;		}		return false;	}	private void parseDirective() throws StringIndexOutOfBoundsException, JSPException {		String[]		keyAndValue;		StringTokenizer	toker;		int				i;		char			c;		srcPos += 3;		skipWhitespace();		for(;;) {			// check for end of directive			c = src.charAt(srcPos);			if(c == '%') {				if(src.charAt(srcPos+1) == '>') {					srcPos += 2;				} else {					srcPos++;				}				return;			} else if(c == '>') {				srcPos++;				return;			}			keyAndValue = parseKeyAndValue();			if(keyAndValue[0].equalsIgnoreCase("content_type")) {				// content_type				if(content_typeDirective == null) {					content_typeDirective = keyAndValue[1];				}			} else if(keyAndValue[0].equalsIgnoreCase("extends")) {				// extends				if(extendsDirective.length() == 0) {					extendsDirective.append(lineSeparator);					recordFileAndLineNr(extendsDirective);					extendsDirective.append(keyAndValue[1]);				}			} else if(keyAndValue[0].equalsIgnoreCase("implements")) {				// implements				toker = new StringTokenizer(keyAndValue[1], " ,");				while(toker.hasMoreTokens()) {					if(implementsDirective.length() == 0) {						implementsDirective.append(" implements").append(lineSeparator);					} else {						implementsDirective.append(",").append(lineSeparator);					}					recordFileAndLineNr(implementsDirective);					implementsDirective.append(toker.nextToken());				}			} else if(keyAndValue[0].equalsIgnoreCase("import")) {				// import				toker = new StringTokenizer(keyAndValue[1], " ,");				while(toker.hasMoreTokens()) {					recordFileAndLineNr(importDirective);					importDirective.append("import ").append(toker.nextToken()).append((char) ';').append(lineSeparator);				}			} else if(keyAndValue[0].equalsIgnoreCase("include")) {				// include				parseInclude(keyAndValue[1], false);			} else if(keyAndValue[0].equalsIgnoreCase("language")) {				// language				if(!keyAndValue[1].equalsIgnoreCase("java")) {					throw new JSPException("<B>" + jspFile.getPath() + ":" + lineNr + "</B>: Unknown jsp language " + keyAndValue[1]);				}			} else if(keyAndValue[0].equalsIgnoreCase("method")) {				// method				if(methodDirective.length() == 0) {					methodDirective.append(lineSeparator);					recordFileAndLineNr(methodDirective);					methodDirective.append(keyAndValue[1]);				}			} else if(keyAndValue[0].equalsIgnoreCase("vinclude")) {				// vinclude				parseInclude(keyAndValue[1], true);			} else {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -