前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >25. 会话技术-Cookie的使用

25. 会话技术-Cookie的使用

作者头像
Devops海洋的渔夫
发布2021-11-12 09:32:41
1.4K0
发布2021-11-12 09:32:41
举报
文章被收录于专栏:Devops专栏

25. 会话技术-Cookie的使用

一 、会话概述

1.1 什么是会话?

日常生活中:从拨通电话到挂断电话之间的一连串你问我答的过程就是一个会话。

B/S架构中:从浏览器第一次给服务器发送请求时,建立会话;直到有一方断开,会话结束。

代码语言:javascript
复制
一次会话:包含多次请求响应。

1587172413825

1.2 会话技术

**问题:**Http是一个无状态协议,同一个会话的连续两个请求相互独立,彼此并不了解

作用:用于 存储 浏览器与服务器在请求和响应过程中产生的 数据

在一次会话中(多次请求响应), 共享数据

客户端会话技术:cookie

服务器端会话技术:session

1587172824573

二、 Cookie

2.1 概述

Cookie作用:在一次会话的多次请求之间共享数据,将数据保存到客户端(浏览器)

代码语言:javascript
复制
#Cookie的特点
1. cookie保存在客户端(浏览器), 往往是由服务器产生发送给浏览器
2. cookie只能保存字符串, 格式是 entry(name : value)
3. cookie的大小有限制: 4k
4. 一般, 同一域名下的cookie限制数量50个

2.2 快速入门

下面我们首先可以以游客的身份访问京东页面,添加商品到购物车上,但是我们并没有登录京东的账号。当我们关闭京东的页面,再次访问的时候,却发现购物车还有我们之前加入购物车的商品。这是为什么呢?

这就是因为 Cookie 的作用了:京东的页面将游客加入购物车的商品信息保存到浏览器下,当使用同一个浏览器在一次会话中再次访问页面,那么商品信息就会自动随着cookie信息请求到 京东服务端,然后由京东服务将你之前选择的商品加入到购物车之中。

1591235563712

1591235580561

下面是谷歌浏览器请求访问京东服务器的示意流程图:

1591235608007

执行伪代码如下:

代码语言:javascript
复制
1. 设置数据到cookie中
 // 1.创建cookie对象,设置数据
  Cookie cookie = new Cookie(String name,String value);
 // 2.通过response,响应(返回)cookie
  response.addCookie(cookie);

2. 从cookie中获取数据
 // 1.通过request对象,接收cookie数组
  Cookie[] cookies = request.getCookies();
 // 2.遍历数组
  获取name值:  String name = cookie.getName();
  获取value值:  String value = cookie.getValue();

2.2.1 代码实现:

首先我们需要创建页面 index.html, 模拟添加商品到购物车 和 第二次查看购物车的 操作。

  • 添加商品到购物车:目的在于将添加的商品信息发送给服务器,由服务器返回给浏览器,将商品信息 设置 Cookie 信息 保存在浏览器。
  • 第二次查看购物车:目的在于浏览器请求服务器的时候,会将同一个域名路径下的 Cookie 发送到服务器,然后由服务器将商品信息返回给浏览器显示。
index.html

image-20210216223410324

代码语言:javascript
复制
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>index</title>
</head>
<body>

    <a href="Cookie01Servlet?product=xiaomi">第一次_添加小米到购物车</a> <br>
    <a href="Cookie02Servlet">第二次_查看购物车</a>  <br>

</body>
</html>

编写好 index.html 页面后,我们启动 tomcat 访问一下页面,如下:

image-20210216223444430

好了,下面我们就要实现 Cookie01Servlet 和 Cookie02Servlet 两个 Servlet 程序,来实现 Cookie 的业务操作。

Cookie01Servlet

创建 Cookie01Servlet 用来处理 添加商品到购物车:目的在于将添加的商品信息发送给服务器,由服务器返回给浏览器,将商品信息 设置 Cookie 信息 保存在浏览器。

