Cookie工作模式(数据存储在客户端)


一、状态管理

学习Cookie和Session之前先了解一下状态管理。

状态管理是将客户端与服务器之间多次交互当做一个整体,并将多次交互之间涉及的数据保存下来,提供给后续的交互进行数据的管理。

状态是当前的数据,管理是在多次交互过程中对数据的存储、修改和删除。

举几个栗子:

  • 洗车卡
    记录洗车的次数,车主每次携带卡片洗车后,由商家修改洗车次数,车主可以携带走记录次数的卡片。(商家并不保存任何数据,客户自己携带需要维护的数据)
  • 理发店
    商家给客户一个卡号,每次客户来理发需要报上卡号,商家就会从系统中找到与此卡号对应的数据,修改后由商家保存。(客户带走的仅是卡号标识)

上面两种模式就是数据的管理,各有利弊。程序中与上面两种模式对应的分别是Cookie和Session。

二、Cookie工作模式

(1)Cookie是什么

Cookie是一种客户端会话技术,将数据保存在客户端。

一小段文本信息随着请求和响应,在客户端和服务器端之间来回传递。根据设定的时间来决定该段文本在客户端保存时长的这种工作模式。

如果服务器创建cookie后,会以uname=value的形式传递到客户端,并保存在客户端

一旦客户端有服务器发回的文本信息,那么当浏览器再次向服务器发起请求时,也会以uname=value这样的形式将文本信息发送到服务器端。

(2)Cookie原理图解

在这里插入图片描述
请求:浏览器发送请求到服务器;②响应:服务器对浏览器给出响应,创建并通过响应头set-Cookie将Cookie发送给浏览器;③保存:浏览器接收到响应后会将Cookie中的数据保存在内存或硬盘上;④携带:当浏览器再次向服务器发送请求时,会通过请求头cookie将Cookie带给服务器。⑤获取:服务器通过自身封住好的API获取这个请求头。

(3)Cookie的特点

  • ①Cookie将数据存储在客户端,只能保存字符串。
  • ②浏览器对单个Cookie大小有限制(4kb左右),对同一个域名下的Cookie总数量也有限制(20个以内)。
  • ③存储在客户端,安全性低。

(4)Cookie的作用

  • ①Cookie一般用于存储少量的不敏感的信息。
  • ②在不登录的情况下,完成服务器对客户端的身份识别。

三、Cookie应用

(1)Cookie操作

创建Cookie

Cookie c = new Cookie(String name,String value);
response.addCookie(c);

查询Cookie

//获取客户端所有Cookie对象
Cookie[] request.getCookies();
//获取一个Cookie对象的名称或值
String Cookie.getName();
String Cookie.getValue();

修改Cookie

Cookie.setValue(String newValue);

设置Cookie的有效路径

//设置当前路径或当前子路径,浏览器才会发送Cookie
Cookie.setPath(String path);

(2)Cookie创建Demo

AddCookieServlet.java

package cookie;
/**
 * 创建Cookie语法:
 * 
 * Cookie c = new Cookie(String name,String value);
 * response.addCookie(c);
 */
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;

public class AddCookieServlet extends HttpServlet {

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {
		//创建Cookie
		Cookie c1 = new Cookie("uname","Hudie");
		Cookie c2 = new Cookie("city","Beijing");//由于没有设置解码,这里先不用中文
		//添加Cookie至Response
		response.addCookie(c1);
		response.addCookie(c2);	
	}
}

打开浏览器的开发者工具中的application,在storage中查看当前的Cookies,
在这里插入图片描述
此时Cookie就保存在了浏览器中。再在Network中查看addCookie。

在这里插入图片描述
第一次访问addCookie时,Request Headers(请求头)中没有任何的文本信息,但在Response Headers(响应头)中出现了Set Cookie的文本信息,这说明了服务器中创建Cookie之后,添加到Response中会直接作为Response Header头返回到浏览器并保存下来。

再次访问addCookie时,可以看到Request Headers(请求头)中多了一个Cookie信息。这个Cookie是之前保存在浏览器中的,直接发送到了服务器端。Response Headers(响应头)同样还会将Cookie信息打印到浏览器中。
在这里插入图片描述
文本信息就这样在客户端和服务器之间来回的传递。如果关闭浏览器再次打开就会发现Cookie消失了,这说明当前Cookie是保存在浏览器内存中的。

(3)Cookie查询Demo

