当使用expires
标志,日期必须完全符合您当前使用的格式以及GMT
(格林威治标准时间)时区。您的 cookie 在创建后 2 分钟内不会过期的原因是您正在使用日期时间.now(),它返回当前的local日期和时间。
因此,例如,如果您当前的本地时区是GMT+2
时间是20:30:00
(因此,GMT
时间是18:30:00
),创建一个过期时间为20:32:00 GMT
实际上会告诉浏览器在 2 小时 2 分钟内删除此 cookie(从创建之日起)。如果你查看 cookieExpires / Max-Age
浏览器开发工具中的列(例如,在 Chrome 上,转到Network
在 DevTools 中的选项卡中,单击请求的名称,然后单击Cookies
选项卡),您会注意到Z
在日期时间的末尾,这意味着UTC
(协调世界时)——即与 UTC 的偏移量为零时-分-秒。您也可以检查响应标头,您可以在其中看到 cookieexpires
标志设置为20:32:00 GMT
。没有什么明显的之间的时间差UTC and GMT(如果您想了解更多关于它们的差异,请查看此post).
因此,您可以替换.now()
with .utcnow()在你的代码中:
from datetime import timedelta, datetime
def get_expiry():
expiry = datetime.utcnow()
expiry += timedelta(seconds=120)
return expiry.strftime('%a, %d-%b-%Y %T GMT')
or use 时间.gmtime(),传递为secs
论证时间.time()(返回以秒为单位的时间)加上所需的租约时间(以秒为单位):
import time
def get_expiry():
lease = 120 # seconds
end = time.gmtime(time.time() + lease)
return time.strftime('%a, %d-%b-%Y %T GMT', end)
对于上述两种方法之一,请使用:
cookie['expires'] = get_expiry()
您还可以使用未记录的方式直接以秒为单位传递到期时间。例如:
cookie['expires'] = 120
替代方案expires
is the max-age
flag ,指定 cookie 从当前时刻起的过期时间(以秒为单位)(与上面的方式类似)。如果设置为零或负值,则 cookie 将被立即删除。例子:
cookie['max-age'] = 120
Note:
If both expires
and max-age
已设定,max-age
具有优先权(参见相关MDN 上的文档).
另外,根据RFC 6265:
4.1.2.1.这Expires
属性
The Expires
属性表示cookie的最大生命周期,
表示为日期和时间cookie 过期的时间。用户
代理无需在指定日期之前保留 cookie
已经过去了。事实上,用户代理经常因内存问题而驱逐 cookie
压力或隐私问题。
4.1.2.2.这Max-Age
属性
The Max-Age
属性表示cookie的最大生命周期,
表示为数量seconds直到cookie过期。这
用户代理不需要保留指定的cookie
期间。事实上,用户代理经常因内存问题而驱逐 cookie
压力或隐私问题。
NOTE: Some existing user agents do not support the Max-Age
attribute. User agents that do not support the Max-Age attribute
ignore the attribute.
如果 cookie 有both the Max-Age
和Expires
属性,即Max-Age
属性具有优先权并控制过期日期
饼干。如果 cookie 有neither the Max-Age
也不Expires
属性,用户代理将保留 cookie 直到“当前
会话结束”(由用户代理定义)。
另请注意,如中所述MDN 文档关于expires
flag:
Warning:许多网络浏览器都有一个会话恢复功能将保存所有选项卡并在下次使用浏览器时恢复它们。
会话 cookies 也会被恢复,就好像浏览器从未恢复过一样
关闭。
另一件值得注意的是,自 2022 年 9 月以来,Chrome 限制 cookiemax-age至 400 天:
当cookies被显式设置时Expires/Max-Age
归因于值现在限制为不超过 400 天将来。
以前,没有限制,cookie 的过期时间可以是
未来几千年。
使用 FastAPI/Starlette
还应该指出的是,FastAPI/Starlette 提供了一种更简单的方法来设置 cookieResponse
对象,使用set_cookie方法,如中所述这个答案。按照星光文档:
-
max_age
- An integer定义 cookie 的生命周期seconds。负整数或值0
将丢弃
立即饼干。Optional
-
expires
- An integer定义了数量seconds直到cookie过期。Optional
示例来自FastAPI文档:
from fastapi import FastAPI, Response
app = FastAPI()
@app.post('/')
def create_cookie(response: Response):
response.set_cookie(key='token', value='token-value', max_age=120, expires=120, httponly=True)
return {'message': 'success'}