Servlet和JSP进阶

Servlet和JSP进阶

  • 掌握JavaWeb核心特性
  • 掌握Servlet核心对象
  • 了解JSP九大内置对象

一、 HTTP请求的结构

HTTP请求包含三部分:请求行、请求头、请求体(只有POST请求才有请求体)
alt

新建一个项目命名为:request-struc
新建一个servlet:

package com.test.servlet;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
* Servlet implementation class RequestServlet
*/
@WebServlet("/request")
public class RequestServlet extends HttpServlet {
   private static final long serialVersionUID = 1L;
      
   /**
    * @see HttpServlet#HttpServlet()
    */
   public RequestServlet() {
       super();
       // TODO Auto-generated constructor stub
   }

   /**
    * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
    */
   protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
   	response.getWriter().println("This is get method");
   }

   /**
    * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
    */
   protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
   	response.getWriter().println("This is post method");
   }

}

新建一个input.html

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
	<form action="/request-struc/request" method="get">
		<input name="username">
		<input name="password" type="password">
		<input type="submit">
	</form>
</body>
</html>

打开网址:
alt
alt
alt

二、 巧用请求头开发多端应用

同一个网站在不同的设备显示样式不同
alt
alt

编写代码查看请求头:

package com.test.servlet;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class UserAgentServlet
 */
@WebServlet("/ua")
public class UserAgentServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public UserAgentServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String userAgent = request.getHeader("user-Agent");
		response.setContentType("text/html;charset=utf-8");
		response.getWriter().println(userAgent);
	}

}

alt
切换模式:alt

改进代码:

package com.test.servlet;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class UserAgentServlet
 */
@WebServlet("/ua")
public class UserAgentServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public UserAgentServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String userAgent = request.getHeader("user-Agent");
		response.setContentType("text/html;charset=utf-8");
		response.getWriter().println(userAgent);
		String output = "";
		if(userAgent.indexOf("Windows NT") != -1) {
			output = "<h1>这是P C端首页</h1>";
		}else if(userAgent.indexOf("iphone") != -1 || userAgent.indexOf("Android") != -1) {
			output = "<h1>这是移动端首页</h1>";
		}
		response.getWriter().println(output);
	}

}

alt

alt

三、 响应的结构

  • HTTP请求包含三部分:请求行、请求头、请求体(只有POST请求才有请求体)
    alt

  • HTTP常见的状态码

状态码错误描述
200服务器处理成功
404无法找到文件
500内部服务器错误
403服务拒绝访问
301、302请求重定向
400无效的请求
401未经过授权
503服务器超负载或正停机维护,无法处理请求处理

四、 ContentType的作用

ContentType决定浏览器采用何种方式对响应体进行处理

MIME类型描述
text/plain纯文本
text/htmlHTML文件
text/xmlXML文档
application/x-msdownload需要下载的资源
image/jpeg图片资源
image/gif图片资源

五、 请求转发与重定向

平时我们只用一个servlet,但在实际开发中我们是需要使用多个servlet的,他们之间如何跳转?
多个servlet(JSP)之间跳转有两种方式:

  1. request.getResquestDispatcher().forward() -请求转发
  2. response.sendRedirect() -响应重定向

在com.test.servlet下面建一个子包com.test.servlet.direct

  • 请求转发的形式:
    alt
    代码:
package com.test.servlet.direct;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class CheckLoginServlet
 */
@WebServlet("/direct/check")
public class CheckLoginServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public CheckLoginServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("用户登录成功");
		//实现了请求转发的功能
		request.getRequestDispatcher("/direct/index").forward(request, response);
	}

}

package com.test.servlet.direct;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class IndexServlet
 */
@WebServlet("/direct/index")
public class IndexServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public IndexServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		response.getWriter().println("This is index page");
	}

}

alt
alt

  • 响应重定向的方式
package com.test.servlet.direct;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class CheckLoginServlet
 */
@WebServlet("/direct/check")
public class CheckLoginServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public CheckLoginServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("用户登录成功");
		//实现了请求转发的功能
		//request.getRequestDispatcher("/direct/index").forward(request, response);
		//响应重定向需要增加contextPath
		response.sendRedirect("/servlet_advanced/direct/index");
	}

}