image-20210217095805904

代码语言:javascript
复制
package com.lijw;

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

/**
 * @author Aron.li
 * @date 2021/2/17 9:49
 */
@javax.servlet.annotation.WebServlet("/Cookie01Servlet")
public class Cookie01Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

        //1. 接收商品参数的信息
        String product = request.getParameter("product");

        //2. 创建Cookie对象
        Cookie cookie = new Cookie("product", product);

        //3. 返回浏览器添加Cookie
        response.addCookie(cookie);

        //4. 页面重定向回 index.html
        response.sendRedirect("index.html");
    }
}
Cookie02Servlet

创建 Cookie02Servlet 用来处理 第二次查看购物车:目的在于浏览器请求服务器的时候,会将同一个域名路径下的 Cookie 发送到服务器,然后由服务器将商品信息返回给浏览器显示。

image-20210217101143665

代码语言:javascript
复制
package com.lijw;

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;

/**
 * @author Aron.li
 * @date 2021/2/17 9:59
 */
@WebServlet("/Cookie02Servlet")
public class Cookie02Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        // 设置返回的内容为 html
        response.setContentType("text/html;charset=utf-8");

        // 1.获取请求中携带过来的所有 Cookie
        Cookie[] cookies = request.getCookies();
        // 2.遍历Cookies信息,显示到浏览器上
        for (Cookie cookie : cookies) {
            String name = cookie.getName();
            String value = cookie.getValue();
            response.getWriter().write("name: " + name + ", value: " + value + "<br/>");
        }

        // 3. 返回 index.html 页面
        response.getWriter().write("<a href='index.html'>返回index</a>");
    }
}
测试第一次将商品加入购物车

启动 tomcat 服务,然后点击第一次_添加小米到购物车:

image-20210217101441237

image-20210217101509747

可以看到请求到了 Cookie01Servlet ,并且重定向回来了,下面看看添加好的 Cookie 信息,如下:

image-20210217101630401

测试 第二次查看购物车

image-20210217101704689

image-20210217101722464

可以看到成功显示出了所有 cookie 信息。

从上面的两个Servlet中,我们理解了如何添加 Cookie 以及 如何查询 Cookie 信息,下面我们来看看在浏览器如何查看 Cookie

google浏览器中查看Cookie的方式一

image-20210217101905786

image-20210217101932923

google浏览器中查看Cookie的方式二

image-20210217101957329

2.3 工作原理

基于HTTP协议:

1. 服务器发送Cookie给浏览器是通过 : 响应(响应头 set-cookie)

Set-Cookie: phone=xiaomi

Set-Cookie: computer=lenovo

2. 浏览器发送Cookie给服务器是通过: 请求(请求头 cookie)

Cookie: phone=xiaomi; computer=lenovo

1587174808482

2.4 Cookie详情

2.4.1 服务器发送多个Cookie?

代码语言:javascript
复制
* 答案: 可以的
 // 1. 创建多个cookie对象
  Cookie cookie1 = new Cookie("name","lucy");
  Cookie cookie2 = new Cookie("age","18");
 // 2. 通过response响应多个
  response.addCookie(cookie1);
  response.addCookie(cookie2);

下面我们写一个简单的示例来看看:

修改之前的 index.html 增加请求 Cookie03Servlet (设置多个Cookie)

image-20210217102853105

Cookie03Servlet :创建多个Cookie

image-20210217105855160

代码语言:javascript
复制
package com.lijw;

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;

/**
 * @author Aron.li
 * @date 2021/2/17 10:46
 */
@WebServlet("/Cookie03Servlet")
public class Cookie03Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //1. 创建多个Cookie,返回浏览器
        Cookie cookie1 = new Cookie("cookie1", "cookie1value");
        Cookie cookie2 = new Cookie("cookie2", "cookie2value");

        response.addCookie(cookie1);
        response.addCookie(cookie2);

        //2. 重定向回 index.html
        response.sendRedirect("index.html");
    }
}
测试设置多个 Cookie

