《JavaWeb从入门到改行》关于BaseServlet那些事
@为什么需要BaseServlet? 我们知道一个POST或者GET提交对应着一个Servlet, 无数的提交会让Servlet页面增加,我们希望一个Servlet就能处理很多提交的请求。
@BaseServlet 是一个继承了HttpServlet的普通类,并不是Servlet类,所以不需要在web.xml中添加路径。但是Servlet会继承这个BaseServlet来实现一个Servlet处理多个提交请求 。
@一些要求 是: 客户端发送请求时,必须提供一个参数(本文编写的这个参数名字叫method,这个method和form中的那个method没有半毛钱关系,只是一个变量名字而已),用来说明要调用Servlet中的那个处理方法; 其次,继承了BaseServlet的Servlet中的处理请求的方法的原型必须与service方法相同,即返回值类型、参数都不需要和service方法相同。即如下的形式:
public String XXX(HttpServletRequest request, HttpServletResponse
response) throws ServletException, IOException { return null ;
}
@POST和GET请求对于method参数的提供技巧 POST请求一般为表单形式,提供method参数的方式可以添加一个隐藏字段 <input type="hidden" name="method" value="希望调用Servlet中的方法的名字"/> ; @GET请求一般为超链接,提供method参数的方式直接在路径后面加 ?method=方法名
@POST和GET请求编码处理 我们知道Servlet对POST请求和对GET请求的请求编码不同,区别如下:
POST的请求
request.setCharacterEncoding("utf-8");
String name = request.getParameter("name");
GET的请求
String name = request.getParameter("name");
name = new String(name.getBytes("ISO-8859-1"),"utf-8");
POST和GET的响应编码都是:
response.setContentType("text/html;charset=UTF-8");
为了使得servlet中的代码简洁,我们可以把两种编码的代码放到BaseServlet中,但是,像上传下载这种请求不适合用BaseServlet,所以我们一般把这种代码写在过滤器中,过滤器不是本文主要内容,如果你不会的话,可以不用过滤器,把编码的代码直接写在servlet中的请求处理方法中即可 。
@源码
<%--get请求,传递过去method参数,指明调用TestServlet的fun2方法,并且传递一个参数param--%>
<a href="<c:url value='/TestServlet?method=fun2¶m=哈哈'/>"> 点击这里啊</a>
<%--post请求--%>
<form action="<c:url value='/TestServlet'/>" method="post">
<input type="hidden" name="method" value="fun1"/>
<input type="text" name="param" value="我是表单参数" />
<input type="submit" name="提交"/>
</form>
请求jsp页面
package cn.demo1.baseServlet; import java.io.IOException; import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* TestServlet
* 实现了一个Servlet中多个请求处理方法
* 方法的的参数必须和service方法相同
* 客户端必须传递过来method参数,说明是调用哪一个请求处理方法
* @author ZHAOYUQIANG
*
*/
public class TestServlet extends BaseServlet {
/**
* 测试post传递过来的参数
* @param request
* @param response
* @return
* @throws ServletException
* @throws IOException
*/
public String fun1(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String param = request.getParameter("param");
request.setAttribute("param", param);
return "f:/baseServlet/index.jsp" ;
}
/**
* 测试get请求传递过来的参数
* @param req
* @param resp
* @return
* @throws ServletException
* @throws IOException
*/
public String fun2(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String param = request.getParameter("param");
request.setAttribute("param", param);
return "f:/baseServlet/index.jsp";
}
}
请求Servlet
package cn.demo1.baseServlet; import java.io.IOException;
import java.lang.reflect.Method; import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* BaseServlet[抽象类] 不需要在web.xml中添加路径
* @功能 1.
* @author ZHAOYUQIANG
*
*/
public abstract class BaseServlet extends HttpServlet {
public void service(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// response.setContentType("text/html;charset=UTF-8");//处理响应编码
/*
* 设置POST和GET请求编码
*/
/*
* 1. 获取参数,用来识别用户想请求的方法
* method是用户在浏览器地址栏中输入的想要调用的方法,是个参数
*/
String methodName = request.getParameter("method");
/*
* 2. 判断用户有没有传参数
*/
if(methodName == null || methodName.trim().isEmpty()){
throw new RuntimeException("您没有传递method参数! 无法确定您要调用的方法!");
}
/**
* 3. 判断是哪一个方法,是哪一个就调用哪一个
* 所用的技术是: 反射
* 需要得到本类Class,然后调用它的getMethod,通过传递过来的方法名字进行得到Method对象
* 这样做的目的是: 以后像其他Servlet中的方法要修改或者添加新方法时,就不用在去修改这一块代码了
*/
/*
* 3.1. 得到当前类的对象
*/
Class c = this.getClass();
/*
* 3.2. 通过传递过来的方法名(addUse等)得到Method对象
* 导包 :java.lang.reflect.Method;
*/
Method method = null ;
try {
method = c.getMethod(methodName,
HttpServletRequest.class,HttpServletResponse.class);
} catch (Exception e) {
throw new RuntimeException("您要调用的方法"+methodName+",它不存在");
}
try {
/*
* 3.3. 调用method表示的方法,即: 调用继承该类的类中的方法
* 反射调用: 用this来调用method表示的方法,并且传递参数req和resp
*/
String result =(String)method.invoke(this, request,response);
/**
* 4. 处理从继承这个类的类中返回的字符串(重定向和转发)
* return "r:/index.jsp"; 和 return "f:/index.jsp";
* 返回的是字符串,需要解读字符串
*/
/*
* 4.1. 如果用户返回的字符串为null,或者"",那么什么都不做
*/
if(result == null || result.trim().isEmpty()){
return ;
}
/*
* 4.2. 解读字符串1:判断字符串中有没有冒号
* 没有冒号默认表示转发,反之再进行判断
*/
if(result.contains(":")){
/*
* 4.3. 解读字符串2 : 先获取冒号位置,然后截取前缀(操作,是重定向还是转发)和后缀(路径)
*/
int index = result.indexOf(":");
String operate = result.substring(0,index);
String path = result.substring(index+1);
/*
* 4.4. 进行处理,如果是r重定向,如果是f则转发
*/
if(operate.equalsIgnoreCase("r")){
response.sendRedirect(request.getContextPath()+path);
}else if(operate.equalsIgnoreCase("f")){
request.getRequestDispatcher(path).forward(request, response);
}else{
throw new RuntimeException("您指定的操作"+operate+
"不支持,请正确填写:r和f");
}
}else{
/*
* 没有冒号默认转发处理
*/
request.getRequestDispatcher(result).forward(request, response);
}
} catch (Exception e) {
System.out.println("您要调用的方法"+methodName+",它内部抛出了异常");
throw new RuntimeException(e);
}
}
}
BaseServlet
package cn.demo1.baseServlet; import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest; /**
* 辅助Servlet简化编码代码
*/
public class EncodingFilter implements Filter { public void destroy() {
// TODO Auto-generated method stub
}
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
/*
* 处理post请求乱码问题
*/
request.setCharacterEncoding("utf-8");
/*
* 处理GET请求编码问题
* String name1 = request.getParameter("name");
* name2 = new String(name.getBytes("ISO-8859-1"),"utf-8");
* GET不一样,设置编码后,servlet中获取name,获取应该是name2,都是如果如上写的话,
* getParameter("name")获取的是name1 .
* 掉包request
* 1. 写一个request的装饰类
* 2. 放行时,使用我们自己的request
* 3. 但是POST方式依然使用request
*/
HttpServletRequest req = (HttpServletRequest) request ;
if(req.getMethod().equals("GET")){
EncodingRequest er = new EncodingRequest(req);
chain.doFilter(er, response);
}else if(req.getMethod().equals("POST")){
chain.doFilter(request, response);
}
response.setContentType("text/html;charset=UTF-8");
} public void init(FilterConfig fConfig) throws ServletException {
// TODO Auto-generated method stub
} }
EncodingFilter类
package cn.demo1.baseServlet; import java.io.UnsupportedEncodingException; import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
/**
* 辅助过滤器来处理GET编码问题
* @author ZHAOYUQIANG
*
*/
public class EncodingRequest extends HttpServletRequestWrapper{
private HttpServletRequest request ; public EncodingRequest(HttpServletRequest request) {
super(request);
this.request = request ;
}
/**
* 处理编码问题
*/
public String getParameter(String name) {
String value = request.getParameter(name);
/*
* 处理编码问题
*/
try {
value = new String (value.getBytes("ISO-8859-1"),"utf-8");
} catch (UnsupportedEncodingException e) {
// TODO Auto-generated catch block
throw new RuntimeException(e);
} return value;
} }
EncodingRequest类
<filter>
<display-name>EncodingFilter</display-name>
<filter-name>EncodingFilter</filter-name>
<filter-class>cn.demo1.baseServlet.EncodingFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>EncodingFilter</filter-name>
<url-pattern>/TestServlet</url-pattern>
</filter-mapping>
过滤器的拦截配置
@项目下载
http://files.cnblogs.com/files/zyuqiang/webBlogTest.rar
《JavaWeb从入门到改行》关于BaseServlet那些事的更多相关文章
- 《JavaWeb从入门到改行》过滤器学习笔记
>"; display: block; height: 0; clear: both; visibility: hidden; } #sitemap, #sitemap ul{disp ...
- 《JavaWeb从入门到改行》注册时向指定邮箱发送邮件激活
javaMail API javaMail是SUN公司提供的针对邮件的API . 两个jar包 mail.jar 和 activation.jar java mail中主要类:javax.mail. ...
- 《JavaWeb从入门到改行》多重外键关系在java中的处理方案
目录:(点击红色方框展开子目录) 问题描述 无 项目案例说明 业务描述 数据库说明 项目源码及下载 无 问题描述 如上两图,数据库中各个表之间有很多的外键关系,其中业务关系是一个用户下有该用户的订单, ...
- 《JavaWeb从入门到改行》分页功能的实现
@目录 什么是分页 ? 两个子模块功能的问题分析 和 解决方案 有条件查和无条件查询的影响 和 解决方案 项目案例: mysql + commons-dbutils+itcast-tools+Base ...
- 《JavaWeb从入门到改行》JSP+EL+JSTL大杂烩汤
title: Servlet之JSP tags: [] notebook: javaWEB --- JSP是什么 ? JSP就是Servlet,全名是"JavaServer Pages&qu ...
- 《JavaWeb从入门到改行》那些年一起学习的Servlet
目录 获取ServletContext : ServletContext接口中的一些方法 application域存取数据功能 代码演示: application域获取项目文件路径 代码演示: API ...
- 《JavaWeb从入门到改行》JDBC经典秘方QueryRunner
目录: 基础篇_功能各自回顾 JDBC基础代码回顾(使用JdbcUtils工具简化) c3p0数据库连接池的使用(使用JdbcUtils工具简化) 大数据的插入(使用c3p0+JdbcUtils工具简 ...
- 《JavaWeb从入门到改行》fileupload,没毛病
目录: » fileupload API > 文件上传的要求 > fileupload组件 » 上传细节的代码演示 » 项目案例-上传头像并显示 fileupload API 文 ...
- 《JavaWeb从入门到改行》很好的复习资料: SQL语句到底怎么写 ?
本文用到的数据库如下: CREATE DATABASE exam; /创建部门表/ CREATE TABLE dept( deptno INT PRIMARY KEY, dname ), loc ) ...
随机推荐
- day03 --class --homework
'''# >>>>>>2 :,有字符串s = "123a4b5c"#>>>>>^ 1: # 1)通过对s切片形成新 ...
- mysql数据库中常用操作汇总
一.查询数据库的基本信息: 1. /* 查询数据库 ‘boss’ 所有表及注释 */SELECT TABLE_NAME,TABLE_COMMENT FROM information_schema ...
- P2278 操作系统
P2278 操作系统 题目描述 写一个程序来模拟操作系统的进程调度.假设该系统只有一个CPU,每一个进程的到达时间,执行时间和运行优先级都是已知的.其中运行优先级用自然数表示,数字越大,则优先级越高. ...
- Hyper-V如何新建虚拟机
http://www.xitongtiandi.net/wenzhang/soft/24543.html
- 前端知识总结--js原型链
js的原型链听着比较深奥,看着容易晕,梳理一下还是比较容易懂的 (先简单写下,后续有时间再整理) 简而言之 原型链:就是js的对象与对象之间,通过原型组成建立的层层关系,构成了整个链条,称之为原型链 ...
- 必须声明表变量 "@P0"
mybatis提示错误 ### Cause: com.microsoft.sqlserver.jdbc.SQLServerException: 必须声明表变量 "@P0". ; u ...
- (JAVA作业)练习:创建一个类名为Fruit;包含实例变量:水果名称,颜色,价格,上市月份,有无种子 10个实例:苹果,香蕉,芭乐,柚子,李子,杨桃,猕猴桃,哈密瓜,葡萄,榴莲; 实现功能:提示用户输入水果品种编号,输出该水果的全部信息。
class Lei { String name; String color; int price; int date; int num; String zz; void assemble(){ Sys ...
- [转] CDH6 安装文章链接收集
CentOS 7下Cloudera Manager及CDH 6.0.1安装过程详解 http://blog.51cto.com/wzlinux/2321433?source=dra Cloudera ...
- mac下抓包工具charles
图片没带过来,想看截图的可以直接点击有道云笔记的链接: http://note.youdao.com/share/?id=f5c7369a0c1e1e37cdcd08a04d33be7e 1.下载 h ...
- (java/javascript) list 交集 并集 差集 去重复并集
java list 交集 并集 差集 去重复并集 package com; import java.util.ArrayList; import java.util.Iterator; import ...