Python给接口加一个装饰器:登记操作记录、接口加锁
1. 登记操作记录:将用户信息、uri、提交的信息存储在数据库
2. 接口加锁:将接口及携带的信息缓存到redis中,访问这个接口时,若接口响应慢,只有等接口响应完后,才可以再次访问接口
一:登记操作记录
1. modul层
class UserOperateRecordModel(BaseModel):
"""用户表"""
class Meta:
db_table = "user_operate_record"
id = AutoField(primary_key=True)
userid = CharField(verbose_name='用户ID', null=False, default="")
method = CharField(verbose_name='请求方式', null=False, default="")
uri = CharField(verbose_name='操作uri', null=False, default="")
params = JSONCharField(verbose_name='操作参数', null=False, default="")
update_time = DateTimeField(verbose_name="更新时间")
create_time = DateTimeField(verbose_name="创建时间", null=False, default=datetime.datetime.now)
2. 装饰器层
def operate_record(func):
"""登记操作记录"""
@functools.wraps(func)
def _wrapper(handler, *args, **kwargs):
uri = handler.request.path
method = handler.request.method
userid = handler.task_node.userid or ""
params = handler.json_param
try:
UserOperateRecordModel.\
create(userid=userid,
method=method,
uri=uri,
params=params,
)
except:
raise HaomoError(1, '登记操作记录失败')
return func(handler, *args, **kwargs)
return _wrapper
3. handler层
from common.decorations import locker, operate_record
class TaskHandler(TaskBaseHandler):
@operate_record
@locker(key_str="mc_task_modify:{task_id}",
key_args=[("task_id", "self", lambda x: x.get_param("task_id", 0))],
expire=10)
def put(self):
"""修改任务配置"""
task_id = self.get_param('task_id', 0)
task_type = self.get_param('task_type', '')
visual_type = self.get_param('visual_type', '')
if not all((task_id, task_type, visual_type)):
raise HaomoError(1, '参数不合法')
if task_type not in DIST_CONFIG.task_type.values:
raise HaomoError(1, '任务类型不合法')
task_type = DIST_CONFIG.task_type[task_type]
task_srv = TaskService.get_by_id(task_id)
if not task_srv:
raise HaomoError(1, '总任务不存在')
task_srv.update(task_type=task_type, visual_type=visual_type)
二、 接口响应加锁
1. 装饰器层
def locker(key_str, key_args=None, expire=3, is_raise=True):
"""redis locker"""
def _cache(fn):
@functools.wraps(fn)
def _wrap(*args, **kwargs):
argvalues = inspect.getcallargs(fn, *args, **kwargs)
cache_key = HMCache.get_cache_key(key_str, key_args, argvalues)
rd = RedisConnector.get("redis")
if not rd.set(cache_key, 1, ex=expire, nx=True):
gen_log.info("获取锁失败 key=%s", cache_key)
if is_raise:
raise HaomoError(-1, "获取锁失败", cache_key=cache_key)
return False
try:
if args and kwargs:
return fn(*args, **kwargs)
elif args and not kwargs:
return fn(*args)
elif not args and kwargs:
return fn(**kwargs)
else:
return fn()
except HaomoError as he:
raise he
finally:
rd.delete(cache_key)
return _wrap
return _cache
2. handler层
from common.decorations import locker, operate_record
class TaskHandler(TaskBaseHandler):
@operate_record
@locker(key_str="mc_task_modify:{task_id}",
key_args=[("task_id", "self", lambda x: x.get_param("task_id", 0))],
expire=10)
def put(self):
"""修改任务配置"""
task_id = self.get_param('task_id', 0)
task_type = self.get_param('task_type', '')
visual_type = self.get_param('visual_type', '')
if not all((task_id, task_type, visual_type)):
raise HaomoError(1, '参数不合法')
if task_type not in DIST_CONFIG.task_type.values:
raise HaomoError(1, '任务类型不合法')
task_type = DIST_CONFIG.task_type[task_type]
task_srv = TaskService.get_by_id(task_id)
if not task_srv:
raise HaomoError(1, '总任务不存在')
task_srv.update(task_type=task_type, visual_type=visual_type)
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列:基于图像分类模型对图像进行分类
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 25岁的心里话
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 按钮权限的设计及实现