alt

两者之间的不同

  1. 从表象上看,两者的地址栏内容不同
  2. alt
  3. alt

设置请求自定义属性

  • 请求允许创建自定义属性
  • 设置请求属性:request.setAttribute(属性名,属性值)
  • 获取请求属性:Object attr = request.getAttribute(属性名)
    代码:
package com.test.servlet.direct;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class CheckLoginServlet
 */
@WebServlet("/direct/check")
public class CheckLoginServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public CheckLoginServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("用户登录成功");
		request.setAttribute("username", "admin");
		//实现了请求转发的功能
		request.getRequestDispatcher("/direct/index").forward(request, response);
		//响应重定向需要增加contextPath
		//response.sendRedirect("/servlet_advanced/direct/index");
	}

}

package com.test.servlet.direct;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class IndexServlet
 */
@WebServlet("/direct/index")
public class IndexServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public IndexServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String username = (String)request.getAttribute("username");
		response.getWriter().println("This is index page!current username is " + username);
	}

}

alt

六、 浏览器Cookie

Cookie(小甜饼)是浏览器保存在本地的文本内容
Cookie常用于保存登录状态、用户资料等小文本
Cookie具有时效性,Cookie内容会伴随着请求发送给Tomcat

举例:7天内自动登录alt

代码:

package com.test.servlet.cookie;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class TestLoginServlet
 */
@WebServlet("/cookies/login")
public class TestLoginServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public TestLoginServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("用户登录成功");
		Cookie cookie = new Cookie("user", "admin");
		response.addCookie(cookie);
		response.getWriter().println("login success");
	}

}

alt
alt

下面我们读取Cookie:

package com.test.servlet.cookie;

import java.io.IOException;
import java.util.Iterator;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class TestIndexServlet
 */
@WebServlet("/cookies/index")
public class TestIndexServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public TestIndexServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//request.getCookies()用于获取所有的Cookie信息
		Cookie[] cs = request.getCookies();
		for (Cookie c : cs) {
			System.out.println(c.getName() + ":" + c.getValue());
		}
	}

}

alt

改进代码,判断用户是否登录:

package com.test.servlet.cookie;

import java.io.IOException;
import java.util.Iterator;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class TestIndexServlet
 */
@WebServlet("/cookies/index")
public class TestIndexServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public TestIndexServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//request.getCookies()用于获取所有的Cookie信息
		Cookie[] cs = request.getCookies();
		String user = null;
		for (Cookie c : cs) {
			System.out.println(c.getName() + ":" + c.getValue());
			if (c.getName().equals("user")) {
				user = c.getValue();
				break;
			}
		}
		
		if (user == null) {
			response.getWriter().println("user not login");
		}else {
			response.getWriter().println("user: "+ user);
		}
	}

}

alt

那么Cookie的有效时长是多少?默认是当前网页,它随着网页的关闭而终止。如果我们将网址复制并关闭浏览器,然后再打开浏览器直接粘贴网址就会发现网页404。

package com.test.servlet.cookie;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class TestLoginServlet
 */
@WebServlet("/cookies/login")
public class TestLoginServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public TestLoginServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("用户登录成功");
		Cookie cookie = new Cookie("user", "admin");
		cookie.setMaxAge(60 * 60 * 24 * 7);  //默认是按秒,所以是最后结果是7天
		response.addCookie(cookie);
		response.getWriter().println("login success");
	}

}

这样就解决了时效性问题。

七、 Session 用户会话

  • Session(用户会话)用于保存与“浏览器窗口”对应的数据
  • 相较于Cookie将资料保存在本地,Session则是将数据保存在服务器,这样既加快速度,也能很好保障安全。
  • Session的数据存储在Tomcat服务器的内存中,具有时效性。Session与浏览器窗口绑定,在没人访问的情况下,默认有效时长30分钟
  • Session通过浏览器Cookie的Sessionld值提取用户数据
package com.test.servlet.session;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

/**
 * Servlet implementation class SessionLoginServlet
 */
