openresty 之设置响应 cookie
文档
ngx.header.HEADER
使用的 Nginx API for Lua
为 ngx.header.HEADER = VALUE
设置、添加或清除当前请求的
HEADER
要发送的响应标头
ngx.header
是什么
ngx.header
是 响应 标头,类型是 table
。
上图所示,我们所使用的是 ngx.header['Set-Cookie']
对响应头中的 Set-Cookie
赋值,而发送到浏览器后,浏览器将内容存储到 cookie 中,即设置 cookie。
code
因此 openresty
中设置 cookie 的代码:
ngx.header['Set-Cookie'] = 'key=value;path=/'
在 lua
中,ngx.header.Set-Cookie
语法是错的,因此用 ['']
。另一种等价写法是 ngx.header.set_cookie
ngx.header.set_cookie = 'key=value;path=/'
同时,还支持赋值 table
,一般是设置多个 key
时使用
ngx.header['Set-Cookie'] = {'key=value;path=/','key2=value2;path=/'}
打印(ngx.header.set_cookie)
2023-05-03 18:17:14 [DEBUG] (table){
[1]="key=value;path=/"
[2]="key2=value2;path=/"
}
Expires
的设置
-- 设置 cookie 过期时间为一小时后
local expires = ngx.cookie_time(ngx.time() + 3600)
ngx.header['Set-Cookie'] = 'key5=value5; path=/; Expires='..expires.. '; Max-Age=' ..3600
使 cookie 过期
ngx.header['Set-Cookie'] = 'key5=deleted; Expires=' .. ngx.cookie_time(0) .. '; path=/'
openresty 的扩展库
有了上面的基础后,github 上的扩展库 lua-resty-cookie 应该能阅读的懂了。以其中设置 cookie 的一段代码解释
function _M.set(self, cookie)
-- cookie 参数为 table,{key='key1',value='value1',path='/'},这是为了传参方便
local cookie_str, err = bake(cookie)
if not cookie_str then
return nil, err
end
-- bake方法返回 cookie_str 是字符串格式 'key1=value1;path=/'
-- 先取出 ngx_header['Set-Cookie'] 中的内容,是因为在之前你可能设置过,如果直接 ngx_header['Set-Cookie']=xx,则会覆盖掉之前设置的值。
local set_cookie = ngx_header['Set-Cookie']
-- 判断类型的目的是想知道 ngx_header['Set-Cookie'] 是字符串还是 table 类型,如果是字符串类型,说明之前只设置了一个 cookie,如果是 table,则往里面添加。
local set_cookie_type = type(set_cookie)
local t = self.set_cookie_table
clear_tab(t)
if set_cookie_type == "string" then
-- only one cookie has been setted
-- 之前设置过,而且是赋值字符串的方式。
-- 那么就采取上文中的 table 方式赋值,即可以设置多个 cookie。set_cookie 为原本存在的,cookie_str 是现在追加的。
if set_cookie ~= cookie_str then
t[1] = set_cookie
t[2] = cookie_str
ngx_header['Set-Cookie'] = t
end
elseif set_cookie_type == "table" then
-- 如果原来的 ngx_header['Set-Cookie'] 是个table,那直接在 table 的末尾追加就可以了。#set_cookie 是长度,lua 中下标从 1 开始,因此长度等于最后一个下标,新设置的 cookie 的下标就是 #set_cookie + 1
-- more than one cookies has been setted
local size = #set_cookie
-- we can not set cookie like ngx.header['Set-Cookie'][3] = val
-- so create a new table, copy all the values, and then set it back
for i = 1, size do
t[i] = ngx_header['Set-Cookie'][i]
if t[i] == cookie_str then
-- new cookie is duplicated
return true
end
end
t[size + 1] = cookie_str
ngx_header['Set-Cookie'] = t
else
-- ngx_header['Set-Cookie'] 既不是字符串也不是table,说明从来没设置过 cookie,不用担心覆盖的问题,直接赋值即可。
-- no cookie has been setted
ngx_header['Set-Cookie'] = cookie_str
end
return true
end
本作品采用《CC 协议》,转载必须注明作者和本文链接