Servlet的生命周期方法
通过Log输出的方式,查看Servlet的生命周期方法,下面模拟发起的是get请求
public class ServletTest01 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {
resp.getWriter().write("this is a pig...........");
System.out.println("---doGet------wyk--->");
}
@Override
public void init() throws ServletException {
System.out.println("----init--wyk>");
super.init();
}
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {
resp.getWriter().write("this is a test demo");
System.out.println("----service--wyk>");
super.service(req, resp);
}
@Override
public void destroy() {
System.out.println("----destroy--wyk>");
super.destroy();
}
}
输出结果
----init--wyk>
----service--wyk>
---doGet------wyk--->
----destroy--wyk>
可以得知执行顺序: init----->service----->doGet------>destroy
生命周期方法的职责:
方法 | 作用 |
---|---|
init | Servlet被创建的时候调用 |
service | 每次请求过来会被调用,将请求进行分发,将请求传递给doGet()或doPost()或者其他请求方法 |
destroy | Servlet被移除出服务器的时候调用 |
HttpRequest
1.获取请求信息
public class MyHttpServlet01 extends HttpServlet {
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
String method = req.getMethod(); //请求方式
String uri = req.getRequestURI(); //请求资源
String protocol = req.getProtocol(); //协议版本
System.out.println("请求行:--请求方式---->" + method + "--请求资源---->" +uri + "--协议版本--->" +protocol);
//获取请求头信息
Enumeration<String> requestHeaders = req.getHeaderNames();
for(;requestHeaders.hasMoreElements();){
String name = requestHeaders.nextElement();
String header = req.getHeader(name);
System.out.println("------请求头信息------>" + name +"-----value--"+header);
}
// 打印的信息:
//
// --请求方式---->GET--请求资源---->/HelloWorld/MyHttpServlet--协议版本--->HTTP/1.1
// ------请求头信息------>host-----value--localhost:8080
// ------请求头信息------>user-agent-----value--Mozilla/5.0 (Windows NT 6.1; WOW64; rv:50.0) Gecko/20100101 Firefox/50.0
// ------请求头信息------>accept-----value--text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
// ------请求行信息------>accept-language-----value--zh-CN,zh;q=0.8,en-US;q=0.5,en;q=0.3
// ------请求头信息------>accept-encoding-----value--gzip, deflate
// ------请求头信息------>connection-----value--keep-alive
// ------请求头信息------>upgrade-insecure-requests-----value--1
}
}
2.通过请求头获取用户目前使用的浏览器类型
public class MyHttpServlet02 extends HttpServlet{
/**
* 注意:contains("") 区分字母大小写的
*/
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
String user_agent = req.getHeader("user-agent");
if(user_agent.contains("chrome")){
System.out.println("谷歌");
}
if(user_agent.contains("ie")){
System.out.println("IE浏览器");
}
if(user_agent.contains("Firefox")){
System.out.println("火狐");
}
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
doGet(req,resp);
}
}
3.防盗链功能
public class MyHttpServlet03 extends HttpServlet{
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
//setContentType():修改response(默认码表为iso8859-1)默认的码表,
//但如果输出中文,浏览器可能还是乱码,
//因为并没告诉浏览器用哪种码表解码,所以浏览器还是使用了默认的码表,
//下面的api可以解决这一问题
//response.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=UTF-8");
PrintWriter writer = resp.getWriter();
String header = req.getHeader("referer");
if(header=="" || header.contains("ad.html")){
writer.write("下载中...");
}else{
writer.write("非官方链接下载,无效!!!");
}
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
doGet(req, resp);
}
}
4.使用缓存
/**
* 如果Servlet的代码需要使用缓存,那么一定要重写getLastModified方法
* 进到HttpServlet的源码里看Service方法,可以看到doGet和doPost就是在service方法进行判断调用的,
* 在里面可以看到当请求方式为get的时候,会去判别是否使用浏览器的缓存,
* 可以看到是否使用缓存的关键点是getLastModified这个方法,而这个getLastModified方法的默认返回值为-1,
* 所以如果我们需要用到缓存,那么就需要重写getLastModified这个方法来获取服务端文件的最近修改时间去返回,
* 这样当get请求的时候,才可能用到浏览器的缓存
*
* 如果请求的是一个静态页面,一般情况下浏览器会使用缓存的;
* 动态web资源除了get请求以外,其他都不使用缓存的,而Servlet的get请求默认也是不使用缓存的
*/
public class MyHttpServlet04 extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
try{
FileInputStream inputStream = new FileInputStream("D:\\ddd.txt");
OutputStream outputStream = response.getOutputStream();
byte[] buf = new byte[1024];
int len = 0;
while((len=inputStream.read(buf))!=-1){
outputStream.write(buf,0,len);
}
inputStream.close();
}catch(Exception ex){
//
}
System.out.println("========请求服务端资源成功=========");
}
@Override
protected long getLastModified(HttpServletRequest req) {
File file = new File("D:\\ddd.txt");
return file.lastModified();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request,response);
}
}
HttpResponse
1.通过响应头告知浏览器要以下载的方式处理文件
public class DownLoadServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
File file = new File("d:\\yh.png");
System.out.println("====Name===>" + file.getName());
//可以从浏览器拿到的响应头 看到 content-disposition: attachment;filename=yh.png(content设置:附件、文件名)
// response.setHeader("content-disposition","attachment");通知浏览器以文件下载的形式处理
//文件下载的时候对文件名称进行URL编码,使用utf-8,各大厂商定的规则
response.setHeader("content-disposition","attachment;filename="+URLEncoder.encode(file.getName(),"utf-8"));
OutputStream outputStream = response.getOutputStream();
FileInputStream inputStream = new FileInputStream(file);
byte[] buf = new byte[1024];
int len = 0;
while((len=inputStream.read(buf))!=-1){
outputStream.write(buf,0,len);
}
inputStream.close();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
2.将文件进行压缩后输出到浏览器
public class GzipServlet extends HttpServlet{
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
//告诉浏览器我传输给你的文件是gzip压缩的,先解压再显示
resp.setHeader("content-encoding", "gzip");
OutputStream outputStream = resp.getOutputStream();
StringBuilder builder = new StringBuilder();
for(int i=0;i<150;i++){
builder.append("abcde" + i);
}
System.out.println("----No Gzip---->" + builder.toString().length()); //1090
//压缩之后,通过谷歌浏览器的请求头信息查看大小是310
GZIPOutputStream gzipOutputStream = new GZIPOutputStream(outputStream);
gzipOutputStream.write(builder.toString().getBytes());
gzipOutputStream.finish();
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
doGet(req, resp);
}
}
3.设置响应头,让其重定向,页面重新跳转
public class LocationServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
/*response.setStatus(302); //302是重定向;
response.setHeader("location","/HelloWorld/ad.html");*/
response.sendRedirect("/HelloWorld/ad.html"); //该代码==上面的两句
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request,response);
}
}
4.通知浏览器不要产生缓存文件
/**
* Expires: -1 --不缓存
* Cache-Control: no-cache --不缓存
* Pragma: no-cache --不缓存
*/
public class NoCacheServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//不同浏览器所需要的头不一样, 凡是涉及到密码的页面信息都不要产生缓存文件,
//容易造成信息外泄。(所以三种都写)
response.setHeader("Expires", "-1");
response.setHeader("Cache-Control","no-cache");
response.setHeader("Pragma", "no-cache");
//response.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
response.getWriter().write("当前的系统时间==" + System.currentTimeMillis());
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
5.设置浏览器定时刷新或跳转
public class RefreshServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//response.setHeader("refresh", "1"); //告知浏览器,每秒刷新一次
response.setHeader("refresh","3;url=/HelloWorld/index.jsp");//指定秒数,然后定时跳转
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
补充
get和post请求方式的区别
-
1.get的数据携带在Url后面,post的数据则在实体内容;
-
2.get携带的数据信息不可大于1kb,post则无限制;
-
3.get不能用于提交敏感数据,post可用于提交敏感数据;
-
4.get提交方式会产生缓存文件,post提交方式不会产生缓存文件