servlet & servlet的配置
servlet
public class BMIServlet extends HttpServlet {
@Override
protected void service(HttpServletRequest req,
HttpServletResponse resp) throws
ServletException, IOException {
// 1. 设置编码
resp.setContentType("text/html;charset=utf-8");
req.setCharacterEncoding("utf-8");
// 2. 获取参数: -- url:
// http://localhost:8080/bmi?tz=60&sg=1.7
// ? key=value & key1+value1 , &用于分隔参数
String tz = req.getParameter("tz");
String sg = req.getParameter("sg");
// 3. 处理数据
double tz1 = Double.valueOf(tz);
double sg1 = Double.valueOf(sg);
double bmi = tz1 / (sg1 * sg1);
// 4. 响应结果
PrintWriter writer = resp.getWriter();
String str = "";
if(bmi < 18){
str = "太瘦了";
}else if(bmi < 24){
str="标准身材";
}else if(bmi < 28){
str="超重了";
}else {
str="肥胖状态。";
}
writer.println("你的bmi是:" + bmi + "\n");
writer.println("<b style='color:red'>"+str+"</b>");
}}
web.xml中对servlet配置
<servlet>
<servlet-name>bmi</servlet-name>
<servlet-class>action.BMIServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>bmi</servlet-name>
<url-pattern>/bmi</url-pattern>
</servlet-mapping>
html界面
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<!-- 绝对路径 :/开始的路径都是绝对路径。在这个绝对路径之前,只拼接:
http://localhost:8080/绝对路径
<form action="/bmi" method="get"> --- http://localhost:8080/bmi (错误路径)
相对路径: 不是/开始的路径,都是相对路径。 根据当前路径, 拼接你的相对路径。
<form action="bmi" method="get"> -- 当前路径:
http://localhost:8080/web01/bmi.html
-- 拼接路径:
http://localhost:8080/web01/bmi
-->
<form action="bmi" method="get">
<label>请输入体重:</label>
<input type="text" name="tz">
<br>
<label>请输入身高:</label>
<input type="text" name="sg">
<br>
<input type="submit" value="计算bmi">
</form>
</body>
</html>
访问方式:
先访问html页面, 输入数据:
http://localhost:8080/web01/bmi.html
然后通过表单提交访问: http://localhost:8080/web01/bmi?tz=60&sg=1.7
接收前端提交的数据
request.getParameter(key) , 获取请求参数。getParameter(key) 的返回值是String , 使用的时候,需要注意数据类型的转换问题。
如果前端没有传入某个参数, 使用getParameter(key) ,那么返回值是null.
响应结果
通过response对象的 getWriter()方法,得到输出流
通过输出流,输出字符串内容,作为响应结果
设置响应结果的类型和字符编码方式:
response.setContentType("text/html;charset=utf-8");
1. text/html , 这个是浏览器能解析的html格式
2. application/json, 这个是浏览器能解析的json格式(后面会使用)
3. 如果格式写错,浏览器不能解析,就会提示你下载。
比如 test/html, 就是浏览器不认识的格式,就会提示下载这个响应结果
http协议
1.通信方式
建立连接
发送请求(请求数据包)
发送响应(响应数据包)
断开连接
2.数据包格式
请求数据包
响应数据包
3.请求方式
get
请求参数在url地址后显示
数据量比较小
不安全
"get请求:浏览器地址栏直接访问,②form的method设置为get,③超链接,④异步请求的是,设置为get.
2.post
数据放在消息体中的
数据量大
相对安全
支持文件上传
" put
web.xml配置
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
version="4.0">
<servlet>
<servlet-name>urlpatten</servlet-name>
<servlet-class>ios.servlet.UrlPattenServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>urlpatten</servlet-name>
<!-- 测试地址是否符合要求,静态资源是否被拦截
-当浏览器发送请求时,tomcat通过web.xml文件,优先访问servlet,如果没有servlet,就找静态资源,如果找不到就响应404
-tomcat优先精确匹配,如果精确匹配失败,就模糊匹配,再失败就找静态资源,都没有就404
-web.xml中配置servlet的地址,尽量避免特殊后缀名,比如jsp,hmtl,js,css
1./ , 模糊匹配,除了jsp之外其他的都会被servlet匹配到
2./* 模糊匹配 所以地址都会被匹配<url-pattern>/*</url-pattern>
3.*.xxx 按后缀名匹配
4./xx 精确地址
5./xx.yy
6.*.xx
-->
<url-pattern>*.do</url-pattern>
</servlet-mapping>
</web-app>
servlet生命周期
![](https://i-blog.csdnimg.cn/blog_migrate/519b9f011050f1da7bd2f695b4ca8aa1.png)
public LifeServlet(){
System.out.println("构造函数被执行");
}
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("业务方法");
}
@Override
public void init() throws ServletException {
System.out.println("初始化");
}
@Override
public void destroy() {
System.out.println("销毁方法");
}
容器启动的时候,或者第一次访问servlet的时候会自动调用init()方法,一个生命周期只执行一次
<servlet>
<servlet-name>life</servlet-name>
<servlet-class>ios.servlet.LifeServlet</servlet-class>
<!-- -->
<load-on-startup>1</load-on-startup>
</servlet>
jsp的使用
jsp是sun公司制定的一种用于服务端的动态页面技术规范,也是一种组件,依赖于tomcat进行运行
jsp不需要在web.xml中配置,直接通过路径和文件名进行访问
jsp是一种运行在服务端的页面,里面可以嵌入一些Java代码和HTML,通过tomcat解析,输出为HTML页面
servlet:数据处理和数据展示(拼HTML标签)
servlet+jsp:servlet处理数据,jsp数据展示
servlet做展示数据的时候,不方便
jsp:让数据的处理和展示进行解耦
.1第一个jsp页面
jsp文件扩展名是.jsp
page指令:指定页面的类型和页面的编码方式(一般在第一行)
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<%
for(int i=0;i<100;i++){
%>
<p style="color: red">记住</p>
<%
}
%>
</body>
</html>
.2.jsp的使用
jsp页面写Java代码
<%for(int i=0;i<100;i++){%>
记住
<% }%>
输出
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>语法规则</title>
</head>
<body>
<%
//Java代码
String str="Rone";
%>
<p style="color: bisque"><%=str%>
<%
str="Darling";
out.print(str);
%>
</p>
</body>
</html>
jsp导入Java类
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
jsp运行
jsp的本质就是servlet
第一次访问一个jsp页面的时候,会将页面转换为一个servlet类
HTML,js,css这种内容就是用输出语句直接拼接
转发和重定向
if(aBoolean){
//删除成功后,重定向到list.do
resp.sendRedirect("list.do");
}else{
mess="error";
req.setAttribute("msg",mess);
RequestDispatcherdispatcher=req.getRequestDispatcher("./jsp/info.jsp");
dispatcher.forward(req,resp);
}
转发
一个请求完成部分功能,希望剩下的功能由另一个请求完成
一般使用servlet完成数据处理,转发到jsp页面,实现数据的展示
转发可以通过request完成,把数据转发给另一个请求
重定向
路径的写法
资源文件的路径(js,css.图片),表单提交的路径,超链接。重定向路径,建议使用绝对路径
转发的路径建议使用相对路径
servlet的绝对路径:/application context/servlet.path
jsp,html的绝对路径:/application context/webapp/*
各种资源文件都是保存在webapp中
相对路径的代码
../ 退出当前目录到上一级目录,然后拼接路径
./表示当前目录
绝对路径的代码
/web04/list.do----属于硬编码不方便维护
String appContext=request.getContextPatg();//获取路径
状态管理
**状态(数据),管理(数据存储):浏览器和服务器的多次交互作为一个整体,这个过程中有一些需要使用的数据,这些数据(状态)需要保存起来,用于表示某种状态
客户端状态管理:cookie技术,把数据存储到浏览器中,就是客户端的状态管理
cookie的使用过程
Cookieusername=newCookie("username", uname);
Cookiepassword=newCookie("password", upwd);
resp.addCookie(username);
resp.addCookie(password);
浏览器保存了响应结果,需要cookie对象,每个cookie和自己的请求的域名一致
浏览器每次给服务器发送请求的时候,会将请求对应域名中保存的cookie数据,一起发送到服务器
服务器通过request获取cookie的对象数据,根据cookie的name,找到value值
cookie的有效期
username.setMaxAge(60*60*24);
password.setMaxAge(60*60*24);
setMaxAge(正数)--当前时间加上数值大小的秒数
setMaxAge(0)--立即失效
setMaxAge() setMaxAge(负数)--会话期间有效,浏览器关闭cookie失效
会话期间:浏览器第一次访问某个服务器,到浏览器关闭期间,称为一个会话
cookie的路径问题
子路径下的可以找到父路径中的cookie
cookie的特点
用户可以删除cookie
用户可以禁止使用cookie
存储小于4k的内容
cookie的个数不能超过300个
只能存储字符串
cookie不安全
Filter的生命周期
public LifeFilter(){
System.out.println("构造函数");
}
@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
System.out.println("dofilter");
filterChain.doFilter(servletRequest,servletResponse);
}
@Override
public void init(FilterConfig filterConfig) throws ServletException {
System.out.println("init");
}
@Override
public void destroy() {
System.out.println("destory");
}
ServletContext的使用
应用程序执行期间都是同一个ServletContext对象,可以在请求中,获取到该对象,操作该对象的数据
//容器程序运行时都有效,可以共享数据,容器停止运行,servletContext失效
ServletContext servletContext = request.getServletContext();
servletContext.setAttribute("total",1);
servlet中数据可以存储的区域
servlet的service方法中的变量
request对象:可以通过转发的方式,把数据转到其它请求中
session对象:可以让一个用户在会话期间,直接使用session中的数据
servletcontext对象:可以让所有的请求在容器运行期间,直接使用servletcontext对象的数据
jsp内置对象
![](https://i-blog.csdnimg.cn/blog_migrate/105ddde1b63ea26e7374805e47196010.png)
EL表达式的使用
--expression language
el表达式主要用于替换<%=%>输出语句
在jsp页面中,可以直接通过el表达式,获取到存储在浏览器的数据
语法规则
${对象}
${对象.属性名}
对象符合java.bean的规范(描述类的属性私有化,提供公开的get/set方法)
${对象.属性名},本质是调用属性名的get方法
el表达式的查找数据方式
<%
pageContext.setAttribute("computer","pc");
request.setAttribute("computer","rs");
session.setAttribute("computer","ss");
ServletContext servletContext = config.getServletContext();
%>
${computer}//指定最小的域开始查找
pageContext:${pageScope.computer}
request:${requestScope.computer}
el表达式的输出结果
如果有这个key,输出时空字符串
如果有这个key,但是key对应的value值时null,输出也是空字符串
其他情况输出的是对应的value值
jstl:jsp标签库
jstl标签,用于替换jsp页面上的<%java代码%>
jsp页面上,如果有太多的java代码,对于jsp页面的修改,维护,前端人员都不友好。
jstl使用
导入jstl的jar包
在jsp页面上,使用taglib指令 ,把想用的标签,导入到jsp页面上,让jsp支持标签的使用
taglib : jsp的导入标签库的指令
prefix : 前缀, 给标签添加上前缀之后,可以和其他的重名标签进行区分。
uri: 标签的访问地址
常用的标签
c:if --- if
c:choose .... if...else
c:forEach .... 循环
${cookie.cookieName.value}
<h3>
根据cookie的名字找value
</h3>
<h3>jsessionid: ${cookie.JSESSIONID.value}</h3>
${pageContext.request.contextPath}
替换掉: <%=request.getContextPath()%>
<!-- https://mvnrepository.com/artifact/javax.servlet.jsp.jstl/jstl -->
<dependency>
<groupId>javax.servlet.jsp.jstl</groupId>
<artifactId>jstl-api</artifactId>
<version>1.2</version>
</dependency>
<!-- https://mvnrepository.com/artifact/taglibs/standard -->
<dependency>
<groupId>taglibs</groupId>
<artifactId>standard</artifactId>
<version>1.1.2</version>
</dependency>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ page import="entity.User" %>
<%@ page import="java.util.List" %>
<%@ page import="entity.BookInfo" %>6.jsp的include指令
<%@ page import="java.util.ArrayList" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
<title>jsp的标签库</title>
</head>
<body>
<%
int age = 19 ; // 判断是否是成年人
int sex = 0 ; // 0 转为女生, 1转为男生, 其他都提示性别错。
List<BookInfo> bs = new ArrayList<>();
BookInfo b1 = new BookInfo() ;
b1.setBookName("one book");
b1.setBookNum(20);
bs.add(b1);
BookInfo b2 = new BookInfo() ;
b2.setBookName("two book");
b2.setBookNum(30);
bs.add(b2);
bs.add(new BookInfo());
bs.add(null);
request.setAttribute("age" ,age);
request.setAttribute("sex" ,sex);
request.setAttribute("bs" ,bs);
%>
<h1>c:if</h1>
<c:if test="${age > 18}">
成年人
</c:if>
<h1>c:choose</h1>
<c:choose>
<c:when test="${sex == 0}">
女生
</c:when>
<c:when test="${sex == 1}">
男生
</c:when>
<c:otherwise>
性别错误
</c:otherwise>
</c:choose>
<h3>c:forEach</h3>
<c:forEach items="${bs}" var="book" varStatus="status">
<p>
${status.index + 1} ,
<c:if test="${!empty book}">
书名 : ${book.bookName } , 数量 : ${book.bookNum}
</c:if>
</p>
</c:forEach>
</body>
</html>
个人总结
这一个阶段的知识也很多,编写的代码量也多,每天练习着所学的内容,虽然过程比较困难,但是编写代码的能力得到了提高,编写代码的逻辑也更加清楚了。