python
def create_access_token(data: dict, expires_delta: timedelta | None = None) -> str:
to_encode = data.copy()
expire = datetime.now(timezone.utc) + (
expires_delta
if expires_delta
else timedelta(minutes=settings.access_token_expire_minutes)
)
to_encode.update({"exp": expire})
return jwt.encode(to_encode, settings.jwt_secret_key, algorithm=settings.jwt_algorithm)
代码运行报错:
def create_access_token(data: dict, expires_delta: timedelta | None = None) -> str: TypeError: unsupported operand type(s) for |: 'type' and 'NoneType'
问题分析
timedelta | None 是 Python 3.10 才引入的管道符(|)联合类型语法糖 ,如果你的 Python 版本低于 3.10,解释器会把 | 当成普通的运算符,试图计算 type(timedelta) 和 NoneType 的 "或运算",这显然是不支持的,因此抛出 TypeError。
解决方案
只需要把新的联合类型写法改成兼容低版本 Python 的标准写法即可,有两种方式:
方式 1:使用 Union 类型(兼容所有 Python 3 版本)
这是最通用的写法,需要先从 typing 模块导入 Union:
python
from datetime import datetime, timedelta, timezone
from typing import Union # 导入Union类型
import jwt
# 假设你的settings模块是这样的,需根据实际情况调整
class Settings:
access_token_expire_minutes = 30
jwt_secret_key = "your-secret-key-here"
jwt_algorithm = "HS256"
settings = Settings()
def create_access_token(data: dict, expires_delta: Union[timedelta, None] = None) -> str:
to_encode = data.copy()
expire = datetime.now(timezone.utc) + (
expires_delta
if expires_delta
else timedelta(minutes=settings.access_token_expire_minutes)
)
to_encode.update({"exp": expire})
return jwt.encode(to_encode, settings.jwt_secret_key, algorithm=settings.jwt_algorithm)
# 测试代码(可选)
if __name__ == "__main__":
token = create_access_token({"sub": "user123"})
print("生成的Token:", token)
方式 2:升级 Python 到 3.10+(推荐长期方案)
如果你的项目环境允许,直接把 Python 版本升级到 3.10 或更高,就可以直接使用 timedelta | None 的写法,无需修改代码。
总结
- 报错根源:Python 版本 < 3.10 不支持
|联合类型语法,将其识别为非法运算符。 - 快速修复:导入
typing.Union,用Union[timedelta, None]替代timedelta | None。 - 长期方案:升级 Python 到 3.10+,保留更简洁的
|语法。