【Head First Servlets and JSP】笔记21:从有脚本到无脚本
从有脚本到无脚本
1、快速搭建一个测试环境:输入用户名,返回“Hello, 用户名”
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
body {
font-family:'comic sans ms',sans-serif;
}
</style>
</head> <body>
<form action="checking" method="post">
<p>Name:</p>
<p><input type="text" name="name" value="admin"></p>
<p>Comments: </p>
<p><textarea name="comments" rows="7" cols="30">Your comments</textarea></p>
<p><input type="submit"></p>
</form>
</body> </html>
web.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
version="3.1"> <servlet>
<servlet-name>checking</servlet-name>
<servlet-class>com.demo.checking</servlet-class>
</servlet> <servlet-mapping>
<servlet-name>checking</servlet-name>
<url-pattern>/checking</url-pattern>
</servlet-mapping> </web-app>
com.demo.checking
package com.demo; import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException; public class checking extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doPost(req, resp);
} @Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String name = req.getParameter("name");
req.setAttribute("name", name); RequestDispatcher view = req.getRequestDispatcher("/index.jsp");
view.forward(req, resp);
}
}
index.jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>$Title$</title>
<style>
body {
font-family:'comic sans ms',sans-serif;
}
</style>
</head>
<body>
<p>Hello, <%=request.getAttribute("name")%></p>
<%--<p>Hello, <%=request.getParameter("name")%></p>--%>
</body>
</html>
2、把传递“值”改为传递“对象”
com.demo.Person
package com.demo; public class Person implements java.io.Serializable {
private String name; public Person() { } public String getName() {
return name;
} public void setName(String name) {
this.name = name;
}
}
com.demo.checking
package com.demo; import javax.servlet.*;
import javax.servlet.http.*;
import java.io.IOException; public class checking extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doPost(req, resp);
} @Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
Person person = new Person();
person.setName(req.getParameter("name"));
req.setAttribute("person", person); RequestDispatcher view = req.getRequestDispatcher("/index.jsp");
view.forward(req, resp);
}
}
index.jsp
<%@ page import="com.demo.Person" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>$Title$</title>
<style>
body {
font-family:'comic sans ms',sans-serif;
}
</style>
</head>
<body>
<p>Hello, <%=((Person)request.getAttribute("person")).getName()%></p>
</body>
</html>
3、不过,还记得那个备忘录吗?可以用一句话来总结:“使用脚本则死”。所以我们需要另一种方法。
Person是一个JavaBean,所以我们使用与bean相关的标准动作
<%@ page import="com.demo.Person" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>$Title$</title>
<style>
body {
font-family:'comic sans ms',sans-serif;
}
</style>
</head>
<body>
<jsp:useBean id="person" class="com.demo.Person" scope="request" />
<p>Person created by servlet: <jsp:getProperty name="person" property="name" /></p>
</body>
</html>
<jsp:useBean>与<jsp:getProperty>的关系
<jsp:useBean>可以用来声明和初始化你在<jsp:getProperty>中使用的具体bean对象。
<jsp:getProperty>中的“name”值与<jsp:useBean>中的“id”值相对应;<jsp:useBean>中的“id”值与requst中的person属性对应。// req.setAttribute("person", person);
事实上,上述代码在_jspService()中将会变成这样
com.demo.Person person = null;
person = (com.demo.Person) _jspx_page_context.getAttribute("person", javax.servlet.jsp.PageContext.REQUEST_SCOPE);
if (person == null){
person = new com.demo.Person();
_jspx_page_context.setAttribute("person", person, javax.servlet.jsp.PageContext.REQUEST_SCOPE);
}
关于PageContext可以参考这里。
4、使用JavaBean标准动作设置对象的成员值。
<%@ page import="com.demo.Person" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>$Title$</title>
<style>
body { font-family:'comic sans ms',sans-serif;
}
</style>
</head>
<body>
<%-- id值对应request的实例域中的person --%>
<jsp:useBean id="person" class="com.demo.Person" scope="request" />
<jsp:setProperty name="person" property="name" value="fuck_admin" />
<p>Person created by servlet: <jsp:getProperty name="person" property="name" /></p>
</body>
</html>
5、但是,上述代码有一个问题:覆盖了用户输入的name。而我们只想在查找不到用户输入的时候,自行创建bean并设置实例域的值。
也就是说,我们希望_jspService()中是这样的:
对应的JavaBean标准动作就是:
<body>
<%-- id值对应request的实例域中的person成员 --%>
<jsp:useBean id="person" class="com.demo.Person" scope="request">
<jsp:setProperty name="person" property="name" value="fuck_admin" />
</jsp:useBean>
<p>Person created by servlet: <jsp:getProperty name="person" property="name" /></p>
</body>
可以建立多态的bean引用吗?——为<jsp:useBean>增加一个type属性
也就是说,我们希望用一个父类引用持有子类对象。类似于:
Person p = new Employee();
首先,我们把Person改为抽象类(这样就无法创建Person类对象了),然后实现一个Employee类:
package com.demo; public class Employee extends Person {
private int empID; public int getEmpID() {
return empID;
} public void setEmpID(int empID) {
this.empID = empID;
}
}
接着修改servlet和JSP,如下所示:
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
Person person = new Employee();
person.setName(req.getParameter("name"));
req.setAttribute("person", person); RequestDispatcher view = req.getRequestDispatcher("/index.jsp");
view.forward(req, resp);
}
<<<<——IDE报错,修改:
<body>
<%-- id值对应request的实例域中的person成员 --%>
<jsp:useBean id="person" type="com.demo.Person" class="com.demo.Employee" scope="request">
<jsp:setProperty name="person" property="name" value="fuck_admin" />
</jsp:useBean>
<p>Person created by servlet: <jsp:getProperty name="person" property="name" /></p>
</body>
type不仅可以是抽象类,也可以是接口类型、普通类。(共同点是都可以作为实现类or子类的持有者)
使用type,但没有class
试一下就知道了,修改一下JSP;
<body>
<%-- id值对应request的实例域中的person成员 --%>
<jsp:useBean id="person" type="com.demo.Person" scope="request">
<jsp:setProperty name="person" property="name" value="fuck_admin" />
<%-- 通过这个体内语句我们可以判断bean是不是新创建的 --%>
</jsp:useBean>
<p>Person created by servlet: <jsp:getProperty name="person" property="name" /></p>
</body>
完全修改servlet;
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
Employee employee = new Employee();
employee.setName(req.getParameter("name"));
req.setAttribute("person", employee); RequestDispatcher view = req.getRequestDispatcher("/index.jsp");
view.forward(req, resp);
}
重新部署,输出结果仍是admin,证明Person引用正确持有了Employee对象。因此“使用type,但没有class”是可行的。这个时候如果我把
上面的一句代码注释掉;
// req.setAttribute("person", employee);
将无法正常运行(并不会输出fuck_admin),所以,只有type的前提是bean已经在指定作用域存在。
scope属性默认为page
【Head First Servlets and JSP】笔记21:从有脚本到无脚本的更多相关文章
- 【Head First Servlets and JSP】笔记23:Expression Language(EL) 完全攻略
基本上是<Head First Servlets and JSP>内容的整理.扩充.顺便推荐一个供参考的JSP教程:JSP Tutorial内容很全面,还有一些有趣的实例. 完整代码参考 ...
- 【Head First Servlets and JSP】笔记22:直接从请求到JSP & 获取Person的嵌套属性
直接从请求到JSP,不经过servlet <!DOCTYPE html> <html lang="en"> <head> <meta ch ...
- Ext.Net学习笔记21:Ext.Net FormPanel 字段验证(validation)
Ext.Net学习笔记21:Ext.Net FormPanel 字段验证(validation) 作为表单,字段验证当然是不能少的,今天我们来一起看看Ext.Net FormPanel的字段验证功能. ...
- SQL反模式学习笔记21 SQL注入
目标:编写SQL动态查询,防止SQL注入 通常所说的“SQL动态查询”是指将程序中的变量和基本SQL语句拼接成一个完整的查询语句. 反模式:将未经验证的输入作为代码执行 当向SQL查询的字符串中插入别 ...
- JAVA自学笔记21
JAVA自学笔记21 1.转换流 由于字节流操作中文不是非常方便,因此java提供了转换流 字符流=字节流+编码表 1)编码表 由字符及其对应的数值组成的一张表 图解: 2)String类的编码和解码 ...
- SpringMVC内容略多 有用 熟悉基于JSP和Servlet的Java Web开发,对Servlet和JSP的工作原理和生命周期有深入了解,熟练的使用JSTL和EL编写无脚本动态页面,有使用监听器、过滤器等Web组件以及MVC架构模式进行Java Web项目开发的经验。
熟悉基于JSP和Servlet的Java Web开发,对Servlet和JSP的工作原理和生命周期有深入了解,熟练的使用JSTL和EL编写无脚本动态页面,有使用监听器.过滤器等Web组件以及MVC架构 ...
- 【Head First Servlets and JSP】笔记 27: web 应用安全
典型的安全问题:假冒者.窃听者.非法升级者 认证方式: Base64 .摘要认证 .客户端证书.表单认证,重点熟悉摘要算法( HASH . MD5 等) 安全机制:授权.认证.数据完整性.机密性 80 ...
- 【Head First Servlets and JSP】笔记 26: web 应用部署
物理目录结构与虚拟目录结构的差异 WAR 实际上就是 JAR 什么东西应该放在 WEB-INF 文件夹下? <mime-mapping> 相关 <env-entry> 相关 [ ...
- 【Head First Servlets and JSP】笔记18:JSP指令
mark. jetbrain tomcat配置:https://www.jetbrains.com/help/idea/2017.1/creating-and-running-your-first-w ...
随机推荐
- c# 可变数目参数params实例
一般来说,参数个数都是固定的,定义为集群类型的参数可以实现可变数目参数的目的,但是.NET提供了更灵活的机制来实现可变数目参数,这就是使用params修饰符 一般来说,参数个数都是固定的,定义为集群类 ...
- Java逍遥游记读书笔记<二>
Abstract抽象类 1.抽象类不能被实例化 2.抽象方法没有方法体 如: public abstract class Weapen { public abstract void attack(); ...
- 如何利用jQuery检查浏览器是否是IE6-8
$.support.leadingWhitespace是IE特有的属性,用来检查浏览器是否是IE6-8
- <pre>标签让<textarea>标签的内容原样输出
当通过<textarea>插数据进数据的库,取出来后都变成一行变成,用这个<pre>标签能原样输入插入时的格式. 当时要对<pre>加一些CSS样式才行啦. 以下为 ...
- ios开源东西
今天,我们将介绍20个在GitHub上非常受开发者欢迎的iOS开源项目,你准备好了吗? 1. AFNetworking 在众多iOS开源项目中,AFNetworking可以称得上是最受开发者欢迎的库项 ...
- 170306、wamp中的Apache开启gzip压缩提高网站的响应速度
一个网站的响应速度决定该网站的人气和质量,所以wamp配置的服务器也需要支持giz压缩来提高网站的响应速度,如何开启wamp的gzip压缩呢,经过在网站查找资料结合自己服务器中的配置,现在将这个方法分 ...
- 巨蟒python全栈开发flask3
首先,我们新建一个项目: 这个时候,我们调用ab函数,可以在所有的模板中使用. 上边是一个特殊装饰器, 1.flask特殊装饰器 下面说几个特殊的装饰器 再请求之前的装饰器 运行: 这个时候,服务端打 ...
- Windows File 管理工具:junction And Subinacl
junction.exe 是 Sysinternals 出品的命令行工具.使用前建议将其复制到%SystemRoot%/system32目录下 创建一个名为 D:/LINK 的[junction ...
- MYSQ无法启动
http://bbs.51cto.com/thread-433491-1.html http://www.linuxdiyf.com/viewarticle.php?id=97065 http://b ...
- mysql 数据库表名大小写问题
lower_case_table_names=1 原来Linux下的MySQL默认是区分表名大小写的,通过如下设置,可以让MySQL不区分表名大小写:1.用root登录,修改 /usr/my.cnf: ...