欢迎大家关注本博,同时欢迎大家评论交流,可以给个赞哦!!!

  谈到Cookie,就得说到会话跟踪技术,在Web发展早期,Cookie是会话跟踪技术的不二选择,拥有统一的实现标准。在基于无状态的HTTP协议进行服务搭建时,如何保持更加安全、简便的保持会话,就成了首要问题,Cookie技术就应运而生了。

  Cookie是由一个键和一个值构成的,由服务器创建,随着服务器响应发送给客户端浏览器。客户端浏览器会把Cookie保存下来,下一次访问服务器时把服务器发送的Cookie再发送给服务器。单独来说Cookie的话,其实属于客户端应用,与之对应的Session属于服务器端应用,两者的交集就是保持会话的基础。

  对于Cookie的内容不做过多的分析,在Cookie源码注释中都进行了标注。

  Cookie

  对于Servlet中Cookie,HttpServletRequest的getCookies提供了Cookie读取的功能,HttpServletResponse的addCookie提供了Cookie写入的功能。

package javax.servlet.http;import java.text.MessageFormat;
import java.util.ResourceBundle;/*** 创建一个Cookie,Servlet发送到Web浏览器,由浏览器保存并稍后发送回服务器的少量信息.* Cookie的值可以唯一地标识客户端,因此Cookie通常用于会话管理.* Cookie有一个名称、一个值和可选属性(如注释、路径和域限定符、最长期限和版本号).* 一些Web浏览器在处理可选属性的方式上存在缺陷,因此要谨慎使用它们来提高servlet的互操作性.* Servlet使用HttpServletResponse.addCookie方法将Cookie发送到浏览器,该方法向HTTP响应头添加字段,以便一次发送一个cookie到浏览器.* 浏览器预计支持每个Web服务器20个cookie,总共300个cookie,并且每个cookie大小限制为4kb.随着客户端浏览器的发展,这一项现在的容量已经大大提供了.* 浏览器通过向HTTP请求头添加字段来将cookies返回给servlet.可以使用HttpServletRequest.getCookies方法从请求中检索Cookies.* 多个cookie可能具有相同的名称,但路径属性不同.* Cookie会影响使用它们的网页的缓存.HTTP1.0不缓存使用此类创建的Cookie的页面.此类不支持用HTTP1.1定义的缓存控件.* 此类同时支持版本0(Netscape的Cookie规范)和版本1(W3C的RFC2109规范)Cookie规范.默认情况下,Cookie是使用版本0创建的,以确保最佳互操作性.*/
public class Cookie implements Cloneable {/*** 错误信息模板位置.*/private static final String LSTRING_FILE = "javax.servlet.http.LocalStrings";/*** 错误信息模板加载.*/private static ResourceBundle lStrings = ResourceBundle.getBundle(LSTRING_FILE);/*** Cookie名称.*/private String name; // NAME= ... "$Name" style is reserved/*** Cookie值.*/private String value; // value of NAME/*** Cookie用处说明.*/private String comment; // ;Comment=VALUE ... describes cookie's use/*** 可以访问该Cookie的域名.*/private String domain; // ;Domain=VALUE ... domain that sees cookie/*** 该Cookie的失效时间.*/private int maxAge = -1; // ;Max-Age=VALUE ... cookies auto-expire/*** 该Cookie的使用路径.*/private String path; // ;Path=VALUE ... URLs that see the cookie/*** 该Cookie是否仅被使用安全协议传输.安全协议有HTTPS、SSL等.*/private boolean secure; // ;Secure ... e.g. use SSL/*** 该Cookie使用的版本号.0表示遵循Netscape的Cookie规范、1表示遵循W3C的RFC2109规范.*/private int version = 0; // ;Version=1 ... means RFC 2109++ style/*** Constructs.初始参数包括name和value.* name:必须遵循RFC 2109规范,只能包含ASCII字母数字字符,不能包含逗号、分号、空格或以$字符开头.创建后无法更改cookie的名称.* value:可以是服务器选择发送的任何内容.* 默认情况下,cookies是根据Netscape cookie规范创建的。可以使用setVersion方法更改版本.* name不允许出现如下情况:*  非Java保留标记,不区分大小写情况下,不等于Commet、Discard、Domain、Expires、Max-Age、Path、Secure、Version,不以$开头.* @param name Cookie名.* @param value Cookie值.*/public Cookie(String name, String value) {if (!isToken(name) || name.equalsIgnoreCase("Comment") // rfc2019|| name.equalsIgnoreCase("Discard") // 2019++|| name.equalsIgnoreCase("Domain") || name.equalsIgnoreCase("Expires") // (old cookies)|| name.equalsIgnoreCase("Max-Age") // rfc2019|| name.equalsIgnoreCase("Path") || name.equalsIgnoreCase("Secure") || name.equalsIgnoreCase("Version")|| name.startsWith("$")) {String errMsg = lStrings.getString("err.cookie_name_is_token");Object[] errArgs = new Object[1];errArgs[0] = name;errMsg = MessageFormat.format(errMsg, errArgs);throw new IllegalArgumentException(errMsg);}this.name = name;this.value = value;}/*** 设置commet.*/public void setComment(String purpose) {comment = purpose;}/*** 获取commet.*/public String getComment() {return comment;}/*** 设置domain.*/public void setDomain(String pattern) {domain = pattern.toLowerCase(); // IE allegedly needs this}/*** 获取domain.*/public String getDomain() {return domain;}/*** 设置maxAge.*/public void setMaxAge(int expiry) {maxAge = expiry;}/*** 获取maxAge.*/public int getMaxAge() {return maxAge;}/*** 设置path.*/public void setPath(String uri) {path = uri;}/*** 获取path.*/public String getPath() {return path;}/*** 设置seure.*/public void setSecure(boolean flag) {secure = flag;}/*** 获取secure.*/public boolean getSecure() {return secure;}/*** 获取name.*/public String getName() {return name;}/*** 设置value.*/public void setValue(String newValue) {value = newValue;}/*** 获取value.*/public String getValue() {return value;}/*** 获取version.*/public int getVersion() {return version;}/*** 设置version.*/public void setVersion(int v) {version = v;}private static final String tspecials = ",; ";/*** 测试字符串,如果该字符串在Java语言中算作保留标记,则返回true.*/private boolean isToken(String value) {int len = value.length();for (int i = 0; i < len; i++) {char c = value.charAt(i);if (c < 0x20 || c >= 0x7f || tspecials.indexOf(c) != -1)return false;}return true;}/*** 重写clone.*/public Object clone() {try {return super.clone();} catch (CloneNotSupportedException e) {throw new RuntimeException(e.getMessage());}}}

