Bootstrap

24.11.28 Cookie

1.cookie

每次请求时 可以把cookie自定义的数据 传给服务端

(请求参数 请求头之外 报文传自定义数据的位置 cookie可以长期保存)

cookie特点

1.数据格式只有字符串
2.按键值对存储
3.对中文支持较差(尽量不要用中文)
4.按照网站(域 domain)存储    
5.可以长期存储 (有效期)
6.存储好之后 每次访问对应网站时 cookie都会自动发送

2.cookie在浏览器中查看和操作

在浏览器中 用户可以直接操作cookie

cookie一般存储跟用户本身相关的数据 而且是非关键数据

一般不要禁用cookie 禁用之后没法在浏览器缓存数据

3.java中读写cookie

java不能直接操作cookie数据 需要通过报文操作

请求时 浏览器会自动发送存储的cookie数据

响应时 通过Set-cookie响应头 通知浏览器操作cookie

java中与cookie相关API

* 写cookie
   Cookie cookie = new Cookie("ckkey","ckval333");

    设置cookie参数
    //直接设置到根 / 防止出现同名cookie
    cookie.setPath("/");
    //正整数  按秒计算过期时间
    //0      让cookie失效
    //-1     恢复为默认值 关闭浏览器自动失效
    cookie.setMaxAge(-1);

   resp.addCookie(cookie) 响应报文中 set-cookie 让浏览器保存

* 覆盖cookie
   cookie的name(key) path 一样
   可以修改其他参数

* 删除cookie
    cookie.setMaxAge(0); 报文中会传已过期的事件 通知浏览器删除
* cookie读取
        * Cookie[] cookies = req.getCookies();
        * 遍历cookies 读取cookie
        *
* cookie 读+写
        * //新创建的cookie对象 只有key value  其他参数都是默认值
        * Cookie[] cookies = req.getCookies();
        * 如果要覆盖cookie 必须保证同key 同path
        *   if("ckkey".equals(name) ){
                ck.setValue("newvalue");
                ck.setPath("/");
                ck.setMaxAge(60*60*24*30);
                resp.addCookie(ck);
            }

写cookie代码:

package com.javasm.controller;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;


@WebServlet("/demo1")
public class CookieDemo1 extends HttpServlet {

    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        /*
        * 写cookie
        * Cookie cookie = new Cookie("ckkey","ckval333");
        * 设置cookie参数
        * resp.addCookie(cookie) 响应报文中 set-cookie 让浏览器保存
        *
        * 覆盖cookie
        * cookie的name(key) path 一样
        * 可以修改其他参数
        *
        * 删除cookie
        * cookie.setMaxAge(0); 报文中会传已过期的事件 通知浏览器删除
        *
        *
        * */
        System.out.println("demo1运行了............");

        Cookie cookie = new Cookie("ckkey","ckval333");
        //直接设置到根 / 防止出现同名cookie
        cookie.setPath("/");
        //正整数  按秒计算过期时间
        //0      让cookie失效
        //-1     恢复为默认值 关闭浏览器自动失效,不设置值也是
        cookie.setMaxAge(-1);
        //通过响应对象 通知浏览器存储cookie
        //生成响应头 Set-Cookie: ckkey=ckval
        resp.addCookie(cookie);

    }
}

读cookie代码:

package com.javasm.controller;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;


@WebServlet("/demo2")
public class CookieDemo2 extends HttpServlet {

    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        /*
        * 写cookie
        * Cookie cookie = new Cookie("ckkey","ckval333");
        * 设置cookie参数
        * resp.addCookie(cookie) 响应报文中 set-cookie 让浏览器保存
        *
        * 覆盖cookie
        * cookie的name(key) path 一样
        * 可以修改其他参数
        *
        * 删除cookie
        * cookie.setMaxAge(0); 报文中会传已过期的事件 通知浏览器删除
        *
        *
        * cookie读取
        * Cookie[] cookies = req.getCookies();
        * 遍历cookies 读取cookie
        *
        * cookie 读+写
        * //新创建的cookie对象 只有key value  其他参数都是默认值
        * Cookie[] cookies = req.getCookies();
        * 如果要覆盖cookie 必须保证同key 同path
        *   if("ckkey".equals(name) ){
                ck.setValue("newvalue");
                ck.setPath("/");
                ck.setMaxAge(60*60*24*30);
                resp.addCookie(ck);
            }
        *
        *
        * cookie笔试题
        * cookie与session的区别
        *
        * cookie与session的关系
        //同一个浏览器 多次访问时 使用的同一个session对象
        //1session是怎么存的   Map存储 <session编号,session对象>
        //2session怎么识别编号 tomcat会创建一条cookie session编号 让浏览器保存
        //3每次请求时 tocmat读取指定的cookie的key 从而找到浏览器对应的cookie对象
        //session 实现依赖 cookie  通过编号 查找后端的共享数据
        *
        *
        *
        * */
        Cookie[] cookies = req.getCookies();
        for(Cookie ck:cookies){
            //根据当次请求报文 新创建的cookie对象
            String name = ck.getName();
            String value = ck.getValue();
            System.out.println(name+"---"+value);
            if("ckkey".equals(name) ){
                ck.setValue("newvalue");
                ck.setPath("/");
                ck.setMaxAge(60*60*24*30);
                resp.addCookie(ck);
            }
        }
    }
}

4.cookie与session的关系

session依赖cookie 如果禁用cookie session无法使用

package com.javasm.controller;

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;
import java.io.IOException;


