Servlet概述
Servlet是由SUN公司提供的动态web资源开发技术, 本质上是一段java程序, 这段java程序无法独立运行, 必须放在Servlet容器(比如: tomcat服务器)中, 由容器调用才可以执行!
[toc]
-
简单开发一个Servlet程序
1.开发步骤
(1).写一个类,实现一个Servlet接口,并添加未实现 的方法
(2).将编译后类,放在WEB应用中,并在WEB应用web.xml文件中配置Servlet对外访问的虚拟路径,将WEB应用部署到虚拟主机中即可
2.开发过程
(1)需求
浏览器向服务器发送一个请求, 访问FirstServlet, FirstServlet将表示当前时间的字符串发送浏览器
(2)创建一个FirstServlet.java文件
(3)编写FirstServlet类
- 实现Servlet接口(或继承Servlet接口的子类),并添加未实现的方法(java_ee_api文档)
- 实现Servlet中提供的处理请求方法service方法, 将表示当前时间的字符串响应给浏览器
- 添加servlet类的包路径和导入依赖包
package com.zn.servlet;
import java.io.*;
import java.util.*;
import javax.servlet.*;
public class FirstServlet extends GenericServlet{
public void service(ServletRequest req, ServletResponse res)
throws ServletException, java.io.IOException{
String datastr = new Date().toLocaleString();;
res.getWriter().write(datastr);
}
}
(4)编译FirstServlet类
在cmd窗口通过命令编译出现报错信息:
E:\>javac FirstServlet.java
FirstServlet.java:4: 错误: 程序包javax.servlet不存在
import javax.servlet.*;
^
FirstServlet.java:6: 错误: 找不到符号
public class FirstServlet extends GenericServlet{
^
原因是 javax.servlet这个包不存在, 所有下面出现了很多找不到符号错误.
在tomcat服务器的lib目录下有servlet的jar包, 可以设置包路径:
设置包路径
E:\>set classpath=...\apache-tomcat-7.0.53\lib\servlet-api.jar
再次编译
/*带包编译:
进入到FirstServlet.java所在路径
命令: javac -d . FirstServlet.java
其中: -d是带包编译
点(.)表示编译后的class存放在当前目录下*/
E:\>javac -d . FirstServlet.java
(5)将FirstServlet类放在WEB应用中, 并在web.xml文件中配置Servlet对外访问的虚拟路径
- 将编译好的class文件(包括包路径)放在web应用的classes目录下
- 在WEB应用的web.xml文件中配置servlet对外访问的虚拟路径:
<?xml version="1.0" encoding="ISO-8859-1"?>
<web-app xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
version="3.0"
metadata-complete="true">
<welcome-file-list>
<welcome-file>login.html</welcome-file>
</welcome-file-list>
<!-- servlet settings -->
<servlet>
<servlet-name>FirstServlet</servlet-name>
<servlet-class>com.zn.servlet.FirstServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>FirstServlet</servlet-name>
<url-pattern>/FirstServlet</url-pattern>
</servlet-mapping>
</web-app>
(7)将WEB应用部署到虚拟主机中, 启动服务器, 通过浏览器访问FirstServlet
-
Servlet继承结构
Servlet接口 – 通用的Servlet接口,提供了一个Servlet应该具有的功能
|
|-- GenericServlet类, 实现了Servlet接口
并实现了其中的大部分的方法,但是service方法没有实现,
|
|-- HttpServlet类,实现了service方法
在service方法中, 判断请求方式
根据不同的请求方式xxx调用不同doXxx
|
|-- XxxServlet类, 在开发中,
继承HttpServlet,
并覆盖doGet和doPost方法,
来处理GET请求和POST请求
-
Servlet调用过程
开发一个Servlet, 放在WEB应用中, 并将WEB应用部署在服务器中, 启动服务器, 通过浏览器访问Servlet, 可以访问到Servlet处理的结果, 这个Servlet是如何被调用的, Servlet又是如何执行的?
Servlet调用过程.png
1.Servlet生命周期
Servlet在第一次被访问时创建Servlet实例, 创建之后服务器会立即调用init方法进行初始化的操作
创建之后, Servlet实例会一直驻留在服务器的内存中, 为后续的请求服务. 只要有请求来访问这个Servlet, 服务器就会调用service方法来处理请求, 直到服务器关闭, 或者WEB应用被移出容器
随着WEB应用的销毁, Servlet实例也会跟着销毁, 在销毁之前服务器会调用destroy方法进行善后的处理
-
Servlet开发细节
1.Servlet虚拟路径的配置
Servlet在web.xml文件中虚拟路径的配置方式可以有两种方式:
(1) 直接写一个路径
后期需要通过 /FirstServlet这个路径来访问该Servlet
<!-- servlet settings -->
<servlet>
<servlet-name>FirstServlet</servlet-name>
<servlet-class>com.zn.servlet.FirstServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>FirstServlet</servlet-name>
<url-pattern>/FirstServlet</url-pattern>
</servlet-mapping>
(2) 还可以使用星号(*)匹配符来配置一个路径,配置的方式有两中:
- 以斜杠(/)开头,以斜杠星(/*)结尾
/* , /a/* ...
- 以星点后缀(*.后缀)的形式
*.html , *.abc, *do...
使用星号匹配符可以使得路径的访问变得更加灵活, 但是也可能会导致一个url会被多个mapping所匹配。路径的优先级规则是什么?
(1)哪一个更接近(更精准、更像)哪一个起作用
(2)*.后缀的优先级永远最低.
-
Request
代表HTTP请求的对象。浏览器向服务器发送一个请求,服务器在调用Servlet的service方法处理请求之前,会创建代表Http请求的request对象,将所有的请求信息封装在request对象中。
1.Request的继承结构
ServletRequest -通用的Request接口,提供一个Request对象应该具有的功能
|
|-- HttpServletRequest接口 -
继承了ServletRequest接口,
在父接口的基础上,
HttpServletRequest增加了一些和Http协议相关的方法
2.Request对象提供的功能
(1)获取客户端基本信息、获取请求头信息
/** Request获取客户机的基本信息、获取请求头信息
* @author: zn
* @time: 2018年8月16日,上午10:13:20
*/
public class RequestDemo1 extends HttpServlet {
private static final long serialVersionUID = 1L;
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//1.getRemoteAddr() -- 获取ip地址
String ip = request.getRemoteAddr();
System.out.println("ip:"+ip);
//2.getContxtPath() --获取web应用虚拟路径
String path = request.getContextPath();
System.out.println("path:"+path);
//3.getHader() --获取请求头信息
String host = request.getHeader("host");
System.out.println("host:"+host);
}
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
(2)获取请求参数
header 1 | header 2 |
---|---|
getParameter(String name) | 通过请求参数的名字获取对应的参数值 |
getParameterValues(String name) | |
getParameterMap() | |
getParameterNames() |
请求参数乱码问题
在通过request对象获取请求参数时, 如果参数中有中文数据, 在获取时就会出现乱码, 其原因是由于浏览器发送参数时(编码时)使用的码表 和 服务器在结束数据时(解码时)使用的码表不一致造成的.
请求参数乱码
解决方案:让编码时使用的码表和解码时使用的码表保持一致即可
- 手动编解码解决乱码,通用,适应POST和GET
(1)根据获取的乱码字符串,反向编码得回正确的二进制数据(iso8859-1)
(2) 将二进制数组查询utf-8码表转成字符串, 得回正确的数据
- 如果请求方式是POST,可以通过request提供的方法解决
(1)request.setCharacterEncoding(“utf-8”);//这行代码是通知服务器使用utf-8来接收请求
(2)必须放在任何获取参数代码之前,否则无法生效
(3)GET提交的参数在请求行中的请求资源路径后面拼接着, 不在请求实体内容中,所有这行代码对GET提交产生的乱码不会起作用!
/** 通过Request获取请求参数
* @author: zn
* @time: 2018年8月16日,上午10:33:44
*/
public class RequestDemo2 extends HttpServlet {
private static final long serialVersionUID = 1L;
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
/**
* 通知服务器使用UTF-8接收请求实体内容中的数据,对POST提交的乱码起作用
*/
request.setCharacterEncoding("utf-8");
//获取用户名
String username = request.getParameter("username");
//获取用户昵称
String nickname = request.getParameter("nickname");
System.out.println("username:"+username+"\nnickname:"+nickname);
//获取爱好
String[] likes = request.getParameterValues("like");
System.out.println("likes"+Arrays.toString(likes));
//================= GET乱码解决 =======================//
byte[] bytes = username.getBytes("iso8859-1");
username = new String(bytes,"utf-8");
System.out.println("GET-> username:"+username);
}
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
![请求转发](https://img.haomeiwen.com/i4495072/928577dda76eb86e.jpg?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)
(3)实现请求转发
-
请求重定向:实现资源的跳转
-
请求转发:实现资源的跳转,并且是服务器
网友评论