Response概述:
response是Servlet.service方法的一个参数,类型为javax.servlet.http.HttpServletResponse。在客户端发出每个请求时,服务器都会创建一个response对象,并传入给Servlet.service()方法。response对象是用来对客户端进行响应的,这说明在service()方法中使response对象可以完成对客户端的响应工作。
response对象的功能分为以下四种:
- 设置响应头信息;
- 发送状态码;
> sendError(int sc) --> 发送错误状态码,例如404、500
> sendError(int sc, String msg) --> 也是发送错误状态码,还可以带一个错误信息!
> setStatus(int sc) --> 发送成功的状态码,可以用来发送302
3. 设置响应正文;
4. 重定向;
具体应用:
1.重定向
package zy.servlet;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class Aservlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
/*
* 设置location响应头 ,实现请求重定向
*/
//response.setHeader("Location","/JavaWeb/Bservlet");
//设置服务器的响应状态码
//response.setStatus(302);
//快捷的重定向方式
//response.sendRedirect(""http://www.baidu.com""); response.sendRedirect("/JavaWeb/Bservlet");
}
}
抓包可以看见:
服务器返回一个302状态码告诉浏览器,你要的资源我没有,但是我通过Location响应头告诉你哪里有,而浏览器解析响应头Location后知道要跳转到/JavaWeb/Bservlet页面,所以就会自动跳转到Bservlet。
2.设置refresh响应头,让浏览器定时刷新
package zy.servlet;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/*
* 设置location响应头 ,实现请求重定向
*/
public class Cservlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/html;charset=utf-8");
response.getWriter().print("5s中后将跳转到百度主页");
/*
* 设置refresh响应头,让浏览器每隔3秒定时刷新
* response.setHeader("refresh", "3");
*/
//设置refresh响应头,让浏览器3秒后跳转到http://www.baidu.com
response.setHeader("Refresh","5;URL=http://www.baidu.com");
/*
* 5秒跳转到Csevlet
response.setHeader("Refresh","5;URL=/JavaWeb/Cservlet");
*/
}
}
访问Cservlet,5秒将会跳转
3.禁用浏览器缓存
开发项目的时候浏览器的缓存会很讨厌,这时我们可以禁用它,可以参考indexjsp.
package zy.servlet;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/*
* 禁用浏览器缓存
*/
public class Dservlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
/*
* 这三个响应头的设置可以禁用所有浏览器的缓存
*/
response.setHeader("cache-control","no-cache");
response.setHeader("pragma","no-cache");
response.setDateHeader("expires",-1);
response.getWriter().print("hello world");
}
}
访问:
4.设置页面缓存
对于不经常变化的数据,在servlet中可以为其设置合理的缓存时间值,以避免浏览器频繁向服务器发送请求,提升服务器的性能。例如:
package zy.servlet;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class Eservlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String data = "helloworld";
/**
* 设置数据合理的缓存时间值,以避免浏览器频繁向服务器发送请求,提升服务器的性能
* 这里是将数据的缓存时间设置为1天
*/
response.setDateHeader("expires",System.currentTimeMillis() + 24 * 3600 * 1000);
response.getOutputStream().write(data.getBytes());
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
this.doGet(request, response);
}
}
访问页面,并查看响应头:
有8个小时的时差。
另外也可以在“C:\Users\zydev\AppData\Local\Microsoft\Windows\Temporary Internet Files”找到该文件,注意要打开隐藏文件夹选项才看得见。
Response的响应正文
response是响应对象,向客户端输出响应正文(响应体)可以使用response的响应流,repsonse一共提供了两个响应流对象:
1. PrintWriter out = response.getWriter():获取字符流;
2. ServletOutputStream out = response.getOutputStream():获取字节流
OutputStream流是字节流,可以处理任意类型的数据,而PrintWriter流是字符流,只能处理字符数据,如果用字符流处理字节数据,会导致数据丢失。
A. 相应图片字节流
package zy.servlet;
import java.io.FileInputStream;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.io.IOUtils;
/*
* 演示响应字节数据
*/
public class Fservlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String path = "D:/demo.jpg";
FileInputStream in = new FileInputStream(path);
//读取输入流的字节到字节数组中,IOUtis是Apache提供的一个工具jar包
byte[] bytes = IOUtils.toByteArray(in);
response.getOutputStream().write(bytes);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
this.doGet(request, response);
}
}
访问结果:
B. 下载图片
package com.web.study;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* 文件下载
*/
public class Bresponse extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
downloadFileByOutputStream(response);//下载文件,通过OutputStream流
}
/**
* 下载文件,通过OutputStream流
* @param response
* @throws FileNotFoundException
* @throws IOException
*/
private void downloadFileByOutputStream(HttpServletResponse response)
throws FileNotFoundException, IOException {
//1.获取要下载的文件的绝对路径
String realPath = this.getServletContext().getRealPath("/download/demo.jpg");
//2.获取要下载的文件名
String fileName = realPath.substring(realPath.lastIndexOf("\\")+1);
//3.设置content-disposition响应头控制浏览器以下载的形式打开文件
response.setHeader("content-disposition", "attachment;filename="+fileName);
//4.获取要下载的文件输入流
InputStream in = new FileInputStream(realPath);
int len = 0;
//5.创建数据缓冲区
byte[] buffer = new byte[1024];
//6.通过response对象获取OutputStream流
OutputStream out = response.getOutputStream();
//7.将FileInputStream流写入到buffer缓冲区
while ((len = in.read(buffer)) > 0) {
//8.使用OutputStream将缓冲区的数据输出到客户端浏览器
out.write(buffer,0,len);
}
in.close();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
访问:
如果文件名是中文的:设置content-disposition响应头控制浏览器以下载的形式打开文件,中文文件名要使用URLEncoder.encode方法进行编码,否则会出现文件名乱码
response.setHeader("content-disposition", "attachment;filename="+URLEncoder.encode(fileName, "UTF-8"));