AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / server / 问题 / 1118173
Accepted
Budianto IP
Budianto IP
Asked: 2022-12-16 22:16:36 +0800 CST2022-12-16 22:16:36 +0800 CST 2022-12-16 22:16:36 +0800 CST

清漆 - 分离和附加 cookie

  • 772

首先,我想知道这是否可能。

所以,我可以看到如果 Varnish 有 cookie,它就不会缓存对象。

我在考虑当传入请求有 cookie 时,Varnish 会将它们存储在变量中并删除这些 cookie,然后让它通过后端。后端完成处理后,Varnish 会将 cookie 放回。

这是可能的吗?

如果是,vcl 是什么样子的?

varnish
  • 1 1 个回答
  • 18 Views

1 个回答

  • Voted
  1. Best Answer
    Thijs Feryn
    2022-12-17T02:28:48+08:002022-12-17T02:28:48+08:00

    语境

    Varnish 在缓存方面比较保守,并假设 cookie 的使用意味着响应的个性化程度。

    缓存个性化响应可能会导致隐私或安全问题。它还可能导致输出不一致。

    想象一下缓存一个有购物车的页面。缓存整个页面会导致每个人都拥有相同的购物车值。

    下面是 Varnish for cookies 的内置 VCL 行为:

    • 当 VarnishCookie在请求中看到标头时,它不会从缓存中提供对象,因为它假定内容是个性化的。

    请参阅https://www.varnish-software.com/developers/tutorials/varnish-builtin-vcl/#authorization-headers-and-cookies-are-not-cacheable

    • 当 VarnishSet-Cookie在响应中看到标头时,它不会将对象存储在缓存中,因为设置 cookie 是一种状态更改,也意味着个性化。

    请参阅https://www.varnish-software.com/developers/tutorials/varnish-builtin-vcl/#dont-cache-responses-with-set-cookie-headers

    剥离饼干

    一旦通过Set-Cookie响应标头设置了 cookie,它将作为Cookie每个后续请求的请求标头传递,即使对于并不真正需要这些 cookie 的页面也是如此。

    这就是为什么确定哪些页面需要 cookie 哪些不需要 cookie 很重要。识别跟踪 cookie 同样重要,因为它们由客户端在 Javascript 中处理,而不是在服务器上处理。

    这是一个 VCL 示例,我们在其中删除了所有 cookie,除了我们在服务器上需要的那些:

    vcl 4.1;
    
    sub vcl_recv {
        if (req.http.Cookie) {
            set req.http.Cookie = ";" + req.http.Cookie;
            set req.http.Cookie = regsuball(req.http.Cookie, "; +", ";");
            set req.http.Cookie = regsuball(req.http.Cookie, ";(PHPSESSID)=", "; \1=");
            set req.http.Cookie = regsuball(req.http.Cookie, ";[^ ][^;]*", "");
            set req.http.Cookie = regsuball(req.http.Cookie, "^[; ]+|[; ]+$", "");
        }
        if (req.http.cookie ~ "^\s*$") {
            unset req.http.cookie;
        }
    }
    

    在这种情况下,只PHPSESSID保留 cookie,因为它需要跟踪登录。如果在替换逻辑之后这个 cookie 仍然存在,则 Varnish 将不会提供来自缓存的响应。如果这个 cookie 没有设置,但是有一堆跟踪 cookie,所有的 cookie 都会被删除,页面可以从缓存中获取。

    删除某些页面的 cookie

    虽然前面的示例的特点是剥离选定的 cookie 并仅保留PHPSESSIDcookie,但您最终可能仍会访问实际上不需要该会话 cookie 的页面。

    这是一个 VCL 示例,其中 cookie 被完全剥离,除了在实际需要特定 cookie 的页面上,如管理页面和购物车页面:

    vcl 4.1;
    
    sub vcl_recv {
        if(req.url ~ "^/admin" || req.url == "/cart") {
            return(pass);
        }
        unset req.http.Cookie;
    }
    

    删除 Set-Cookie 标头

    如https://www.varnish-software.com/developers/tutorials/varnish-builtin-vcl/#dont-cache-responses-with-set-cookie-headers所示,内置 VCL 不会存储对象如果使用标头,则在缓存Set-Cookie中,因为它意味着状态更改。

    然而,这并不意味着页面永远不会在缓存中结束:下一个后端响应可能不会包含Set-Cookie标头,因为 cookie 已经设置。在那种情况下,没有Set-Cookie标头的下一个响应可能会在缓存中结束。

    但是,如果您确定不需要为某些页面设置 cookie,您也可以决定去掉Set-Cookie标题。

    以下示例阻止后端为静态内容设置 cookie:

    vcl 4.1;
    
    sub vcl_backend_response {
        if (bereq.url ~ "^[^?]*\.(7z|avi|bmp|bz2|css|csv|doc|docx|eot|flac|flv|gif|gz|ico|jpeg|jpg|js|less|mka|mkv|mov|mp3|mp4|mpeg|mpg|odt|ogg|ogm|opus|otf|pdf|png|ppt|pptx|rar|rtf|svg|svgz|swf|tar|tbz|tgz|ttf|txt|txz|wav|webm|webp|woff|woff2|xls|xlsx|xml|xz|zip)(\?.*)?$") {
            unset beresp.http.Set-Cookie;
        }
    }
    

    重新附加 cookie

    虽然可以将 cookie 值存储在标头中,然后在 VCL 中剥离 cookie 以便从缓存中提供服务,最后重新附加后端请求,但这并没有多大意义。

    如果可缓存响应不需要 cookie 来创建其输出,为什么要为后端请求发送 cookie?

    如果后端请求需要 cookie 值来组成输出,这可能意味着响应将不可缓存,因此您不妨为该请求完全绕过缓存。

    下一步

    因为你的问题不是很具体,我也不得不给你一个非常笼统的答复。

    如果我的回答完全回答了您的问题,我邀请您详细说明您的用例,作为回报,我会给您更详细的答复。

    • 2

相关问题

  • 清漆配置仅缓存未登录用户

  • Varnish 缓存如何处理不同的域?

  • 缩放大文件下载?

  • Gzip 与反向代理缓存

  • 在 Windows XP 主机上使用虚拟化 linux 来宾评估 Varnish 的最简单方法是什么?

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    新安装后 postgres 的默认超级用户用户名/密码是什么?

    • 5 个回答
  • Marko Smith

    SFTP 使用什么端口?

    • 6 个回答
  • Marko Smith

    命令行列出 Windows Active Directory 组中的用户?

    • 9 个回答
  • Marko Smith

    什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同?

    • 3 个回答
  • Marko Smith

    如何确定bash变量是否为空?

    • 15 个回答
  • Martin Hope
    Tom Feiner 如何按大小对 du -h 输出进行排序 2009-02-26 05:42:42 +0800 CST
  • Martin Hope
    Noah Goodrich 什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同? 2009-05-19 18:24:42 +0800 CST
  • Martin Hope
    Brent 如何确定bash变量是否为空? 2009-05-13 09:54:48 +0800 CST
  • Martin Hope
    cletus 您如何找到在 Windows 中打开文件的进程? 2009-05-01 16:47:16 +0800 CST

热门标签

linux nginx windows networking ubuntu domain-name-system amazon-web-services active-directory apache-2.4 ssh

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve