用FastAPI+Redis 复刻常驻Agent

结论先行:OpenAI 的 dots、Meta 的 Muse 把「智能体」从「你召唤一次它干一次」变成了「7×24 在后台替你盯目标」。这种常驻 Agent 到底凭什么算范式跃迁?核心不是模型多强,而是三件事,状态要持久、循环要可控、工具要可恢复。本文用一个 FastAPI + Redis 的最小骨架,把这套思路本地跑通。

一、原理:常驻 Agent 到底和普通脚本差在哪普通 Agent 是「请求,响应」:你发一句话,它答一句,进程结束,记忆清零。常驻 Agent(always-on agent)多了一层:它有自己的目标,会在后台持续轮询、执行、记录反馈,并在崩溃后从断点恢复 。OpenAI dots 的设计要点是「跑在自己的云电脑上、从反馈里学习、接 4000+ 应用」;Meta Muse 则是「在独立安全 VM 里后台管理目标,敏感动作要你批准」。抽象出来就三件套:状态存储(记住目标和进度)、执行循环(定时或事件驱动地干活)、工具接口(调 API / 发消息 / 读写文件) 。比如 一个「盯竞品价格」的常驻 Agent,状态里存着「上一次看到的最低价」,循环每 30 分钟抓一次页面,工具负责发钉钉通知。例如 一个「每日周报」Agent,状态里记着「已收集的素材列表」,循环在每天 18:00 触发汇总并写文档。差别就在「它替你记得,且会自己动」。## 二、环境准备bashpip install fastapi uvicorn redis openaidocker run -d --name agent-redis -p 6379:6379 redis:7Redis 承担三件事:目标队列(pending tasks)、状态快照(agent state)、反馈日志(feedback log)。用 Redis 而不是内存,是为了进程重启后不丢上下文。## 三、最小化常驻 Agent 骨架下面这个 FastAPI 应用实现了「提交目标 → 后台循环执行 → 记录反馈 → 可恢复」的完整闭环:```pythonimport asyncio, json, time, openaiimport redis.asyncio as aioredisfrom fastapi import FastAPI, BackgroundTasksapp = FastAPI()r = aioredis.Redis(host="localhost", port=6379, decode_responses=True)MODEL = "gpt-6-sol" # 按你自己的可用模型替换client = openai.AsyncOpenAI()async def exec_step(goal_id: str, step: str) -> str: # 1) 读当前状态 state = json.loads(await r.get(f"agent:{goal_id}:state") or "{}") # 2) 调模型推进一步 resp = await client.chat.completions.create( model=MODEL,

复制代码
    messages=[            {"role": "system", "content": f"你是常驻执行体,目标={state.get('goal')}"},            {"role": "user", "content": f"下一步执行:{step}。当前进度:{state}"},        ],        max_tokens=400,    )    result = resp.choices[0].message.content    # 3) 写回状态 + 追加反馈日志    state["last_result"] = result    state["updated_at"] = int(time.time())    await r.set(f"agent:{goal_id}:state", json.dumps(state))    await r.rpush(f"agent:{goal_id}:feedback", json.dumps({"step": step, "result": result}))    return resultasync def loop_until_done(goal_id: str):    while True:        state = json.loads(await r.get(f"agent:{goal_id}:state") or "{}")        if state.get("done"):            break        plan = state.get("plan", [])        idx = state.get("cursor", 0)        if idx >= len(plan):            break        await exec_step(goal_id, plan[idx])        await r.hset(f"agent:{goal_id}:state", "cursor", idx + 1)  # 断点可恢复        await asyncio.sleep(2)  # 控制节奏,避免打爆 API@app.post("/goal")async def submit_goal(goal: str, plan: list[str], bg: BackgroundTasks):    goal_id = f"g_{int(time.time())}"    await r.set(f"agent:{goal_id}:state", json.dumps(        {"goal": goal, "plan": plan, "cursor": 0, "done": False}))    bg.add_task(loop_until_done, goal_id)    return {"goal_id": goal_id, "status": "running"}```提交一个目标:`curl -XPOST /goal?goal=每日汇总竞品价格&plan=["抓页面","比价","写周报"]`,后台就会按步执行,每一步结果都落 Redis。进程挂了重启,从 `cursor` 接着跑,不会重复第一步。

