summarize
session就是专门存服务器的 一个客户端一个区域,Http一共三个域,session能存中文,cookie不能存中文
学习session 主要考虑三个问题 :1 怎样获得 2.怎样存取 session对象(内存区域) 3.session对象生命周期
客户端端不同 JSESSIONID就不同,一个客户端只能存在一个session,清理了缓存后,JSESSIONID会从新导入
创建和访问session的顺序是 先设置 在获取,当关闭客户端后,在访问,就获取不到了,显示空指针
session持久化:跟Cookie一样:从新建一个设置时间的session头 覆盖原来的session
JSP:它本身就是一个Servlet。第一行
jsp有三大指令:① page(最常用) ② include(一个页面包含另一个页面) ③ taglib 搭配jstl标签使用
language:声明jsp只能嵌套 java语言。contenType:解决response中文乱码,pageEncoding:当前jsp页面的中文乱码。属性session:默认true
原理图
1.获得Session对象
HttpSession session = request.getSession();
此方法会获得专属于当前会话的Session对象,如果服务器端没有该会话的Session 对象会创建一个新的Session返回,如果已经有了属于该会话的Session直接将已有的Session返回(实质就是根据JSESSIONID判断该客户端是否在服务器上已经存在 session了)
2.向session存取数据(session也是一个域对象)
三个方法:
session.setAttribute(String name,Object obj);
session.getAttribute(String name);
session.removeAttribute(String name);
package com.oracle.demo01;
//创建Session向里面存数据
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
public class SessionServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// 获取Session对象
HttpSession session=request.getSession();
// 向session域中存储数据
session.setAttribute("goods","奶瓶");
// 获取JSESSIONID
String id=session.getId();
// 创建Cookie
Cookie cookie=new Cookie("JSESSIONID",id);
cookie.setPath("/WEB08");
cookie.setMaxAge(60);//设置持久化时间
// 发送Cookie
response.addCookie(cookie);
response.getWriter().write("JSESSIONID:"+id);
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
}
---------------------------------------------
package com.oracle.demo01;
//获取Session对象的内容
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
public class Servlet02 extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// 获取Session对象
HttpSession session=request.getSession();//这里获取的是内存里的session
// 获取session中的内容 这里getattribute得到obj 需要向下转型(强转)
String goods=(String)session.getAttribute("goods");
// 解决乱码
response.setContentType("text/html;charset=utf-8");
response.getWriter().write(goods);
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
}
获取session内容的原理是,先打开已经设置好的session,然后在获取,当客户端关闭后,session的值就消失,因为
获取的内容已关闭,空指针无法强转 只会显示空指针
3.Session对象的生命周期(面试题/笔试题)
创建:第一次执行request.getSession()时创建
销毁:
1)服务器(非正常)关闭时
2)session过期/失效(默认30分钟)
问题:时间的起算点 从何时开始计算30分钟?
从不操作服务器端的资源开始计时
可以在工程的web.xml中进行配置
<session-config>
<session-timeout>30</session-timeout>
</session-config>
3)手动销毁session
session.invalidate();
设置登录验证码
1 <%@ page language="java" contentType="text/html; charset=UTF-8"
2 pageEncoding="UTF-8"%>
3 <!DOCTYPE html>
4 <html>
5 <head>
6 <meta name="viewport" content="width=device-width, initial-scale=1">
7 <title>会员登录</title>
8 <link rel="stylesheet" href="css/bootstrap.min.css" type="text/css" />
9 <script src="js/jquery-1.11.3.min.js" type="text/javascript"></script>
10 <script src="js/bootstrap.min.js" type="text/javascript"></script>
11 <!-- 引入自定义css文件 style.css -->
12 <link rel="stylesheet" href="css/style.css" type="text/css" />
13
14 <style>
15 body {
16 margin-top: 20px;
17 margin: 0 auto;
18 }
19
20 .carousel-inner .item img {
21 width: 100%;
22 height: 300px;
23 }
24
25 .container .row div {
26 /* position:relative;
27 float:left; */
28
29 }
30
31 font {
32 color: #666;
33 font-size: 22px;
34 font-weight: normal;
35 padding-right: 17px;
36 }
37 </style>
38 <script type="text/javascript">
39 function change(node){ /* node是 自定义 */
40 node.src="/Shop/CheckImgServlet?time="+new Date().getTime();
41 }
42 </script>
43 </head>
44 <body>
45
46 <!-- 引入header.jsp -->
47 <jsp:include page="/header.jsp"></jsp:include>
48
49
50 <div class="container"
51 style="width: 100%; height: 460px; background: #FF2C4C url('images/loginbg.jpg') no-repeat;">
52 <div class="row">
53 <div class="col-md-7">
54 <!--<img src="./image/login.jpg" width="500" height="330" alt="会员登录" title="会员登录">-->
55 </div>
56
57 <div class="col-md-5">
58 <div
59 style="width: 440px; border: 1px solid #E7E7E7; padding: 20px 0 20px 30px; border-radius: 5px; margin-top: 60px; background: #fff;">
60 <font>会员登录</font>USER LOGIN
61 <!-- <%-- <%=%> --%> 相当于往页面输出代码 -->
62 <div><%=request.getAttribute("info")==null?"":request.getAttribute("info") %></div>
63 <form class="form-horizontal" action="/Shop/LoginServlet" method="post">
64 <div class="form-group">
65 <label for="username" class="col-sm-2 control-label">用户名</label>
66 <div class="col-sm-6">
67 <input type="text" class="form-control" id="username"
68 placeholder="请输入用户名" name="username">
69 </div>
70 </div>
71 <div class="form-group">
72 <label for="inputPassword3" class="col-sm-2 control-label">密码</label>
73 <div class="col-sm-6">
74 <input type="password" class="form-control" id="inputPassword3"
75 placeholder="请输入密码" name="password">
76 </div>
77 </div>
78 <div class="form-group">
79 <label for="inputPassword3" class="col-sm-2 control-label">验证码</label>
80 <div class="col-sm-3">
81 <input type="text" class="form-control" id="inputPassword3"
82 placeholder="请输入验证码" name="checkcode">
83 </div>
84 <div class="col-sm-3">
85 <img src="/Shop/CheckImgServlet" onClick="change(this)"/>
86 </div>
87 </div>
88 <div class="form-group">
89 <div class="col-sm-offset-2 col-sm-10">
90 <div class="checkbox">
91 <label> <input type="checkbox"> 自动登录
92 </label> <label> <input
93 type="checkbox"> 记住用户名
94 </label>
95 </div>
96 </div>
97 </div>
98 <div class="form-group">
99 <div class="col-sm-offset-2 col-sm-10">
100 <input type="submit" width="100" value="登录" name="submit"
101 style="background: url('./images/login.gif') no-repeat scroll 0 0 rgba(0, 0, 0, 0); height: 35px; width: 100px; color: white;">
102 </div>
103 </div>
104 </form>
105 </div>
106 </div>
107 </div>
108 </div>
109
110 <!-- 引入footer.jsp -->
111 <jsp:include page="/footer.jsp"></jsp:include>
112
113 </body>
114 </html>
当输入验证码时, 验证码在 82行 ,起名为 checkcode,产生的验证码放在session域里面,
修改LoginServlet 从13行到38行
1 package com.oracle.web;
2
3 import java.io.IOException;
4 import javax.servlet.ServletException;
5 import javax.servlet.http.HttpServlet;
6 import javax.servlet.http.HttpServletRequest;
7 import javax.servlet.http.HttpServletResponse;
8 import com.oracle.service.UserService;
9
10 public class LoginServlet extends HttpServlet {
11 private UserService userService=new UserService();
12 public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
13 // 解决中文乱码
14 request.setCharacterEncoding("utf-8");
15 // 获取用户输入的验证码
16 String checkcode=request.getParameter("checkcode");
17 // 获取session域中验证码
18 String code=(String)request.getSession().getAttribute("checkcode_session");
19 // 当两个验证码不匹配的话
20 if(!checkcode.equals(code)){
21 request.setAttribute("info","验证码错误");
22 request.getRequestDispatcher("/login.jsp").forward(request, response);
23 }
24 // 获取用户名
25 String username=request.getParameter("username");
26 // 获取密码
27 String password=request.getParameter("password");
28 // 调用service层的方法
29 int count=userService.login(username,password);
30 // 如果登录成功
31 if(count>0){
32 // 重定向 获取 web应用名称request 设置用get
33 response.sendRedirect(request.getContextPath()+"/index.jsp");//这里跳转首页
34 }else{
35 // 如果登录不成功 因这句话只需要在这次请求中用 so 用request域对象的setAttribute
36 request.setAttribute("info","用户名或密码错误");
37 // 请求转发 这里服务器内部行为不需要写项目名
38 request.getRequestDispatcher("/login.jsp").forward(request, response);//获取转发器
39 }
40 }
41
42 public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
43 doGet(request, response);
44 }
45 }
pm
JSP技术
1.jsp脚本和注释
jsp脚本:
1)<%java代码%> ----- 内部的java代码翻译到service方法的内部 注意: 不+! 不可以定义方法
2)<%=java变量或表达式%>
3)<%!java代码%> ---- 会被翻译成servlet的成员的内容 注意:+!的可定义方法
jsp注释:不同的注释可见范围是不同
1)Html注释:<!--注释内容-->
2)java注释://单行注释 /*多行注释*/
3)jsp注释:<%--注释内容--%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
<!-- 这是HTML注释 -->
<%
//这是java单行注释
/*这是java多行注释*/
int i=100;
System.out.println(i);
%>
<%--这是jsp注释 --%>
<%=i %>
<%! String str="袁一鸣" ;%>
<%=str %>
</body>
</html>
2.jsp运行原理-----jsp本质就是servlet(面试)
jsp在第一次被访问时会被Web容器翻译成servlet,在执行过程:
第一次访问---->helloServlet.jsp---->helloServlet_jsp.java---->编译运行
PS:被翻译后的servlet在Tomcat的work目录中可以找到
3.jsp指令(3个)
jsp的指令是指导jsp翻译和运行的命令,包括三大指令:
1)page指令 --- 属性最多的指令(实际开发中page指令默认)
属性最多的一个指令,根据不同的属性,指导整个页面特性
格式:<%@ page 属性名1= "属性值1" 属性名2= "属性值2" ...%>
常用属性如下:
language:jsp脚本中可以嵌入的语言种类
pageEncoding:当前jsp文件的本身编码---内部可以包含contentType
contentType:response.setContentType(text/html;charset=UTF-8)
session:是否jsp在翻译时自动创建session 默认是true 看代码
<%@page import="java.util.ArrayList"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8" session="false" errorPage="error.jsp"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
<%
int y=1/0;
HttpSession session=request.getSession();
session.setAttribute("goods","naiping");
%>
<%
ArrayList<String> arr=new ArrayList<String>();
%>
</body>
</html>
import:导入java的包 手动(在第一行后面+import属性)或者 alt+/
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8" isErrorPage="true"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
这是一个处理错误页面
</body>
</html>
errorPage:当当前页面出错后跳转到哪个页面
isErrorPage:当前页面是一个处理错误的页面
2)include指令
页面包含(静态包含)指令,可以将一个jsp页面包含到另一个jsp页面中
格式:<%@ include file="被包含的文件地址"%>
在WebContext目录上建三个jsp head.jsp 、body.jsp 、footer.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
这是头部
</body>
</html>
--------------------------------------------------------
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
<%@ include file="header.jsp" %>
这是内容
<%@ include file="footer.jsp" %>
</body>
</html>
----------------------------------------------------------
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
这是尾部
</body>
</html>
3)taglib指令
在jsp页面中引入标签库(jstl标签库、struts2标签库)
格式:<%@ taglib uri="标签库地址" prefix="前缀"%>