  若文中存在错误和不足,欢迎指正!

本博微信公众号“超哥说码”,欢迎大家订阅,公众号正在完善中,会及时将更优质的博文推送于您!

Servlet规范系列 之 Cookie源码分析相关推荐

  1. Laravel核心解读--Cookie源码分析

    Laravel Cookie源码分析 使用Cookie的方法 为了安全起见,Laravel 框架创建的所有 Cookie 都经过加密并使用一个认证码进行签名,这意味着如果客户端修改了它们则需要对其进行 ...

  2. SequoiaDB 系列之六 :源码分析之coord节点

    好久不见. 在上一篇SequoiaDB 系列之五   :源码分析之main函数,有讲述进程开始运行时,会根据自身的角色,来初始化不同的CB(控制块,control block). 在之前的一篇Sequ ...

  3. paho架构_MQTT系列最终章-Paho源码分析(三)-心跳与重连机制

    写在前面 通过之前MQTT系列-Eclipse.Paho源码分析(二)-消息的发送与接收的介绍,相信仔细阅读过的小伙伴已经对Eclipse.Paho内部发送和订阅消息的流程有了一个较为清晰的认识,今天 ...

  4. 【阅读源码系列】ConcurrentHashMap源码分析(JDK1.7和1.8)

    个人学习源码的思路: 使用ctrl+单机进入源码,并阅读源码的官方文档–>大致的了解一下此类的特点和功能 使用ALIT+7查看类中所有方法–>大致的看一下此类的属性和方法 找到重要方法并阅 ...

