一、请求:(request)
组成部分:请求行 请求头 请求体。
请求行:请求信息的第一行,格式:请求方式 访问的资源 协议/版本
例如:GET /day0801/1.html HTTP/1.1
请求方式:get和post
get会把参数放在url的后面,post不会
get参数大小有限制,post请求却没有限制
get请求没有请求体;post请求有请求体 请求参数放在请求体中
请求头:请求信息的第二行到空行结束,格式:key/value (value可以是多个值)
常见的请求头:Accept: text/html,image/bmp --支持数据类型,例如text/html、text/css、text/javascript,格式为:大类型/小类型,称之为mime类型。
Accept-Charset:ISO-8859-1 --字符集,不支持中文
Accept-Encoding:gzip --支持压缩
Accept-Language:zh-cn --语言环境
Host: www.itcast.cn:80 --访问主机
If-Modified-Since:Tue,11 Jul 2000 18:23:51 GMT --缓存文件的最后修改时间
Referer:http://www.itcast.com/index.jsp --来自哪个页面,用于防盗链
User-Agent:Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 5.0) MSIE微软IE浏览器
Cookie:
Connection:Keep-Alive --链接状态
请求体:空行以下的内容,只有post才有请求体
二、响应:(response)
组成部分:响应行 响应头 响应体
响应行:响应信息的第一行,格式:协议/版本 状态码 状态码说明
例如:HTTP/1.1 200 OK
状态码:
200 正常响应成功
302 重定向,跳转
304 读缓存
404 用户操作资源不存在
500 服务器内部异常
响应头:从响应信息的第二行到空行结束,格式:key/value(value可以是多个值)
常见的头:
Location:http://www.it315.org/index.jsp --跳转方向 和302一起使用的
Server:apache tomcat --服务器型号,不安全,有的已经取消掉
Content-Encoding: gzip --数据压缩
Content-Length: 80 --数据长度
Content-Language: zh-cn --语言环境
Content-Type: text/html; charset=GB2312 --数据类型
Last-Modified: Tue, 11 Jul 2000 18:23:51 GMT --最后修改时间
Refresh:1;url=http://www.it315.org --定时刷新
Content-Disposition: attachment; filename=aaa.zip --下载
Set-Cookie:SS=Q0=5Lb_nQ; path=/search
Expires: -1 --缓存
Cache-Control: no-cache --缓存
Pragma: no-cache --缓存
Connection: Keep-Alive --连接
响应体:空行以下的内容
三、servlet
动态的web开发技术,本质就是一个类,运行在服务器端的一个java小程序,处理业务逻辑(处理代码),一般没有具体的方法,都是调用其他,生成动态web内容。
1.编写一个servlet步骤
1.编写一个类
a.继承HttpServlet,注意这步之前要先把Tomcat的依赖包加载进来。
b.重写doGet或者doPost方法
request.getParameter("key");
response.getWriter().print("success");
处理响应数据中文乱码:response.setContentType("text/html;charset=utf-8");
2.编写配置文件(web-inf/web.xml)
a.注册servlet,告诉服务器是servlet
b.绑定路径,使类和路径产生关系
3.访问:http://主机:端口号/项目名/路径(在idea中的访问和eclipse中的访问不一样,注意区别。)
2.serlvet总结
servlet的体系结构:
Servlet:接口
|
GenericServlet:抽象类
|
HttpServlet:抽象类
|
自定义servlet
servlet常用方法:
void init(ServletConfig config):初始化
void service(ServletRequest request,ServletResponse response):服务 处理业务逻辑
void destroy():销毁
ServletConfig getServletConfig() :获取当前servlet的配置对象
GenericServlet常用方法:
除了service方法没有显示,其他都实现了
空参的Init() 若我们自己想对servlet进行初始化操作,重写这个init()方法即可
HttpServlet常用方法:
service做了实现,把参数强转,调用了重载的service方法,重载的service方法获取请求的方式,根据请求方式的不同调用相应doXxx()方法。
3.案例
网上商城有一个登录的功能。需求:在页面上输入用户名和密码,提交到服务器上,服务器拿着用户名和密码去数据库中查找有无此用户,若有用户,则提示登录成功;若无此用户,则提示用户名密码不匹配。
1.先有数据库和表
create database day09;
use day09;
create table user(
id int primary key auto_increment,
username varchar(20),
password varchar(20),
email varchar(20),
name varchar(20),
sex varchar(10),
birthday date,
hobby varchar(50)
);
insert into user values (null,'tom','123','tom@126.com','tom','1','1988-01-01',null);
2.创建工程
3.复制页面
修改login.html
给用户名和密码添加name属性
修改表单的action属性
action="http://localhost/day0901/login"
添加method属性
method="post"
4.导入jar包:
驱动、 dbutils、 c3p0
5.导入工具类和配置文件
datasourceUtils(自己编写的生成一个连接的java程序)
c3p0-config.xml(注意修改数据名称)
6.创建servlet(LoginServlet: 路径 /login)
接受用户名和密码
调用service层(UserService)完成登录操作
提示信息
7.UserService
login(username,password)
调用dao
8.dao
通过用户名和密码查询数据库
1.LoginServlet.java
package com.it.dragon;
import com.it.domain.User;
import com.it.service.UserService;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.sql.SQLException;
import java.sql.SQLOutput;
public class LoginServlet extends HttpServlet {
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws IOException {
resp.setContentType("text/html;charset=utf-8");
String username = req.getParameter("username");
String password = req.getParameter("password");
//String username = "tom";
//String password = "123";
User user = null;
try {
user = new UserService().login(username, password);
} catch (SQLException e) {
e.printStackTrace();
}
if (user == null) {
resp.getWriter().print("no such man");
} else {
resp.getWriter().print(" hello my lord");
}
}
}
2.UserService.java
package com.it.service;
import com.it.dao.UserDao;
import com.it.domain.User;
import java.sql.SQLException;
public class UserService {
public User login(String username, String password) throws SQLException {
UserDao dao = new UserDao();
return dao.getUser(username,password);
}
}
3.User.java
package com.it.domain;
public class User {
private int id;
private String username;
private String password;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
4.UserDao.java
package com.it.dao;
import com.it.domain.User;
import com.it.utils.DataSourceUtils;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import java.sql.SQLException;
public class UserDao {
public User getUser(String username, String password) throws SQLException {
QueryRunner qr = new QueryRunner(DataSourceUtils.getDataSource());
//编写sql
String sql="select * from user where username = ? and password = ?";
//执行sql
User user = qr.query(sql, new BeanHandler<>(User.class), username,password);
return user;
}
}
5.DataSourceUtils.java
package com.it.utils;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import javax.sql.DataSource;
import com.mchange.v2.c3p0.ComboPooledDataSource;
public class DataSourceUtils {
private static ComboPooledDataSource ds=new ComboPooledDataSource();
public static DataSource getDataSource(){
return ds;
}
public static Connection getConnection() throws SQLException{
return ds.getConnection();
}
public static void closeResource(Connection conn, Statement st, ResultSet rs) {
closeResultSet(rs);
closeStatement(st);
closeConn(conn);
}
public static void closeConn(Connection conn) {
if (conn != null) {
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
conn = null;
}
}
public static void closeStatement(Statement st) {
if (st != null) {
try {
st.close();
} catch (SQLException e) {
e.printStackTrace();
}
st = null;
}
}
public static void closeResultSet(ResultSet rs) {
if (rs != null) {
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
}
rs = null;
}
}
}
四、servlet生命周期
void init(ServletConfig config):初始化
* 执行者:服务器
* 执行次数:一次
* 执行时机:默认第一次访问的时候
void service(ServletRequest request,ServletResponse response):服务 处理业务逻辑
* 执行者:服务器
* 执行次数:请求一次执行一次
* 执行时机:请求来的时候
void destroy():销毁
* 执行者:服务器
* 执行次数:只执行一次
* 执行时机:当servlet被移除的时候或者服务器正常关闭的时候
serlvet是单实例多线程,默认第一次访问的时候,服务器创建servlet,并调用init实现初始化操作,并调用一次service方法,每当请求来的时候,服务器创建一个线程,调用service方法执行自己的业务逻辑,当serlvet被移除的时候或服务器正常关闭的时候,服务器调用servlet的destroy方法实现销毁操作。
在servlet的web.xml标签有一个子标签 load-on-startup
作用:用来修改servlet的初始化时机
取值:正整数,值越大优先级越低。
当我们的配置文件里面没有指定配置的话,会查找tomcat的web.xml,若请求我们自己的项目处理不了,tomcat的默认的servlet会帮我们处理信息,例如跳出的404窗口等。
五、url-pattern
方式1:完全匹配 必须以"/"开始 例如: /hello /a/b/c
方式2:目录匹配 必须"/"开始 以"*"结束 例如: /a/* /*
方式3:后缀名匹配 以"*"开始 以字符结尾 例如: *.jsp *.do *.action
优先级:完全匹配>目录匹配>后缀名匹配
练习:
有如下的一些映射关系:
Servlet1 映射到 /abc/*
Servlet2 映射到 /*
Servlet3 映射到 /abc
Servlet4 映射到 *.do
问题:
当请求URL为“/abc/a.html”,“/abc/*”和“/*”都匹配,哪个servlet响应
Servlet引擎将调用Servlet1。
当请求URL为“/abc”时,“/*”和“/abc”都匹配,哪个servlet响应
Servlet引擎将调用Servlet3。
当请求URL为“/abc/a.do”时,“/abc/*”和“*.do”都匹配,哪个servlet响应
Servlet引擎将调用Servlet1。
当请求URL为“/a.do”时,“/*”和“*.do”都匹配,哪个servlet响应
Servlet引擎将调用Servlet2.
当请求URL为“/xxx/yyy/a.do”时,“/*”和“*.do”都匹配,哪个servlet响应
Servlet引擎将调用Servlet2。
常见的响应头-refresh
响应头格式:refresh:秒数;url=跳转的路径
设置定时刷新:response.setHeader("refresh","3;url=/day0901/login.htm");
设置响应头:
response.setHeader(String key,String value);设置字符串形式的响应头
response.addHeader(String key,String value);追加响应头,若之前设置设置过这个头,则追加;若没有设置过,则设置。
六、ServletContext
上下文(全局管理者),一个项目的引用,代表了当前项目。当项目启动的时候,服务器为每一个web项目创建一个servletcontext对象,当项目被移除的时候或者服务器关闭的时候servletcontext销毁。作用:获取全局的初始化参数、共享资源(xxxAttribute)、获取文件资源、其他操作。
获取全局管理者:getServletContext()、 getServletConfig().getServletContext()(用不多)。
常用的方法:
1.了解
String getInitParameter(String key):通过名称获取指定的参数值
Enumeration getInitParameterNames() :获取所有的参数名称
在web.xml根标签下有一个 context-param子标签 用来存放初始化参数
<context-param>
<param-name>encoding</param-name>
<param-value>utf-8</param-value>
</context-param>
2.xxxAttribute
setAttribute(String key,Object value);//设置值
Object getAttribute(String key);//获取值
removeAttribute(String key)://移除值
3.String getRealPath(String path):获取文件部署到tomcat上的真实路径(带tomcat路径)
InputStream getResourceAsStream(String path):以流的形式返回一个文件
4.获取文件的mime类型,大类型/小类型:String getMimeType(String 文件名称)
案例:在一个用户登录成功之后,获取之前登录成功总人次,将次数+1.在访问另一个servlet的时候,显示登录成功的总人次。
@Override
public void init() throws ServletException {
ServletContext context = getServletContext();
context.setAttribute("count",0);
}
//在servlet中重写init,然后获取servletcontext对象,设置该变量即可,在用户登录后,再重新获取,然后加1,再写回去。
七、ServletConfig
servletconfig是由服务器创建的,在创建servlet的同时也创建了它,通过servlet的init(ServletConfig config)将config对象,传递给servlet,由servlet的getServletConfig方法获取。
作用:1.获取当前servlet的名称、2.获取当前servlet的初始化参数、3.获取全局管理者
ServletConfig servletConfig = this.getServletConfig();
String servletName = servletConfig.getServletName();
System.out.println(servletName);
String name = servletConfig.getInitParameter("name");
System.out.println(name);
方法:
String getServletName():获取当前servlet的名称(web.xml配置的servlet-name)
String getInitParameter(String key):通过名称获取指定的参数值
Enumeration getInitParameterNames() :获取所有的参数名称
初始化参数是放在 web.xml文件servlet标签下子标签 init-param。
获取文件的路径:
可以通过类加载器获取,无论是java项目还是web项目都可以。文件需要放在src目录下。
类.class.getClassLoader().getResource("2.txt").getPath()