Tomcat容器:按照Http协议的格式,把请求信息封装成Request对象,把响应信息封装成Response对象,所以Servlet实现类中就能够获取这两个对象。
主要学习这两个对象中的常用方法
Response对象中常用的方法:
getWrite()获取字符流
getOutPutStream()获取字节流
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//1)向浏览器发送404状态码
//response.sendError(404,"页面找不到了,怎么办?");
//2)页面定时跳转,定时刷新,刷新响应头(Refresh键的使用)
//实现的功能:网页将在几秒钟之后进行跳转,通过配合js进行实现
//response.getWriter().write(new Random().nextInt() + "test");
//参数为刷新时间,每隔1秒刷新一次,打印随机数
//response.setHeader("Refresh", "1");//刷新
//response.setHeader("Refresh", "3;http://www.baidu.com");
//3)设置重定向(设定响应状态码,关键字是Location)
//response.setStatus(302);
//添加Location头,高速浏览器重定向到哪里去
//response.setHeader("Location","http://www.baidu.com");
//另一种实现方式:封装好的重定向,参数只要传递重定向的路径就可以啦
//response.sendRedirect("http://www.baidu.com");
//4)使用字节流,向浏览器发送中文
//如何解决乱码问题:编解码表一致即可,使用utf-8进行编码,也要告诉浏览器使用此进行解码
//response.getOutputStream().write("相守余生".getBytes("UTF-8"));
//response.setHeader("Content-type","text/html;charset=GBK");//出现乱码
//response.setHeader("Content-type","text/html;charset=UTF-8");
//5)字符流发送中文(字节流和字符流不能同时使用)
//设置解码码表
//response.setCharacterEncoding("UTF-8");
//设置编码码表
//response.setHeader("Content-Type","text/html;charset=UTF-8");
//response.getWriter().write("相守余生");//单纯发送字符,会出现乱码
//6)将图片发送给浏览器展示(字节流的形式实现)(把图片通过输入流读取到内存中,写入到输出流汇总)
//告诉浏览器发送的数据类型 在网页中显示图片而不是下载到本地
//ServletContext sc = this.getServletContext();
//String mimeType = sc.getMimeType("1.jpg");
//response.setContentType(mimeType);
//通过全局变量,获取图片的资源
//InputStream stream = sc.getResourceAsStream("/WEB-INF/classes/1.jpg");
//获取一个输出流
//ServletOutputStream ops = response.getOutputStream();
//byte[] bytes = new byte[1024];
//int len = -1;
//while ((len = stream.read(bytes)) != -1) {
// ops.write(bytes, 0, len);
// ops.flush();
//}
//7)下载文件的实现,主要设置请求头信息:内容配置
//告诉浏览器,当前流中的内容用于文件下载,推荐使用什么名称保存
response.setHeader("Content-Disposition", "attachment;filename=111.jpg");
//把图片加载到内存中
InputStream is = this.getServletContext().getResourceAsStream("/WEB-INF/classes/1.jpg");
//获取输出流对象,并向其中写入图片字节
ServletOutputStream outputStream = response.getOutputStream();
byte[] buffer = new byte[1024];
int len = -1;
while ((len = is.read(buffer)) != -1) {
outputStream.write(buffer, 0, len);
outputStream.flush();
}
}
Request对象中常用的方法:
request.getParameter("names");根据键获取对应的值
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//1)获取所有提交的键(全是字符串,所有键的枚举)
Enumeration<String> parameterNames = request.getParameterNames();
while (parameterNames.hasMoreElements()) {
//获取当前的键
String key = parameterNames.nextElement();
//根据键获取对应的值
if (key.equals("names")) {
String names = request.getParameter("names");
System.out.println(names);
} else {
//如果值有多个
String[] values = request.getParameterValues(key);
System.out.println(Arrays.toString(values));
}
}
//获取封装请求参数的map
Map<String, String[]> map = request.getParameterMap();
System.out.println(map.size());
System.out.println(request.getMethod());
System.out.println(request.getRequestURI());
System.out.println(request.getServletPath());
System.out.println(request.getScheme());
System.out.println(request.getServerPort());
System.out.println(request.getServerName());
System.out.println(request.getLocale());
}
Request对象get方式获取参数解决乱码问题(特别要注意乱码问题的解决)
在字符串转化成字节数组的时候,可以手动设置编码码表
通过字节数组创建字符串的时候也可以设置解码码表
如何理解action?
把action理解成是servlet,因为它的作用和servlet差不多,都是接收页面请求和参数,然后执行跳转。
jsp页面:
通过表单的形式提交参数
设置当前jsp页面的编码方式:pageEncoding="UTF-8"
浏览器编码会使用,表单所在页面的码表作为编码表
<%@ page contentType="text/html;charset=UTF-8" language="java" pageEncoding="UTF-8" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<!--name其实相当于id-->
<form action="/EServlet" method="post">
用户名:<input type="text" name="name"><br/>
密 码:<input type="text" name="password"><br/>
爱好:<input type="checkbox" name="habit" value="a"/> 抽烟
<input type="checkbox" name="habit" value="b"/> 喝酒
<input type="checkbox" name="habit" value="c"/> 打豆豆
<br/>
<input type="submit" value="登录">
</form>
</body>
</html>
和协议有关的类:HttpServletRequest 、HttpServletResponse
request域:其实就是放置在request对象中的一个map集合,它是用来专门配合请求转发使用的;因为在servlet中我们需要把处理的结果交给后续的jsp,我们可以通过request域进行数据传递。
新建Servlet,别忘了在web.xml中进行注册和配置。
访问jsp页面,直接在地址栏中输入即可;http://localhost:8080/servlet/request.jsp
访问servlet,要知道准确的url-pattern;/servlet/request,记得配置action。
HTTP协议常见错误码:
1) 在HTTP协议中,HTTP Status 500 是服务器内部错误。错误的直接现象是,JSP有错,没法编译。
2) HTTP404 错误意味着链接指向的网页不存在,即原始网页的URL失效
请求转发与请求重定向的区别:
1)是否是一个请求?请求转发是一个请求,而请求重定向是两个请求。
2)浏览器地址栏变化?请求转发时地址栏中的地址不会发生改变,而重定向会发生改变
3)是否可以携带数据?请求转发可以在request域中携带数据,而重定向是两个请求,会创建两个request对象,不能携带数据。
4)请求转发不会改变请求方式,可能一直是get;但是重定向的第二次请求永远都是get。
jsp的本质是servlet。
请求转发什么时候使用:一般都是Servlet转发给一个jsp,因为servlet适合处理业务逻辑,不适合前端显示;而jsp适合输出前端代码,不适合做逻辑处理;所以请求转发可以使jsp与servlet配合起来,一个负责业务逻辑处理,一个负责前端显示。
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//设置解码码表
//获取用户输入的用户名和密码
//验证用户名和密码是否正确
//将验证结果放到request域中
//转发request对象和response对象到FServlet中
request.setCharacterEncoding("UTF-8");
String name = request.getParameter("name");
String password = request.getParameter("password");
if (name.equals("chenrushui") && password.equals("0000")) {
request.setAttribute("result", true);
} else {
request.setAttribute("result", false);
}
//进行请求转发(获取一个请求转发器,进行转发)
//请求转发是一个请求,url地址栏中的地址并没有发生改变,使用同一个request对象
request.getRequestDispatcher("/FServlet").forward(request, response);
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
byte[] bytes = "陈如水".getBytes("utf-8");
String s = new String(bytes,"utf-8");
}
请求包含:多个servlet共同输出内容。开发时,如果多个页面要显示相同的内容,那么我们可以把这些相同的内容抽取到一个单独的jsp页面中,在凡是需要显示这部分相同内容时,在需要显示的地方,把jsp页面包含进来即可。
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//HttpServletRequest request 请求对象:包含一些请求信息,可以获取,浏览器帮我们发出网络请求。
//HttpServletResponse response详情对象:用于响应客户端请求,通过response对象向客户端发送信息
//1,如何实现重定向功能
response.setStatus(302); //设置状态码 302表示重定向,将资源定位到新的url
response.setHeader("Location", "https://www.baidu.com/");//设置响应头(返回一个键值对信息)
//告诉浏览器,服务器端返回内容类型与编码方式
String result = "谁在悬崖沏一壶茶\n" +
"温热前世的牵挂\n" +
"而我在调整千年的时差\n" +
"爱恨全喝下";
//对响应头进行设置
//告诉浏览器,请求资源的最后修改时间
response.setHeader("Last-Modified", new Date() + "");
response.setHeader("Content-type", "text/html;charset=utf-8");
//打印编码类型
System.out.println(response.getCharacterEncoding());
//可以直接返回字符串
response.getWriter().write(result);
//response.getOutputStream().write(result.getBytes());
//刷新响应头
response.getWriter().write(new Random().nextInt() + "test");
//参数为刷新时间,每隔1秒刷新一次
response.setHeader("Refresh", "1");
}
@Override
public void init(ServletConfig config) throws ServletException {
super.init(config);
//Tomcat在启动的时候就会创建Servlet
System.out.println("测试在容器加载的时候,创建Servlet1");
ServletContext servletContext = getServletContext();
servletContext.setAttribute("name", "太古神王");
}