  5. java tomcat源码_详解Tomcat系列(一)-从源码分析Tomcat的启动

    在整个Tomcat系列文章讲解之前, 我想说的是虽然整个Tomcat体系比较复杂, 但是Tomcat中的代码并不难读, 只要认真花点功夫, 一定能啃下来. 由于篇幅的原因, 很难把Tomcat所有的知 ...

  6. SequoiaDB 系列之五 :源码分析之main函数

    好久好久没有写博客了,因为一直要做各种事,工作上的,生活上的,这一下就是半年. 时光如梭. 这两天回头看了看写的博客,感觉都是贻笑大方. 但是还是想坚持把SequoiaDB系列写完. 初步的打算已经确 ...

  7. java多线程系列:ThreadPoolExecutor源码分析,java基础面试笔试题

    我总结出了很多互联网公司的面试题及答案,并整理成了文档,以及各种学习的进阶学习资料,免费分享给大家. 扫描二维码或搜索下图红色VX号,加VX好友,拉你进[程序员面试学习交流群]免费领取.也欢迎各位一起 ...

  8. 【网络安全】登录问题(一)Session/Cookie源码分析

    从身份验证开始说起. 知 我们在上BBS的时候,有些帖子是有限制的,只有允许身份的人才能观看,那么如果去校验你的身份呢?我们想到了一个办法,让用户有一个唯一的身份证明.但只有身份证明是不够的,你的身份 ...

  9. dubbo源码分析系列——dubbo-cluster模块源码分析

    2019独角兽企业重金招聘Python工程师标准>>> 模块功能介绍 该模块的使用介绍请参考dubbo官方用户手册如下章节内容. 集群容错 负载均衡 路由规则 配置规则 注册中心参考 ...

最新文章

  1. python笔记:数组的一些操作
  2. wxWidgets:wxSplitterWindow类用法
  3. SpringBoot集成EasyPoi实现Excel导入导出
  4. java chinapay_通过PHP/Java Bridge来实现ecshop的chinapay支付接口
  5. 浅谈EntityFramework框架的使用
  6. java 创建日程到期提醒_日程管理工具—Things 3
  7. matlab表达式,表达式 - MATLAB Simulink - MathWorks 中国
  8. spring的Bean属性
  9. 华为正式宣布全场景AI计算框架MindSpore开源 降低AI开发门槛
  10. 如鹏java学习进程 模拟小球弹跳
  11. python破解加密压缩包
  12. 产品设计学习(一)——梁宁产品思维大纲
  13. kktv电视剧鸿蒙,KKTV K70系列新品上市 京东、天猫、苏宁易购同步预售
  14. 滴滴CTO张博港科大演讲:详解未来交通变革的三层“折叠”
  15. 直接让Windows注销的脚本
  16. 清差额征税和简易计税的适用情形
  17. Activiti7工作流引擎:进阶篇(十) 多实例
  18. Android studio运行出现Unable to determine application id: com.android.tools.idea.run.ApkProvisionExcepti
  19. Hibernate的evict方法和clear方法的区别
  20. 完美玩机 三星I9000解锁工具实测教程

热门文章

  1. 维度和指标(metrics and dimensions)
  2. 2012互联网趋势报告详览:互联网女皇眼中的移动互联网
  3. potplayer_常用配置(窗口/快捷键/播放列表/)
  4. 如何写好外贸函电?利用7C原则
  5. Squeeze-and-Excitation Networks论文翻译——中英文对照
  6. selenium谷歌浏览器驱动配置
  7. 关于CheckBox和EditText在ListView里多布局的处理
  8. crontab用法与实例
  9. Le Potato + Jumbospot MMDVM热点盒子
  10. linux spt 脚本,写一个简单的FGO脚本