@WebServlet("/session/login")
public class SessionLoginServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public SessionLoginServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("用户登录成功");
		//获取到用户会话Session对象
		HttpSession session = request.getSession();
		session.setAttribute("name", "张三");
		request.getRequestDispatcher("/session/index").forward(request, response);
	}

}

package com.test.servlet.session;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

/**
 * Servlet implementation class SessionIndexServlet
 */
@WebServlet("/session/index")
public class SessionIndexServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public SessionIndexServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		HttpSession session = request.getSession();
		String name = (String)session.getAttribute("name");
		response.setContentType("text/html;charset=utf-8");
		response.getWriter().println("这是首页,当前用户为:" + name);
	}

}

alt

Session的原理

alt

八、 ServletContext

  • ServletContext(Servlet上下文对象),是Web应用全局对象
  • 一个Web应用只会创建一个ServletContext对象
  • ServletContext随着Web应用启动而自动创建

例如每个网站下面都会有备案信息
代码:

package com.test.servlet.servletcontext;

import java.io.IOException;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class ServletContextInitServlet
 */
@WebServlet("/servletcontext/init")
public class ServletContextInitServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public ServletContextInitServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		ServletContext context= request.getServletContext();
		context.setAttribute("copyright", "© 2018 test.com 京ICP备 12008569号-37");
		context.setAttribute("title", "这是一个测试样例!");
		response.getWriter().println("init success");
	}

}

package com.test.servlet.servletcontext;

import java.io.IOException;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class ServletContextDefaultServlet
 */
@WebServlet("/servletcontext/default")
public class ServletContextDefaultServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public ServletContextDefaultServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		ServletContext context = (ServletContext)request.getServletContext();
		String copyright = (String)context.getAttribute("copyright");
		String title = (String)context.getAttribute("title");
		response.setContentType("text/html;charset=utf-8");
		response.getWriter().println("<h1>"+ title +"</h1>" + copyright);
	}

}

alt
alt

九、 总结Java Web三大作用域对象

  • HttpServletRequest : 请求对象(生命周期最短)
  • HttpSession : 用户会话对象
  • ServletContext : web应用全局对象(生命周期最长)

十、 Web应用中乱码问题

  • Tomcat默认使用字符集ISO-8859-1,属于西欧字符集
  • 解决乱码的核心思路是将ISO-8859-1转换成UTF-8
  • Servlet中请求与响应都需要设置UTF-8字符集

1. 解决Post请求中文乱码问题

alt
新建一个html

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
	<form action="/servlet_advanced/charset/process" method="post">
		姓名:<input name="ename">
		地址:<input name="address">
		<input type="submit" value="提交">
	</form>
</body>
</html>
package com.test.servlet.charset;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class CharsetServlet
 */
@WebServlet("/charset/process")
public class CharsetServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public CharsetServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		// TODO Auto-generated method stub
		response.getWriter().append("Served at: ").append(request.getContextPath());
	}

	/**
	 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String ename = request.getParameter("ename");
		String address = request.getParameter("address");
		System.out.println(ename + ":" + address);
	}

}

浏览器打开:
alt

回到控制台:
alt

改name后:
alt
alt

这样改写太麻烦了,改进:

package com.test.servlet.charset;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class CharsetServlet
 */
@WebServlet("/charset/process")
public class CharsetServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public CharsetServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		// TODO Auto-generated method stub
		response.getWriter().append("Served at: ").append(request.getContextPath());
	}

	/**
	 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//改进,一定要写在第一行,并且该方法只能用于请求体中,也就是只有post可以用,而get不可以。
		request.setCharacterEncoding("utf-8");
		String ename = request.getParameter("ename");
		String address = request.getParameter("address");
		
		//String utf8Ename = new String(ename.getBytes("iso-8859-1"), "utf-8");
		//String utf8address = new String(address.getBytes("iso-8859-1"), "utf-8");
		System.out.println(ename + ":" + address);
	}

}

2. 解决Get请求中文乱码问题

package com.test.servlet.charset;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class CharsetServlet
 */