image-20210217105957270

2.4.2 Cookie是否可以存储中文和非法字符?

代码语言:javascript
复制
* tomcat8之前的版本,不支持中文
* tomcat8以后的版本,支持中文...
 但是按照 Rfc6265Cookie规范,在cookie值中不能使用分号(;)、逗号(,)、等号(=)以及空格

我们可以存储,但是要使用url编码,来避开这个规范限制

* 解决
  java.net.URLEncoder.encode(字符串","utf-8") 把字符串使用utf-8进行编码
  java.net.URLDecoder.decode(字符串","utf-8")  把字符串使用utf-8进行解码

下面我们再写一个服务端设置 中文 和 非法字符 的 Cookie。

修改 index.html 请求 Cookie04Servlet(用来设置中文和非法字符)

image-20210217110247192

Cookie04Servlet:先直接存储中文 和 非法字符

image-20210217110549982

代码语言:javascript
复制
package com.lijw;

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;

/**
 * @author Aron.li
 * @date 2021/2/17 11:03
 */
@WebServlet("/Cookie04Servlet")
public class Cookie04Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //1. 创建存储中文和非法字符的cookie内容(按照 Rfc6265Cookie规范,在cookie值中不能使用分号(;)、逗号(,)、等号(=)以及空格)
        Cookie cookie = new Cookie("cookie04", "中文内容 空格 逗号内容");
        //2. 返回浏览器,以及重定向
        response.addCookie(cookie);
        response.sendRedirect("index.html");
    }
}
测试请求非法内容

image-20210217110618332

image-20210217110639728

Cookie04Servlet:使用 URLEncoder 存储中文 和 非法字符

在上面的测试中,我们已经发现 Cookie 无法直接存储 中文 和 非法字符,为了解决这个问题。我们需要将内容进行 URL 编码。

image-20210217110926586

代码语言:javascript
复制
package com.lijw;

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;
import java.net.URLEncoder;

/**
 * @author Aron.li
 * @date 2021/2/17 11:03
 */
@WebServlet("/Cookie04Servlet")
public class Cookie04Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //1. 创建存储中文和非法字符的cookie内容(按照 Rfc6265Cookie规范,在cookie值中不能使用分号(;)、逗号(,)、等号(=)以及空格)
        String str = "中文内容 空格 逗号内容";
        String encode = URLEncoder.encode(str, "utf-8");  //使用URL编码解决Cookie无法存储非法字符的问题
        Cookie cookie = new Cookie("cookie04", encode);
        //2. 返回浏览器,以及重定向
        response.addCookie(cookie);
        response.sendRedirect("index.html");
    }
}
测试请求URL编码后的Cookie内容

image-20210217111032266

下面我们再写一个读取 URL 编码的 Cookie 内容。

修改 index.html 请求 Cookie05Servlet(用来读取 URL 编码的内容)

image-20210217112205049

Cookie05Servlet:使用URL解码读取Cookie的中文以及非法字符内容

image-20210217112247638

代码语言:javascript
复制
package com.lijw;

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;
import java.net.URLDecoder;

/**
 * @author Aron.li
 * @date 2021/2/17 11:15
 */
@WebServlet("/Cookie05Servlet")
public class Cookie05Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        response.setContentType("text/html;charset=utf-8"); // 设置返回的内容为HTML

        //1. 读取全部Cookie的信息
        Cookie[] cookies = request.getCookies();
        for (Cookie cookie : cookies) {
            String name = cookie.getName();
            String value = cookie.getValue();

            // 如果是cookie04,需要进行URL解码
            if ("cookie04".equalsIgnoreCase(name)) {
                // 对内容进行URL解码
                String decode = URLDecoder.decode(value, "utf-8");
                response.getWriter().write(name + "--" + decode + "<br/>");
            } else {
                // 打印其他Cookie内容
                response.getWriter().write(name + "--" + value + "<br/>");
            }

        }
    }
}
测试请求读取URL解码后的Cookie内容

