session:服务器给每个用户浏览器创建会话对象,就是session对象;一般一个浏览器独占一个session对象
URL(Uniform Resource Locator,统一资源定位符) 是互联网上用于标识和定位资源(如网页、图片、文件等)的地址字符串。通俗地说,URL 就是你在浏览器地址栏里输入的网址,它告诉浏览器去哪里找到特定的内容。
1. 会话(Session)的底层机制
-
会话通常由服务端通过 Session ID(存储在浏览器的Cookie中或URL参数)来跟踪用户状态。
-
刷新网页时,浏览器会重新发送之前的请求(包括Cookie或URL中的Session ID),服务端通过这个ID识别同一会话。
结论:如果Session ID未失效,刷新不会创建新会话,而是延续原有会话
2. 可能触发新会话的情况
-
Session过期:若服务端设置了会话超时时间,且刷新时已超时,可能生成新Session ID。
-
手动清除Session:某些网站会在刷新时主动重置会话(如退出登录)。
-
无痕模式/隐私浏览:浏览器可能不持久化Cookie,导致每次刷新被视为新会话(但这类情况较少见)。
-
注意:
-
Session依赖Cookie:默认情况下,
JSESSIONID
通过Cookie传递。如果浏览器禁用Cookie,需通过URL重写(如response.encodeURL()
)保持Session跟踪。
-
浏览器关闭≠Session销毁:除非手动调用
invalidate()
或Session超时,否则Session在服务端仍存在(但浏览器关闭后,Cookie中的JSESSIONID
丢失,导致无法关联原有Session)。
设置cookie禁用:session也会用不了
package com.qc.cookie;
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 SetSession
*/
@WebServlet("/SetSession")
public class SetSession extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public SetSession() {
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//服务端创建并设置Session属性
//doget不需要前端,直接运行就可以
//cookie可以直接new创建,但session一次会话只有一个,不会修改,所以session是读取的
//getSession() 获取jsession对象,如果没有携带session 会创建新的
HttpSession session=request.getSession();
//设置session账号
session.setAttribute("account", "aaaaa");
//设置session密码
session.setAttribute("password", "123");
//session会随着浏览器关闭关闭,不像cookie可以长久保存
//删除值
session.removeAttribute("password");
//设置session的有效期
//哪怕没有到期,只要关掉浏览器,session就会结束,无论有没有在有效期之内;
//session超时失效;服务器关闭;手动销毁session
//销毁session
session.invalidate();//网站退出登录,就可以销毁session
//禁用cookie时,解决方法:
//重写URL,在地址后面拼接上jsession id;通过重定向访问
String newURL=response.encodeRedirectUrl("GetSession");//GetSession是需要访问的对象
response.sendRedirect(newURL);
//关键方法说明
// response.encodeRedirectUrl("GetSession")
// 作用:
// 对目标URL("GetSession")进行重写,如果客户端禁用了 Cookie,则自动在URL后追加 ;jsessionid=xxx。
// 例如:GetSession → GetSession;jsessionid=1A2B3C4D5E6F
// 底层逻辑:
// 检查请求头是否包含 Cookie: JSESSIONID=xxx(即浏览器是否支持 Cookie)。
// 如果没有 Cookie,则将 JSESSIONID 嵌入到 URL 中。
// response.sendRedirect(newURL)
// 作用:
// 发送 302 重定向响应,强制客户端跳转到重写后的 URL(此时 URL 中已包含 jsessionid)。
// 效果:
// 即使浏览器禁用 Cookie,服务端仍能通过 URL 中的 jsessionid 找到对应的 Session。
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
package com.qc.cookie;
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 GetSession
*/
@WebServlet("/GetSession")
public class GetSession extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public GetSession() {
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//服务端获取并操作Session
//获取session对象
HttpSession session=request.getSession();
System.out.println(session.getAttribute("account"));
System.out.println(session.getAttribute("password"));
System.out.println(session.getId());
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
请求转发/重定向:服务端的跳转方式
请求转发---->服务器行为,当客户端请求到达后,服务器进行转发,此时会将请求对象进行保存,地址栏中的URL地址不会发生改变,得到响应后,服务器将请求发送给客户端;客户端只发起一次请求;
重定向---->由服务器指导的客户端行为;客户端发起第一个请求,被服务器接收处理后给客户端一个新的响应(一个新的地址)客户端接收到响应后,根据发来的地址再次发起请求,服务器接收处理请求,重定向完成;客户端发起两次请求
package com.qc.cookie;
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 S01
*/
@WebServlet("/S01")
public class S01 extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public S01() {
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("S01");
String account =request.getParameter("account");
String password=request.getParameter("password");
System.out.println("S01 account:"+account);
System.out.println("S01 password:"+password);//携带参数可以直接在URL中追加
//1.请求转发
//把当前的请求转发到S02里:会打印S01和S02
//只有一个请求发出,也可以跳转student.html页面
//如果跳转的是Servlet,数据在request域里共享,S01和S02都有account和password的参数
//404表示资源没找到 只能跳转当前网站内的资源
request.getRequestDispatcher("S02").forward(request, response);
//WEB-INF是只针对后端访问,屏蔽了前端的访问路径;请求转发可以访问WEB-INF(重定向不可以)
//2.重定向
response.sendRedirect("https://www.baidu.com/");
//有两个请求发出,地址栏发生改变
//数据在request域中不共享
//重定向可以跳转到任意资源
//不可以访问WEB-INF里的资源
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
package com.qc.cookie;
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 S02
*/
@WebServlet("/S02")
public class S02 extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public S02() {
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("S02");
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}