@WebServlet("/charset/process")
public class CharsetServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public CharsetServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//对于Tomcat8.X版本,默认get请求发送的中文就是UTF-8,因此无需转换
		String ename = request.getParameter("ename");
		String address = request.getParameter("address");
		System.out.println(ename + ":" + address);
	}

	/**
	 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//改进,一定要卸载第一行。
		request.setCharacterEncoding("utf-8");
		String ename = request.getParameter("ename");
		String address = request.getParameter("address");
		
		//String utf8Ename = new String(ename.getBytes("iso-8859-1"), "utf-8");
		//String utf8address = new String(address.getBytes("iso-8859-1"), "utf-8");
		System.out.println(ename + ":" + address);
	}

}

alt
alt

我们发现控制台输出正常,这是因为对于Tomcat8.X版本,默认get请求发送的中文就是UTF-8,因此无需转换。

十一、 web.xml常用配置

  • 修改web应用默认首页
  • Servlet通配符映射即初始化参数
  • 设置404、500等状态码默认页面

1. 修改web应用默认首页

新建index.html

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
	我是默认首页
</body>
</html>

alt

如果向利用url来获取信息,代码:

package com.test.servlet.pattern;

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 PatternServlet extends HttpServlet{

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//查询员工的基本信息
		//获取当前的URL
		String url = request.getRequestURI().toString();
		System.out.println(url);
	}
	
}


<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1" metadata-complete="false">
  <display-name>servlet_advanced</display-name>
  <welcome-file-list>
    <welcome-file>index.html</welcome-file>
    <welcome-file>index.htm</welcome-file>
    <welcome-file>index.jsp</welcome-file>
    <welcome-file>default.html</welcome-file>
    <welcome-file>default.htm</welcome-file>
    <welcome-file>default.jsp</welcome-file>
  </welcome-file-list>
  
  <servlet>
  	<servlet-name>PatternServlet</servlet-name>
  	<servlet-class>com.test.servlet.pattern.PatternServlet</servlet-class>
  </servlet>
  <servlet-mapping>
  	<servlet-name>PatternServlet</servlet-name>
  	<url-pattern>/pattern/*</url-pattern>
  </servlet-mapping>
</web-app>

结果和控制台:
alt
alt

改进:

package com.test.servlet.pattern;

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 PatternServlet extends HttpServlet{

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//查询员工的基本信息
		//获取当前的URL
		String url = request.getRequestURI().toString();
		System.out.println(url);
		//获取最后一次/出现的位置
		String id = url.substring(url.lastIndexOf("/") + 1);
		response.setContentType("text/html;charset=utf-8");
		PrintWriter out = response.getWriter();
		out.println(id);
		if (id.equals("1")) {
			out.println("张三");
		}else if (id.equals("2")) {
			out.println("李四");
		}else {
			out.println("其他员工");
		}
	}
	
}

alt
alt
alt
alt

2. 全局参数的配置

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1" metadata-complete="false">
  <display-name>servlet_advanced</display-name>
  <welcome-file-list>
    <welcome-file>index.html</welcome-file>
    <welcome-file>index.htm</welcome-file>
    <welcome-file>index.jsp</welcome-file>
    <welcome-file>default.html</welcome-file>
    <welcome-file>default.htm</welcome-file>
    <welcome-file>default.jsp</welcome-file>
  </welcome-file-list>
  
  <servlet>
  	<servlet-name>PatternServlet</servlet-name>
  	<servlet-class>com.test.servlet.pattern.PatternServlet</servlet-class>
  </servlet>
  <servlet-mapping>
  	<servlet-name>PatternServlet</servlet-name>
  	<url-pattern>/pattern/*</url-pattern>
  </servlet-mapping>
  
  <!-- 应用程序的全局参数配置 -->
  <context-param>
  	<param-name>copyright</param-name>
  	<param-value>© 2018 test.com 京ICP备 12008569号-37</param-value>
  </context-param>
  <context-param>
  	<param-name>title</param-name>
  	<param-value>这是一个测试样例</param-value>
  </context-param>
  
</web-app>
package com.test.servlet.servletcontext;

import java.io.IOException;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class ServletContextInitServlet
 */