image-20210217112335728

image-20210217112351152

2.4.3 Cookie的域名作用(domain)

image-20210217112542516

代码语言:javascript
复制
1. cookie信息中的域名作用是标记这个cookie的归属
  在我们的浏览器中,既保存了域名为localhost的cookie,又保存域名为baidu的cookie
  那么访问的网站如果是 http://localhost:8080, 浏览器的请求只会携带域名为localhost的cookie
  
2. 默认情况下,cookie的域名是发送此cookie的服务器域名是一致的
 url格式 ->  协议://域名:端口/资源位置

2.4.4 Cookie的路径作用(path)

代码语言:javascript
复制
0. 在我们的项目中,cookie的路径默认为项目的虚拟路径
  url->  http://localhost:8080/项目虚拟路径/Servlet的虚拟路径
  比如: 项目虚拟路径 = /  
   
1. 第一个作用: cookie信息中的path和name共同决定了cookie的唯一性
     a. PathServlet被浏览器每访问一次, cookie就会发送一次
        b. 如果服务器再次发送一个同 path+name的cookie,会覆盖浏览器的那个cookie
         (新覆盖旧)
        c. 服务器再次发送一个同 path, 异name的cookie , 不会覆盖
        d. 服务器再次发送一个异 path, 同name的cookie, 不会覆盖
        
2. 第二个作用: cookie的path还决定了cookie允许被访问的范围
  特点:Cookie在其设置的有效路径和其子路径下能够被访问到;
  举例: 有一个cookie,路径为 /aaa
          只有访问 http://localhost:8080/aaa 以及其子路径,才会携带这个cookie
                问题:
                1. 访问http://localhost:8080/PathServlet  -> PathServlet
                  会携带这个cookie吗     ->  不会
                2. 访问http://localhost:8080/aaa    -> AaaServlet
                  会携带这个cookie吗     ->  会
                3. 访问http://localhost:8080/aaa/MyServlet -> MyServlet
                  会携带这个cookie吗     ->  会
#API : cookie.setPath(虚拟路径); 
 路径要以 / 开头
第一个作用的示例

下面我们来写一个简单的示例,编写 Cookie06Servlet 保存两个不同path 但是同 name 的cookie

首先修改 index.html 如下:

image-20210217152045596

编写 Cookie06Servlet 如下:

image-20210217152801055

代码语言:javascript
复制
package com.lijw;

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;

/**
 * @author Aron.li
 * @date 2021/2/17 15:21
 */
@WebServlet("/Cookie06Servlet")
public class Cookie06Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        // 创建两个Cookie,同name,但是path不一样
        Cookie cookie1 = new Cookie("cookie06", "value01");
        cookie1.setPath("/");
        response.addCookie(cookie1);

        Cookie cookie2 = new Cookie("cookie06", "value02");
        cookie2.setPath("/a");
        response.addCookie(cookie2);

    }
}

测试请求,查看是否存在两个不同的 Cookie,如下:

image-20210217152837509

image-20210217152912147

image-20210217152925825

可以看到具有两个 cookie06,路径不一致。

第二个作用的示例

第二个作用: cookie的path还决定了cookie允许被访问的范围

image-20210217153122515

2.4.5 Cookie的存活时间

代码语言:javascript
复制
# 浏览器中cookie的信息
1. 创建时间: 浏览器接收到此cookie的时间
2. 到期时间: cookie销毁的时间

# cookie的存活时间有两种
1. 会话级别(默认,浏览器关闭,cookie销毁 )
 浏览器中的cookie显示(浏览会话结束时: 浏览器关闭)
 原因: 浏览器将cookie保存内存中(临时的)
 
 cookie在一个会话中(浏览器从打开到关闭: 访问服务器)共享数据
 