四、工程取舍1. 轮询 vs 事件驱动 :简单场景用 asyncio.sleep 轮询最稳;实时性要求高就改成消息队列(Redis Stream / Kafka)触发。轮询的好处是逻辑直观、易于本地复现。2. 状态放 Redis 还是数据库 :Redis 快、适合热状态;但长期目标建议异步落 PostgreSQL,避免 Redis 重启丢历史。比如 feedback log 让它同时写一份到文件,排查时直接 cat。3. 模型调用粒度 :每一步都调一次模型很贵。把「能本地算的」(格式化、比对、去重)留在 Python 里,只把「需要判断的」交给模型,成本能砍掉一大半。## 五、踩坑清单- 忘记给状态加 TTL,Redis 撑爆 :pending 队列和 feedback log 要设 EXPIRE,比如 7 天,否则常驻 Agent 跑一个月能把内存写满。- 崩溃后重复执行 :必须像上面那样用 cursor 做幂等断点;否则重启会从头再来一遍,重复发通知被拉黑。- 反馈循环被污染 :如果 Agent 把「上一步的结果」又当成「新目标」喂回自己,会陷入自指循环。每次写 feedback 要打 step 标签,循环里只消费 plan[cursor],绝不回读 feedback 当输入。- 敏感动作没拦 :常驻 Agent 最容易出事的就是「自己决定发邮件 / 转账」。所有写外设的动作必须加 human_approval 开关,参考 Muse 的「敏感动作需批准」设计。## 六、辩证:常驻不等于永远正确必须泼盆冷水:7×24 在线带来的是「持续在动」,不是「持续做对」。常驻 Agent 的风险在于它会在你睡着时默默犯错,错误通知刷屏、误删数据、把半成品发出去。工程上要守住三条线:敏感动作人工确认、失败自动暂停而非硬撑、关键结果留可审计日志。24 小时跑模型调用是有真金白银成本的,不是所有任务都值得「常驻」,一次性脚本能解决的就别让它睡在后台烧钱。## 互动提问如果你要给自己搭第一个常驻 Agent,最想让它替你盯什么?1. 是信息类(竞品 / 股价 / 论文更新)的定期汇总?2. 还是执行类(定时发报告 / 自动回复 / 数据同步)的重复劳动?3. 又或者是决策类(异常自动告警 + 建议)的监控哨兵?欢迎在评论区聊聊你的第一个常驻场景,或者你最担心的「它半夜干傻事」会是什么?## 数据与事件来源:- OpenAI 发布 dots 常驻智能体公告(GPT-6 Astra 驱动,7×24、自学习、接 4000+ 应用)- Meta 发布 Muse 个人智能体说明(MuseSecureVM 隔离、后台管理目标、敏感动作需批准)- AIBriefs 2026-10-02 AI 日报(dots 与 Muse 同周上线,常驻 Agent 成为产品范式)- 各厂商 API 文档与发布说明(FastAPI / Redis / OpenAI AsyncClient 接口规范)

相关推荐
ly76895 小时前
Redis 主从复制全解析:从 PSYNC 协议到复制积压缓冲区的故障切换边界
java·数据库·redis·主从复制·故障切换·psync
hweiyu006 小时前
Redis命令:HPEXPIREAT
redis·缓存
ShineWinsu9 小时前
对于Redis:ZSet类型的解析
数据库·c++·redis·缓存·面试·有序集合·zset
新鲜势力呀9 小时前
PHP 定时任务系统实战:从 Cron 混乱执行到任务调度中心 + Redis队列 + 失败重试
android·java·redis
hweiyu0010 小时前
Redis命令:HPTTL
redis·缓存
imDwAaY10 小时前
Redis List 是链表吗?从 Ziplist 到 Quicklist 揭开底层实现
redis·后端
知守观10 小时前
从三个带病的 Guava 本地缓存出发:Redis + Guava 二级缓存的读写路径与失效设计推演
java·redis·后端
imDwAaY10 小时前
Redis Set 如何节省内存?从整数集合到哈希表的设计取舍
数据结构·redis·散列表