Servlet学习之JSP
文章目录
- 1.概述
- 2.本质
- 3.JSP与Servlet的区别
- 4.JSP的常用基础语法
- 5.JSP指令
- 6.JSP的九大内置对象
1.概述
首先我们说一下JSP的概念(以下内容来自百度百科):
JSP(全称JavaServer Pages)是由[Sun Microsystems](https://baike.baidu.com/item/Sun Microsystems)公司主导创建的一种动态网页技术标准。JSP部署于网络服务器上,可以响应客户端发送的请求,并根据请求内容动态地生成HTML、XML或其他格式文档的Web网页,然后返回给请求者。JSP技术以Java语言作为脚本语言,为用户的HTTP请求提供服务,并能与服务器上的其它Java程序共同处理复杂的业务需求。
由上我们可以知道:
- JSP是java程序。(JSP本质还是一个Servlet)
- JSP是:JavaServer Pages的缩写。(基于Java语言实现的服务器端的页面。)
- Servlet是JavaEE的13个子规范之一,那么JSP也是JavaEE的13个子规范之一。
- JSP是一套规范。所有的web容器/web服务器都是遵循这套规范的,都是按照这套规范进行的“翻译”
- 每一个web容器/web服务器都会内置一个JSP翻译引擎。
2.本质
为了更好的了解JSP,我们可以在idea部署tomcat的项目中中手写一个jsp文件名为index.jsp,如下:
这是由JSP翻译器翻译过来的Servlet
启动服务器,再通过URL访问我们的服务器上的index.jsp,这个时候我们的jsp文件就已经被我们的JSP翻译器翻译为Servlet了。我们可以通过下面的路径找到翻译完成的Servlet。(下面关于翻译完成的Servlet的路径不是重点,看不懂可以略过)
C:\Users\?1\?2\system\tomcat\?3\Catalina\localhost\?4\org\[apache](https://so.csdn.net/so/search?q=apache&spm=1001.2101.3001.7020)\jsp?1:在计算机上使用IDEA的用户的用户名 ;?2:.IntelliJIdea2018.2 + IDEA的版本日期(下载使用的IDEA的版本不一样日期也不一样);?3:此web应用在IDEA上使用的tomcat的名字(自己取的) + 项目名;?4:项目名;比如我自己的路径就是C:\Users\少不入川。\AppData\Local\JetBrains\IntelliJIdea2021.3\tomcat\82919bbd-7058-4746-851f-6389e107e42a\work\Catalina\localhost\xmm\org\apache\jsp
在这个文件目录下我们可以发现名为index_jsp.java、index_jsp.class文件。这个就是由我们JSP文件翻译过来的Servlet以及编译过后生成的字节码文件。index_jsp.java的内容如下:
package org.apache.jsp;import jakarta.servlet.*;import jakarta.servlet.http.*;import jakarta.servlet.jsp.*;public final class index_jsp extends org.apache.jasper.runtime.HttpJspBase implements org.apache.jasper.runtime.JspSourceDependent, org.apache.jasper.runtime.JspSourceImports { private static final jakarta.servlet.jsp.JspFactory _jspxFactory = jakarta.servlet.jsp.JspFactory.getDefaultFactory(); private static java.util.Map<java.lang.String,java.lang.Long> _jspx_dependants; private static final java.util.Set<java.lang.String> _jspx_imports_packages; private static final java.util.Set<java.lang.String> _jspx_imports_classes; static { _jspx_imports_packages = new java.util.HashSet<>(); _jspx_imports_packages.add("jakarta.servlet"); _jspx_imports_packages.add("jakarta.servlet.http"); _jspx_imports_packages.add("jakarta.servlet.jsp"); _jspx_imports_classes = null; } private volatile jakarta.el.ExpressionFactory _el_expressionfactory; private volatile org.apache.tomcat.InstanceManager _jsp_instancemanager; public java.util.Map<java.lang.String,java.lang.Long> getDependants() { return _jspx_dependants; } public java.util.Set<java.lang.String> getPackageImports() { return _jspx_imports_packages; } public java.util.Set<java.lang.String> getClassImports() { return _jspx_imports_classes; } public jakarta.el.ExpressionFactory _jsp_getExpressionFactory() { if (_el_expressionfactory == null) { synchronized (this) { if (_el_expressionfactory == null) { _el_expressionfactory = _jspxFactory.getJspApplicationContext(getServletConfig().getServletContext()).getExpressionFactory(); } } } return _el_expressionfactory; } public org.apache.tomcat.InstanceManager _jsp_getInstanceManager() { if (_jsp_instancemanager == null) { synchronized (this) { if (_jsp_instancemanager == null) { _jsp_instancemanager = org.apache.jasper.runtime.InstanceManagerFactory.getInstanceManager(getServletConfig()); } } } return _jsp_instancemanager; } public void _jspInit() { } public void _jspDestroy() { } public void _jspService(final jakarta.servlet.http.HttpServletRequest request, final jakarta.servlet.http.HttpServletResponse response) throws java.io.IOException, jakarta.servlet.ServletException { if (!jakarta.servlet.DispatcherType.ERROR.equals(request.getDispatcherType())) { final java.lang.String _jspx_method = request.getMethod(); if ("OPTIONS".equals(_jspx_method)) { response.setHeader("Allow","GET, HEAD, POST, OPTIONS"); return; } if (!"GET".equals(_jspx_method) && !"POST".equals(_jspx_method) && !"HEAD".equals(_jspx_method)) { response.setHeader("Allow","GET, HEAD, POST, OPTIONS"); response.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, "JSP 只允许 GET、POST 或 HEAD。Jasper 还允许 OPTIONS"); return; } } final jakarta.servlet.jsp.PageContext pageContext; jakarta.servlet.http.HttpSession session = null; final jakarta.servlet.ServletContext application; final jakarta.servlet.ServletConfig config; jakarta.servlet.jsp.JspWriter out = null; final java.lang.Object page = this; jakarta.servlet.jsp.JspWriter _jspx_out = null; jakarta.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("\r\n"); out.write("\r\n"); out.write("\r\n"); out.write("\r\n"); out.write(" 这是由JSP翻译器翻译过来的Servlet \r\n"); out.write("\r\n"); out.write("\r\n"); out.write(" "); out.print("什么也不做"); out.write("\r\n"); out.write("\r\n"); out.write("\r\n"); } catch (java.lang.Throwable t) { if (!(t instanceof jakarta.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文件中手动编写的两行内容被翻译到由jsp文件生成的Servlet文件中了,所以我们可以知道jsp的本质也是就是Servlet。
3.JSP与Servlet的区别
从架构上说,JSP可以被看作是从Servlets高级提炼而作为JAVA Servlet2.1 API的扩展而应用。Servlets和JSP最早都是由Sun Microsystems(升阳公司)开发的。从JSP1.2版本以来,JSP处于Java Community Process(有人译为:JAVA社区组织)开发模式下。JSR-53规定了JSP 1.2和Servlet 2.4的规范,JSR-152规定了JSP 2.0的规范。2006年5月,JSP 2.1的规范作为Java EE5的一部份,在JSR-245中发布。
更加直观的说,JSP和Servlet的职责不同:
- Servlet的职责是什么:收集数据。(Servlet的强项是逻辑处理,业务处理,然后链接数据库,获取/收集数据。)
- JSP的职责是什么:展示数据。(JSP的强项是做数据的展示)
这样的目的也是为了让我们的代码更加的清晰。
4.JSP的常用基础语法
- JSP中直接编写普通字符串
- 会被翻译到由jsp文件生成的Servlet类的service方法的中的out.write(“这里”)语句当中。
-
- 会被翻译到由jsp文件生成的Servlet类的service方法体内部,里面是一条一条的java语句。
-
- 会被翻译到由jsp文件生成的Servlet类的service方法之外。
-
- 会被翻译到由jsp文件生成的Servlet类的service方法体内部,翻译为:out.print();
- 主要是用来输出Java变量与字符串的组合
-
- page指令,通过contentType属性用来设置响应的内容类型。
- jsp中的指令还有很多,我也不了解,我也就不细说了
5.JSP指令
-
指令的作用:指导JSP的翻译引擎如何工作(指导当前的JSP翻译引擎如何翻译JSP文件。)
-
指令包括哪些呢?
- include指令:包含指令,在JSP中完成静态包含,很少用了。(这里不讲)
- taglib指令:引入标签库的指令。这个到JJSTL标签库的时候再学习。现在先不管。
- page指令:目前重点学习一个page指令。
-
指令的使用语法是什么?
-
关于page指令当中都有哪些常用的属性呢?
-
true表示启用JSP的内置对象session,表示一定启动session对象。没有session对象会创建。如果没有设置,默认值就是session="true"session="false" 表示不启动内置对象session。当前JSP页面中无法使用内置对象session。
-
contentType属性用来设置响应的内容类型但同时也可以设置字符集。
-
pageEncoding="UTF-8" 表示设置响应时采用的字符集。
-
import语句,导包。
-
当前页面出现异常之后,跳转到error.jsp页面。errorPage属性用来指定出错之后的跳转位置。
-
表示启用JSP九大内置对象之一:exception默认值是false。
-
6.JSP的九大内置对象
-
jakarta.servlet.jsp.PageContext pageContext 页面作用域
-
jakarta.servlet.http.HttpServletRequest request 请求作用域
-
jakarta.servlet.http.HttpSession session 会话作用域
-
jakarta.servlet.ServletContext application 应用作用域
- pageContext < request < session < application
- 以上四个作用域都有:setAttribute、getAttribute、removeAttribute方法。
- 以上作用域的使用原则:尽可能使用小的域。
-
java.lang.Throwable exception
-
jakarta.servlet.ServletConfig config
-
java.lang.Object page (其实是this,当前的servlet对象)
-
jakarta.servlet.jsp.JspWriter out (负责输出)
-
jakarta.servlet.http.HttpServletResponse response (负责响应)