2. 持久级别(需要手动设置)
 cookie.setMaxAge(int second); -- 单位是秒
  正数:指定存活时间,持久化浏览器的磁盘中,到期后自动销毁
  零:立即销毁
 原因: 浏览器将cookie保存在硬盘上(持久的) 
 
 cookie在可以在多个会话中(浏览器从打开到关闭多次: 访问服务器)共享数据
 

编写一个设置cookie的时长示例。

index.html 增加请求 Cookie07Servlet:

image-20210217153340447

Cookie07Servlet 设置 cookie 的 存活时间

image-20210217153648640

代码语言:javascript
复制
package com.lijw;

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;

/**
 * @author Aron.li
 * @date 2021/2/17 15:34
 */
@WebServlet("/Cookie07Servlet")
public class Cookie07Servlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        // 设置存活时间为30分钟的cookie
        Cookie cookie07 = new Cookie("cookie07", "30min");
        cookie07.setMaxAge(60*30); // 30分钟
        response.addCookie(cookie07);

        // 重定向回 index.html
        response.sendRedirect("index.html");
    }
}
测试请求生成的 cookie 存活时间

image-20210217153859689

可以看到 cookie07 的存活时间。

2.4.6 Cookie的删除

代码语言:javascript
复制
# 目标:删除Cookie
 1. 用户在浏览器中手动删除cookie(清除浏览记录): 用户未必知道或者配合
 2. 从服务端远程操控删除cookie(服务端)
 
# 远程删除实现步骤:
 0. 核心思想: 服务端发送一个同 path+name的cookie,cookie的存活时间为0
    原理:  新cookie先覆盖浏览器保存的cookie,但是因为时间0,新cookie马上死掉
              
 1. 创建与要删除的cookie同name的cookie,将其值设置成什么都无所谓;
    2. 设置这个cookie的路径(与原cookie的路径一致);
    3. 将这个cookie的最大存活时间设置成0;
    4. 将这个新的cookie响应给浏览器,置换原来的cookie,新cookie也马上销毁; 

删除 cookie 的 Servlet 示例:

代码语言:javascript
复制
@WebServlet("/Cookie08Servlet")
public class Cookie08Servlet extends HttpServlet {

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        this.doPost(request, response);
    }

    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

        //创建一个短命cookie,跟要删除cookie同path+name
        Cookie cookie = new Cookie("car", "");
        cookie.setPath("/"); // http://localhost:8080/...
        cookie.setMaxAge(0); // 设置存活时间只有0秒
        response.addCookie(cookie);

    }

}

2.5 Cookie特点

代码语言:javascript
复制
1. cookie存储数据在客户端(浏览器)
2. cookie的存储数据(name和value)只能是字符串
3. cookie单个大小不能超过4KB
4. 同一个域名下cookie数量一般不能超过50个
5. 同一域名下, cookie的path和name决定了它的唯一性
6. cookie存储的数据不太安全
  信息保存在用户的电脑上,都相对不安全

三、 综合案例

3.1 商品浏览记录

需求

做一个商品页面,当我们访问后,在页面上点击查看商品浏览记录后,可以查看到以前浏览过的商品信息。

3.1.1 需求分析

  • 编写一个商品列表页面 goods.html ,设置两个请求,可以添加两个商品到购物车中(每个添加都会请求到 GoodsServlet 中)
  • GoodsServlet 程序接收页面发送过来的商品信息,将其商品信息拼接保存为一个 Cookie,重定向至 goods2.html
  • 编写另一个 goods2.html,用于查看保存到购物车中的商品信息(请求至 HistoryServlet)
  • HistoryServlet 程序解析 goods2.html 发送过来的 Cookie 信息,显示商品内容

3.1.2 代码实现

① goods.html

image-20210217155259312

代码语言:javascript
复制
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <a href="GoodsServlet?product=huawei">华为手机</a><br>
    <a href="GoodsServlet?product=xiaomi">小米手机</a> <br>
    <a href="GoodsServlet?product=chuizi">锤子手机</a> <br>