FindCookieServlet.java

package cookie;

/**
 * 查找Cookie语法:
 *  //获取客户端所有Cookie对象
 *	Cookie[] request.getCookies();
 *	//获取一个Cookie对象的名称或值
 *	String Cookie.getName();
 *	String Cookie.getValue();
 */
import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class FindCookieServlet extends HttpServlet {

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		response.setContentType("text/html;charset=utf-8");
		PrintWriter out = response.getWriter();
		
		//查询Cookie
		Cookie[] cookies = request.getCookies();
		if(cookies!=null){
			for (Cookie cookie : cookies) {
				String name = cookie.getName();
				String value = cookie.getValue();
				out.print("name:"+name+"value:"+value);
			}
		}else{
			out.println("没有Cookie信息");
		}
	}
}

先addCookie再findCookie,这样就查询到了Cookie。

在这里插入图片描述

(4)Cookie修改Demo

UpdateCookieServlet.java

package cookie;

/**
 * 修改Cookie语法:
 * 		Cookie.setValue(String newValue);
 */
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;

public class UpdateCookieServlet extends HttpServlet {

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {
		//获得Cookie
		Cookie[] cookies = request.getCookies();
		if(cookies!=null){
			for(Cookie cookie:cookies){
				if(cookie.getName().equals("city")){
					//修改Cookie
					cookie.setValue("Shanghai");
					//一定要保存到response中
					response.addCookie(cookie);
				}
			}
		}
	}
}

查询:
在这里插入图片描述

(5)设置Cookie的有效路径

当客户端向http://localhost:8080/test/file/addCookie.jsp发送请求时创建了Cookie,那么该Cookie的路径就是/test/file。请求/test/file/d.jsp会发送Cookie,请求/test/d.jsp不会发送Cookie。

在AddCookieServlet.java中设置c1的有效路径

package cookie;
/**
 * 创建Cookie语法:
 * 
 * Cookie c = new Cookie(String name,String value);
 * response.addCookie(c);
 */
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;

public class AddCookieServlet extends HttpServlet {

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {
		//创建Cookie
		Cookie c1 = new Cookie("uname","Hudie");
		Cookie c2 = new Cookie("city","Beijing");//由于没有设置解码,这里先不用中文
		//设置Cookie路径
		c1.setPath("/test");
		//添加Cookie至Response
		response.addCookie(c1);
		response.addCookie(c2);	
	}
}

(6)Cookie的本质

关于Cookie其实有一定的限制。Cookie的本质是一小段文本,这个文本只能保存少量的数据。长度一般在4kb左右。只能保存字符串,不能保存复杂的对象数据

四、Cookie的生命周期

默认情况下,Cookie会被浏览器保存在内存中,此时Cookie的声明周期由浏览器决定给,只要不关闭浏览器Cookie就会一直存在。

如果希望关闭浏览器后Cookie仍然存在,则可以通过设置过期时间使得Cookie存在硬盘上得以保存更长的时间。

设置Cookie的过期时间使用如下代码:

	void setMaxAge(int seconds);
	seconds > 0 :代表Cookie保存在硬盘上的时长.
	seconds = 0 :立即删除.
	seconds < 0 :缺省值,浏览器会将Cookie保存在内存中.

在addCookieServlet.java中设置c1的过期时间为100秒

package cookie;
/**
 * 创建Cookie语法:
 * 
 * Cookie c = new Cookie(String name,String value);
 * response.addCookie(c);
 */
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;

public class AddCookieServlet extends HttpServlet {

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {
		//创建Cookie
		Cookie c1 = new Cookie("uname","xiaoguo");
		Cookie c2 = new Cookie("city","shanghai");//由于没有设置解码,这里先不用中文
		//设置c1的过期时间
		c1.setMaxAge(100);
		//设置Cookie路径,只有访问此路径或此路径的子路径才会发送	Cookie
		c1.setPath("/test");
		//添加Cookie至Response
		response.addCookie(c1);
		response.addCookie(c2);	
	}
}

在浏览器中查看cookie的生命周期:
在这里插入图片描述

五、Cookie的中文乱码问题

低版本的tomcat需要添加下面的代码:

String encode = URLEncoder.encode("蝴蝶","utf-8");

String value = URLDecoder.decode(cookie.getValue(),"utf-8");
  • 2
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Hudie.

不要打赏!不要打赏!不要打赏!

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值