版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/cjmust/article/details/83186163
JSP的实质
JSP实际上是一个精心设计的Servlet
在运行时,JSP代码将有JSP编译器进行转换,它将解析出JSP代码的所有特性,并将其转换为Java代码。
由JSP创建得到的Java类都会实现Servlet
tomcat中,JSP默认是不会在Tomcat启动时进行加载编译的,当我们访问时,则会在tomcat根目录\work\Catalina\localhost
中的文件夹中出现刚刚编译好的JSP文件的class文件和Java文件
public final class index_jsp extends org.apache.jasper.runtime.HttpJspBase
implements org.apache.jasper.runtime.JspSourceDependent,
org.apache.jasper.runtime.JspSourceImports {
..............................
}
可以看到由JSP生成的类继承了org.apache.jasper.runtime.HttpJspBase
,而该类又继承了HttpServlet
;
HttpJspBase
提供了一些可用Tomcat编译过的JSP所使用的功能,在执行JSP时,最后将执行Servlet的service方法,而service方法又会执行方法_jspService
。
查看由JSP生成的Java文件中的_jspService方法:
public void _jspService(final javax.servlet.http.HttpServletRequest request, final javax.servlet.http.HttpServletResponse response)
throws java.io.IOException, javax.servlet.ServletException {
final java.lang.String _jspx_method = request.getMethod();
if (!"GET".equals(_jspx_method) && !"POST".equals(_jspx_method) && !"HEAD".equals(_jspx_method) && !javax.servlet.DispatcherType.ERROR.equals(request.getDispatcherType())) {
response.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, "JSPs only permit GET POST or HEAD");
return;
}
final javax.servlet.jsp.PageContext pageContext;
javax.servlet.http.HttpSession session = null;
final javax.servlet.ServletContext application;
final javax.servlet.ServletConfig config;
javax.servlet.jsp.JspWriter out = null;
final java.lang.Object page = this;
javax.servlet.jsp.JspWriter _jspx_out = null;
javax.servlet.jsp.PageContext _jspx_page_context = null;
try {
response.setContentType("text/html;charset=UTF-8");
pageContext = _jspxFactory.getPageContext(this, request, response,
null, true, 8192, true);
_jspx_page_context = pageContext;
application = pageContext.getServletContext();
config = pageContext.getServletConfig();
session = pageContext.getSession();
out = pageContext.getOut();
_jspx_out = out;
out.write("\n");
out.write("<!DOCTYPE html>\n");
out.write("<html>\n");
out.write(" <head>\n");
out.write(" <title>Hello World Application</title>\n");
out.write(" </head>\n");
out.write(" <body>\n");
out.write(" Hello, World!\n");
out.write(" </body>\n");
out.write("</html>\n");
} catch (java.lang.Throwable t) {
if (!(t instanceof javax.servlet.jsp.SkipPageException)){
out = _jspx_out;
if (out != null && out.getBufferSize() != 0)
try {
if (response.isCommitted()) {
out.flush();
} else {
out.clearBuffer();
}
} catch (java.io.IOException e) {}
if (_jspx_page_context != null) _jspx_page_context.handlePageException(t);
else throw new ServletException(t);
}
} finally {
_jspxFactory.releasePageContext(_jspx_page_context);
}
}
在入口处可以看到JSP只支持GET方法和POST方法
接下来将HTML写入输出流中。
不同的容器中创建出的Java类也是不同的
JSP的生命周期
JSP作为Servlet,也有自己的生命周期,在某些容器中(Tomcat),JSP会在第一次请求到达时被即时转换并编译。
当然,很多web容器提供了在部署项目时预编译所有JSP的功能,不过会降低部署速度。
空白的JSP文件
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
没有包含该头部的JSP页面,依旧正常编译
因为JSP默认的内容类型(contentType)为text/html,默认的字符编码(charset)为ISO-8859-1.