@WebServlet("/servletcontext/init")
public class ServletContextInitServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public ServletContextInitServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		ServletContext context= request.getServletContext();
		String copyright = context.getInitParameter("copyright");
		String title = context.getInitParameter("title");
		context.setAttribute("copyright", copyright);
		context.setAttribute("title", title);
		response.getWriter().println("init success");
	}

}


3. 设置404、500等状态码默认页面

原始报错:alt

这样的报错页面会暴露重要信息,所以我们要对错误页面进行修改,代码:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1" metadata-complete="false">
  <display-name>servlet_advanced</display-name>
  <welcome-file-list>
    <welcome-file>index.html</welcome-file>
    <welcome-file>index.htm</welcome-file>
    <welcome-file>index.jsp</welcome-file>
    <welcome-file>default.html</welcome-file>
    <welcome-file>default.htm</welcome-file>
    <welcome-file>default.jsp</welcome-file>
  </welcome-file-list>
  
  <servlet>
  	<servlet-name>PatternServlet</servlet-name>
  	<servlet-class>com.test.servlet.pattern.PatternServlet</servlet-class>
  </servlet>
  <servlet-mapping>
  	<servlet-name>PatternServlet</servlet-name>
  	<url-pattern>/pattern/*</url-pattern>
  </servlet-mapping>
  
  <!-- 应用程序的全局参数配置 -->
  <context-param>
  	<param-name>copyright</param-name>
  	<param-value>© 2018 test.com 京ICP备 12008569号-37</param-value>
  </context-param>
  <context-param>
  	<param-name>title</param-name>
  	<param-value>这是一个测试样例</param-value>
  </context-param>
  
  <!-- 指定错误页面 -->
  <error-page>
  	<error-code>404</error-code>
  	<location>/error/404.html</location>
  </error-page>
    <error-page>
  	<error-code>500</error-code>
  	<location>/error/500.html</location>
  </error-page>
</web-app>
package com.test.servlet.servletcontext;

import java.io.IOException;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class ServletContextInitServlet
 */
@WebServlet("/servletcontext/init")
public class ServletContextInitServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public ServletContextInitServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		ServletContext context= request.getServletContext();
		String copyright = context.getInitParameter("copyright");
		String title = context.getInitParameter("title");
		context.setAttribute("copyright", copyright);
		context.setAttribute("title", title);
		response.getWriter().println("init success");
	}

}

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
	资源不存在
</body>
</html>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
	服务器内部错误,请联系管理员
</body>
</html>

结果:
alt
alt

十二、 JSP九大内置对象

代码含义
request请求对象 - HttpServletRequest
response响应对象 - HttpServletResponse
session用户对象 - HttpSession
application应用全局对象 - ServletContext
out输出对象 - PrintWriter
page当前页面对象 - this
pageContext页面上下文对象 - PageContext
config应用配置对象 - ServletConfig
exception应用异常对象 - Throwable

例子:

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
	<%
		String url = request.getRequestURI().toString();
	    response.getWriter().println(url);
	%>
	<%
		out.println("<br>AABCC");
		session.setAttribute("user", "张三");
		out.println((String)session.getAttribute("user"));
	%>
	<%
		String cp = application.getInitParameter("copyright");
		out.println("<hr/>");
		out.println(cp);
		pageContext.getRequest();
		pageContext.getResponse();
		pageContext.getSession();
		pageContext.getServletContext();
	%>
	
</body>
</html>

也可以把错误状态编写成JSP形式:

<%@ page contentType="text/html;charset=utf-8" isErrorPage="true"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
	服务器内部错误,请联系管理员,错误信息如下:
	<%
		String msg = exception.getMessage();
		out.print("<br>" + msg)
	%>
</body>
</html>

十三、 Java Web打包与发布

  • Java Web应用采用war包进行发布
  • 发布路径为:{TOMCAT_HOME}/webapps
  • Eclipse支持war包

导出war包:
alt
alt
alt
alt

发布:

alt
alt
alt
alt
alt
alt
这样就可以不用打开eclipse运行能打开项目,但是地址栏的格式很明显不符合我们平时使用习惯,现在我们优化一下:
先去除8080:
alt
alt
alt
alt

接下来去除上下文路径:
alt
alt

alt

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值