</body>
</html>
② goods2.thml

image-20210217155344702

代码语言:javascript
复制
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<a href="goods.html">继续浏览</a> <br>
<a href="HistoryServlet">查看浏览记录</a> <br>
</body>
</html>
③ GoodsServlet

image-20210217160819321

代码语言:javascript
复制
package com.lijw;

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;

/**
 * @author Aron.li
 * @date 2021/2/17 15:54
 */
@WebServlet("/GoodsServlet")
public class GoodsServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //1. 获取请求参数
        String product = request.getParameter("product");

        //2. 获取请求中的cookie
        Cookie[] cookies = request.getCookies();
        //2.1 判断是否存在 history 的 cookie
        Boolean exist_history = false; // 用于标识history的cookie是否存在
        if (cookies != null && cookies.length > 0){
            for (Cookie cookie : cookies) {
                String name = cookie.getName();
                if("history".equalsIgnoreCase(name)){
                    // 设置标识存在 history cookie
                    exist_history = true;
                    // history的cookie存在
                    String value = cookie.getValue();
                    value = value + "_" + product;
                    cookie.setValue(value);
                    response.addCookie(cookie);
                }
            }

            //判断history如果不存在,则创建新的Cookie
            if (!exist_history) {
                Cookie cookie = new Cookie("history", product);
                cookie.setMaxAge(60*30);//30分钟
                response.addCookie(cookie);
            }

        }

        //3. 重定向到 goods2.html
        response.sendRedirect("goods2.html");
    }
}
④ HistoryServlet

image-20210217155643123

代码语言:javascript
复制
package com.lijw;

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;

/**
 * @author Aron.li
 * @date 2021/2/17 15:55
 */
@WebServlet("/HistoryServlet")
public class HistoryServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request, response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        response.setContentType("text/html;charset=utf-8");
        //1.获取请求中的cookie
        Cookie[] cookies = request.getCookies();
        if(cookies != null && cookies.length > 0){
            for (Cookie cookie : cookies) {
                String name = cookie.getName();
                if("history".equalsIgnoreCase(name)){
                    String value = cookie.getValue();

                    String[] array = value.split("_");
                    response.getWriter().print("<h1>浏览器记录:</h1>");
                    for (String element : array) {
                        response.getWriter().print(element + "<br>");
                    }
                }
            }

        }else{
            response.getWriter().print("无浏览记录");
        }
        response.getWriter().print("<br>");
        response.getWriter().print("<a href='goods.html'>继续浏览</a>");
    }
}

3.1.3 测试功能

image-20210217155801203

image-20210217160740185

image-20210217160752549

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-11-09,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 海洋的渔夫 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 25. 会话技术-Cookie的使用
  • 一 、会话概述
    • 1.1 什么是会话?
      • 1.2 会话技术
      • 二、 Cookie
        • 2.1 概述
          • 2.2 快速入门
            • 2.2.1 代码实现:
          • 2.3 工作原理
            • 2.4 Cookie详情
              • 2.4.1 服务器发送多个Cookie?
              • 2.4.2 Cookie是否可以存储中文和非法字符?
              • 2.4.3 Cookie的域名作用(domain)
              • 2.4.4 Cookie的路径作用(path)
              • 2.4.5 Cookie的存活时间
              • 2.4.6 Cookie的删除
            • 2.5 Cookie特点
            • 三、 综合案例
              • 3.1 商品浏览记录
                • 3.1.1 需求分析
                • 3.1.2 代码实现
                • 3.1.3 测试功能
            相关产品与服务
            云服务器
            云服务器(Cloud Virtual Machine,CVM)提供安全可靠的弹性计算服务。 您可以实时扩展或缩减计算资源,适应变化的业务需求,并只需按实际使用的资源计费。使用 CVM 可以极大降低您的软硬件采购成本,简化 IT 运维工作。
            领券
            问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档