@WebServlet("/cookieSession")
public class CookieAndSession extends HttpServlet {
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        HttpSession session = req.getSession();
        //服务会对浏览器应用 建立对应的session对象
        //同一个浏览器 多次访问时 使用的同一个session对象
        //1session是怎么存的   Map存储 <session编号,session对象>
        //2session怎么识别编号 tomcat会创建一条cookie session编号 让浏览器保存
        //3每次请求时 tocmat读取指定的cookie的key 从而找到浏览器对应的cookie对象
        //session 实现依赖 cookie  通过编号 查找后端的共享数据
        System.out.println(session.getId());


    }
}

5.js中读写cookie

js可以直接操作cookie 如果不向后端传递的情况 可以用作跨页面共享数据

js操作cookieAPI

*  写cookie
    *  document.cookie = 
             "jskey=jsval2;path=/;expires="+new Date('2024/12/15 12:12:12');
*  覆盖cookie
    *  保证同key 同path
*  删除
    *  document.cookie = "jskey=jsval2;path=/;expires="+new Date(过期时间);

*  读取cookie
    *  console.log(document.cookie)
    * ckkey=newvalue; 3333=4444; 4444=55555; ckkey=newvalue
    *
* 读+写
    * document.cookie.split("; ").forEach(data=>{
          //console.log(data);
          let kvarr = data.split("=");
          if("3333" == kvarr[0]){
              let newNum = parseInt(kvarr[1])+1
              document.cookie = `3333=${newNum};path=/;
                                 expires=`+new Date('2024/12/15 12:12:12');
          }
      })
    *
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<input type="button" value="操作cookie" onclick="addCookie()">
<input type="button" value="读取cookie" onclick="readCookie()">
</body>
<script>
  const addCookie = ()=>{
    /*
    *  写cookie
    *  document.cookie = "jskey=jsval2;path=/;expires="+new Date('2024/12/15 12:12:12');
    *  覆盖cookie
    *  保证同key 同path
    *  删除
    *  document.cookie = "jskey=jsval2;path=/;expires="+new Date(过期时间);
    *
    *  读取cookie
    *  console.log(document.cookie)
    * ckkey=newvalue; 3333=4444; 4444=55555; ckkey=newvalue
    *
    * 读+写
    * document.cookie.split("; ").forEach(data=>{
          //console.log(data);
          let kvarr = data.split("=");
          if("3333" == kvarr[0]){
              let newNum = parseInt(kvarr[1])+1
              document.cookie = `3333=${newNum};path=/;expires=`+new Date('2024/12/15 12:12:12');
          }
      })
    *
    *
    * js操作cookie的主要异议
    * 跨页面共享数据 纯前端存储
    *
    *
    * html5 webstorage
    *
    * */


    document.cookie = "jskey=jsval2;path=/;expires="+new Date('2000/12/15 12:12:12');

  }


  const readCookie = ()=>{
      //读到的是字符串
      console.log(document.cookie)
      document.cookie.split("; ").forEach(data=>{
          //console.log(data);
          let kvarr = data.split("=");
          if("3333" == kvarr[0]){
              let newNum = parseInt(kvarr[1])+1
              document.cookie = `3333=${newNum};path=/;expires=`+new Date('2024/12/15 12:12:12');
          }

      })


  }
</script>
</html>

6.webStorage

webStorage在html5版本时 添加的前端共享数据的技术(跨页面共享数据)

两个对象 API操作相同

sessionStorage 会话存储 关闭浏览器自动清除

localStorage 本地存储 长期有效

特征:

* 1.存储键值对
  * 2.数据格式字符串
  * 3.按域存储
  * 4.key唯一

API操作

写
      sessionStorage.新key = '值'
      sessionStorage.setItem('新key','值');

      删除
      sessionStorage.removeItem('key')
      sessionStorage.clear() 全部清除

      读取
      sessionStorage.name              读不到 undefined
      sessionStorage.getItem('addr')   读不到 null

示例:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<input type="button" value="操作storage" onclick="addstorage()">
<input type="button" value="读取storage" onclick="readstorage()">
</body>
<script>
  /*
  * webStorage  通过js操作 api简单
  *
  *sessionStorage  关闭浏览器自动失效
  *  localStorage  只要不删一直存在
  *
  * 1.存储键值对
  * 2.数据格式字符串
  * 3.按域存储
  * 4.key唯一
  *
  *   浏览器版本有要求 老浏览器用不了 ie8之前
  *   // sessionStorage  关闭浏览器自动删除
      // localStorage    长期有效
      *
      写
      sessionStorage.新key = '值'
      sessionStorage.setItem('新key','值');

      删除
      sessionStorage.removeItem('key')
      sessionStorage.clear() 全部清除

      读取
      sessionStorage.name              读不到 undefined
      sessionStorage.getItem('addr')   读不到 null
  *
  *
  *
  * */



const addstorage = ()=>{
    //属性方式操作
    localStorage.addr='430000';
    // //函数方式操作
    sessionStorage.setItem('name','jack213');

    // localStorage.removeItem('addr');
    // sessionStorage.clear()
    //组合json对象使用
    let myJsonstr = JSON.stringify({name:'jack',age:15,address:'xxxstreet'})
    sessionStorage.setItem('user',myJsonstr)

}

const readstorage  = ()=>{
    console.log(localStorage.getItem('addr'))
    console.log(sessionStorage.name)
    console.log(JSON.parse(sessionStorage.getItem('user')) )//转为JSON格式可以发送到后端
}

</script>
</html>

7.cookie与storage对比

*   cookie  前后端数据交互
  *   纯前端共享数据(跨页面共享数据) api使用麻烦
  *   自动拼入请求报文 向服务端发送
  *
  *   storage  跨页面共享数据
  *   纯前端共享数据(跨页面共享数据) api简单
  *   不自带发送功能 可以手动发送
  *
  *
  *   都可以结合json使用  需要转格式 cookie storage 值都是字符串

;