Devin+RPA 项目实战复盘:AI 编程 Agent 生成脚本的稳定性优化与工程化落地|TaoToken 统一 Key 接入

发布时间:2026/10/8 17:44:57
Devin+RPA 项目实战复盘:AI 编程 Agent 生成脚本的稳定性优化与工程化落地|TaoToken 统一 Key 接入
1. Devin 生成脚本跑一周就崩问题到底出在哪Devin 这类 AI 编程 Agent 最让人上头的地方就是它能在很短时间内把一个想法变成能跑的脚本。我接过一个电商竞品监控的活客户要每天从几个平台抓价格、库存和促销信息人工做要花大半天。用 Devin 搭原型自动登录、翻页、提取字段、导出表格一个下午就跑通了。当时觉得这事稳了。结果交付后一周报错十几个。不是逻辑错是脚本太脆了。Devin 生成的代码本质上是基于生成那一刻的页面结构写死的快照它假设 DOM 永远不变、网络永远通畅、登录态永远有效。但真实业务里前端改版、A/B 测试、节日活动页、验证码弹窗任何一个变量都能让脚本当场挂掉。这就是 AI 编程 Agent 生成脚本的稳定性问题原型阶段效率极高生产阶段维护成本极高。Demo 能跑不等于能长期跑中间隔着一整套工程化落地的工作。这篇复盘就围绕这个 gap 展开讲清楚怎么把 Devin 生成的脚本从能跑一次推进到跑一个月不报警同时给出可复制的 Agent 配置片段和 TaoToken 统一 Key 接入步骤。适合谁看正在用 Devin、Cursor、Claude Code 这类 AI 编程 Agent 做 RPA 或自动化脚本的开发者手里有 Demo 级脚本但不知道怎么工程化的团队以及想搞清楚 AI 生成代码和 RPA 引擎怎么分层协作的人。核心检索词先摆出来Devin 生成脚本稳定性优化、AI 编程 Agent 工程化落地、RPA 脚本异常重试与版本管理。这三个词基本覆盖了从原型到生产的全部痛点。先说结论后面展开AI 负责生成主逻辑RPA 引擎负责稳定执行两者分层协作而不是互相替代。Devin 写代码快但它不负责长期运行RPA 引擎不擅长从零生成复杂逻辑但它擅长元素自愈、异常兜底、定时调度和授权分发。把这两件事分开架构就清晰了。我踩过的坑里最典型的是把 Devin 生成的 xpath 直接用到生产。那段代码长这样price_elem wait.until( EC.presence_of_element_located( (By.XPATH, //div[classprice-box]/span[classnum]) ) )生成当天能跑因为页面就是那个结构。但目标站点做了一次 A/B 测试价格容器的 class 从price-box变成了price-box-v2脚本立刻失效。这不是 Devin 的错它只能看到生成时刻的页面。问题在于我们把快照当成了契约。所以第一步要建立的认知是AI 生成的定位策略是建议不是真理。生产环境需要的是能自愈的定位机制而不是写死的路径。这个认知转变是后面所有工程化工作的前提。2. TaoToken 统一 Key 接入给 Agent 一个稳定的模型入口在讲脚本稳定性之前先把模型接入这块理顺。因为不管是 Devin 还是其他 AI 编程 Agent只要涉及调用大模型 API就会遇到一个现实问题不同模型厂商的 Key 格式不一样、计费方式不一样、限流策略不一样。项目里如果同时用 DeepSeek 做推理、用豆包做快速响应、用 Kimi 处理长文本光是管理这些 Key 就够头疼的。TaoToken 解决的就是这个统一入口的问题。它提供一个兼容 OpenAI 格式的 API 端点你可以用同一套 Key 调用多个模型切换模型只需要改 model 字段。对 RPA 场景来说这意味着脚本里的模型调用逻辑可以标准化不用为每个厂商写一套适配代码。官网地址是 https://taotoken.net/?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewriteutm_content API 端点是 https://taotoken.net/api 注意 API 地址不带 UTM 参数。接入方式很直接。如果你用的是 Claude Code 这类工具配置 Base URL 指向 TaoToken 的端点Key 填你在控制台生成的 KeyModel ID 填你要用的模型名。这三件套是固定的Base URL、Key、Model ID。缺一个都连不上。对于 Devin 生成的脚本我通常会在项目里放一个统一的模型调用封装把 TaoToken 的配置集中管理。这样脚本里只调用封装函数不直接写 API 细节。好处是换模型、换 Key、加限流都只改一个地方。具体到配置环境变量方式最省事export TAOTOKEN_BASE_URLhttps://taotoken.net/api export TAOTOKEN_API_KEYsk-你的Key export TAOTOKEN_MODELdeepseek-v4然后在 Python 里这样调用import os from openai import OpenAI client OpenAI( base_urlos.environ[TAOTOKEN_BASE_URL], api_keyos.environ[TAOTOKEN_API_KEY], ) def ask_model(prompt: str, model: str None) - str: resp client.chat.completions.create( modelmodel or os.environ[TAOTOKEN_MODEL], messages[{role: user, content: prompt}], timeout30, ) return resp.choices[0].message.content这段封装的价值在于RPA 脚本里所有需要 AI 判断的地方比如这个页面是不是验证码页这条促销信息是不是目标品类都走ask_model。模型换了、Key 换了脚本不用动。如果你用的是 Cline 或类似的 VS Code 插件配置方式是在 settings 里填 Base URL 和 Key。Cline 的 MCP 配置里模型提供方选 OpenAI CompatibleBase URL 填 TaoToken 端点Model ID 填对应模型。这样 Cline 里的对话和代码生成都走统一入口。对于 Codex 这类需要 auth.json 的工具配置结构大致是{ base_url: https://taotoken.net/api, api_key: sk-你的Key, model: deepseek-v4 }注意 auth.json 的字段名不同工具可能不一样以官方文档为准。接入文档在 https://taotoken.net/doc 里面有各工具的详细配置说明。为什么要先讲这个因为脚本稳定性优化里有一环是模型调用失败的重试与降级。如果模型入口是统一的重试逻辑就只需要写一套如果每个厂商一套 Key重试逻辑会变得很乱。统一 Key 是工程化的基础设施。另外提一句成本控制。RPA 场景是高频持续调用如果每次都走云端大模型做判断月度账单会很难看。我的做法是确定性逻辑用本地规则引擎跑只有需要语义判断的环节才调模型。TaoToken 按量计费用多少付多少配合这种能本地就本地的策略成本可控。3. 可复制的 Agent 配置与脚本稳定性改造这一节是核心给出可以直接抄的配置和改造步骤。目标是把 Devin 生成的脆弱脚本改造成带重试、带自愈、带版本管理的生产级流程。3.1 Agent 配置片段先给一份 Agent 的配置模板适用于 Cline、Claude Code 这类支持自定义模型端点的工具。以 JSON 格式为例{ provider: openai-compatible, baseUrl: https://taotoken.net/api, apiKey: sk-你的Key, modelId: deepseek-v4, temperature: 0.2, maxTokens: 4096, timeout: 60000, retry: { maxAttempts: 3, backoffMs: 1000, retryOn: [timeout, rate_limit, 5xx] } }几个参数说明。temperature设 0.2 是因为脚本生成需要确定性太高会引入随机性。timeout设 60 秒因为复杂脚本生成可能耗时较长。retry块是关键AI 编程 Agent 调用模型时也会遇到限流和超时内置重试能减少人工干预。如果你用 TOML 格式比如某些 CLI 工具等价配置是[model] provider openai-compatible base_url https://taotoken.net/api api_key sk-你的Key model_id deepseek-v4 temperature 0.2 max_tokens 4096 timeout 60000 [model.retry] max_attempts 3 backoff_ms 1000 retry_on [timeout, rate_limit, 5xx]这份配置的作用是让 Agent 在生成脚本时有一个稳定的模型后端。Base URL、Key、Model ID 三件套齐全缺一不可。3.2 脚本稳定性改造从写死到自愈Devin 生成的脚本元素定位通常是写死的 xpath。改造的第一步是引入多候选定位和自愈机制。思路是这样不依赖单一 xpath而是为每个目标元素准备多个候选定位策略按优先级依次尝试。如果全部失败触发 AI 自愈——把页面截图或 DOM 片段发给模型让它重新推断定位方式。from selenium.webdriver.common.by import By from selenium.common.exceptions import NoSuchElementException def find_element_with_fallback(driver, candidates): candidates: 候选定位列表每项是 (By, value) 元组 按顺序尝试返回第一个成功的元素 for by, value in candidates: try: return driver.find_element(by, value) except NoSuchElementException: continue return None # 使用示例价格元素的多候选定位 price_candidates [ (By.CSS_SELECTOR, [data-testidprice]), (By.XPATH, //div[contains(class,price)]//span[contains(class,num)]), (By.XPATH, //span[classprice-now]), ] price_elem find_element_with_fallback(driver, price_candidates) if price_elem is None: # 触发 AI 自愈截图 DOM 片段发给模型 healed ai_heal_locator(driver, 商品价格)ai_heal_locator的实现走 TaoToken 统一入口def ai_heal_locator(driver, target_desc: str): dom_snippet driver.page_source[:5000] prompt f页面中需要定位「{target_desc}」元素。 以下是页面 DOM 片段 {dom_snippet} 请给出 3 个最稳定的 CSS 选择器按稳定性排序只输出选择器每行一个。 result ask_model(prompt) selectors [s.strip() for s in result.splitlines() if s.strip()] for sel in selectors: try: return driver.find_element(By.CSS_SELECTOR, sel) except NoSuchElementException: continue return None这套机制的价值在于页面小改版时多候选定位能兜住页面大改版时AI 自愈能重新推断。两者结合脚本的存活周期从几天延长到几个月。3.3 异常重试与日志分级原型脚本几乎没有异常处理。生产脚本必须给每个关键步骤包上重试和日志。import time import logging logging.basicConfig( levellogging.INFO, format%(asctime)s [%(levelname)s] %(message)s, handlers[ logging.FileHandler(rpa_run.log), logging.StreamHandler(), ], ) logger logging.getLogger(rpa) def retry_on_failure(func, max_attempts3, backoff2, *args, **kwargs): for attempt in range(1, max_attempts 1): try: return func(*args, **kwargs) except Exception as e: logger.warning(f第 {attempt} 次尝试失败: {e}) if attempt max_attempts: logger.error(f重试 {max_attempts} 次后仍失败放弃) raise time.sleep(backoff ** attempt)日志分级的意义在于排障。INFO 记录正常流程节点WARNING 记录重试ERROR 记录最终失败。配合截图留痕出问题时能快速定位是页面变了、网络抖了还是登录态过期了。3.4 版本管理脚本也要有 gitDevin 生成的脚本迭代很快如果没有版本管理改着改着就不知道哪版能跑了。我的做法是每个脚本目录都初始化 git每次 AI 生成或人工修改后提交一次commit message 写清楚改了什么、为什么改。cd rpa-scripts git init git add . git commit -m feat: 初始版本Devin 生成的价格抓取脚本 # 改造后 git commit -m fix: 价格元素改为多候选定位 AI 自愈修复 A/B 测试导致的失效更进一步可以把脚本的配置项目标 URL、字段映射、重试次数抽到单独的 config.yaml脚本逻辑和配置分离。这样换站点、调参数不用改代码版本管理也更清晰。# config.yaml target: url: https://example-mall.com fields: price: candidates: - [data-testidprice] - //div[contains(class,price)]//span stock: candidates: - [data-testidstock] retry: max_attempts: 3 backoff: 2脚本读取 config.yaml 来驱动定位和重试Devin 生成的硬编码逻辑就被替换成了可配置的流程。这一步做完脚本才算真正具备了工程化的底子。4. 验证请求与成功结果怎么确认脚本真的稳了改造完不能凭感觉说应该稳了要有可验证的标准。这一节给出验证方法和成功结果的判断依据。4.1 模型接入验证先确认 TaoToken 统一 Key 能正常调用。用 curl 发一个最小请求curl https://taotoken.net/api/chat/completions \ -H Content-Type: application/json \ -H Authorization: Bearer sk-你的Key \ -d { model: deepseek-v4, messages: [{role: user, content: 回复 OK}], max_tokens: 10 }成功的话返回 JSON 里choices[0].message.content会有内容。如果返回 401说明 Key 有问题如果返回 404检查 Base URL 是不是写成了带路径的形式如果超时检查网络和端点可达性。Python 侧验证result ask_model(回复 OK) print(result) # 期望输出包含 OK这一步过了说明模型入口通了后面脚本里的 AI 调用才有基础。4.2 脚本稳定性验证清单我整理了一份验证清单每次改造完脚本都跑一遍验证项方法通过标准元素定位手动改页面 class 后重跑多候选或自愈能兜住网络抖动用弱网工具模拟延迟重试机制生效不崩溃登录态过期清除 cookie 后重跑能检测到并重新登录弹窗拦截触发活动弹窗后重跑能识别并关闭弹窗模型超时断网后触发 AI 调用降级到本地规则或报错可控日志完整性检查 rpa_run.log每个关键节点有记录版本可回滚git log 查看历史能定位到上一可用版本这份清单跑完脚本的稳定性就有底了。重点说两个容易忽略的登录态过期和模型超时。登录态过期是 RPA 最常见的崩溃原因。脚本跑着跑着 cookie 失效了后续所有操作都失败。改造方法是在每个关键步骤前检查登录态失效则触发重新登录流程。重新登录本身也要有重试和验证码处理分支。模型超时的降级策略是AI 调用失败时不直接崩溃而是回退到本地规则。比如价格提取AI 自愈失败就用正则从 DOM 里捞数字。降级不完美但比崩溃强。4.3 成功结果的判断脚本跑通一次不算成功。我的判断标准是连续运行 7 天无人工干预日志里 ERROR 级别记录为 0WARNING 记录在可接受范围内比如每天不超过 3 次重试。达到这个标准脚本才算从 Demo 级进入生产级。这时候可以打包交付了。打包交付的形态很关键。客户是业务人员不可能让他们配 Python 环境。生产交付需要的是可执行文件双击就能跑。如果平台支持导出 EXE 并带授权管理交付门槛会低很多。授权管理包括授权码、有效期、加密分享这些是工程化交付的标配。5. 本篇常见错排查401、local proxy failed、reading choices、OAuth这一节对照真实报错给出排查路径。这些错我在项目里都遇到过按顺序排查基本能解决。5.1 401 Unauthorized最常见。原因通常是 Key 无效、Key 过期、或者 Key 和 Base URL 不匹配。排查步骤先确认 Key 是从 TaoToken 控制台生成的没有多余空格。然后确认 Base URL 是https://taotoken.net/api注意结尾没有多余的斜杠或路径。如果用的是环境变量打印出来确认没有引号包裹问题。import os print(repr(os.environ.get(TAOTOKEN_API_KEY))) print(repr(os.environ.get(TAOTOKEN_BASE_URL)))repr能看出有没有隐藏字符。如果 Key 正确但还报 401检查是不是把 Key 用在了错误的端点上。5.2 local proxy failed这个报错通常出现在工具配置了本地代理但代理没启动或者代理配置和实际网络环境冲突。排查方向检查工具的代理设置确认是否需要代理。如果不需要把代理配置清空。如果需要确认代理服务在运行。注意这里说的是工具自身的网络配置不是让你去搞什么特殊网络手段。企业内网环境通常有统一的网络出口按 IT 规范配置即可。5.3 reading choices 相关报错典型报错是KeyError: choices或reading choices。这说明返回的 JSON 结构里没有choices字段通常是请求失败但代码没检查状态码。修复方法是在解析前先检查响应resp client.chat.completions.create(...) if not resp.choices: logger.error(f响应无 choices: {resp}) raise RuntimeError(模型返回异常) return resp.choices[0].message.content更稳妥的做法是捕获异常并记录完整响应方便排查是模型名写错了、还是请求格式不对。5.4 OAuth 相关报错如果工具用 OAuth 方式认证报错通常是 token 过期或回调地址不匹配。排查确认 OAuth 配置里的回调地址和实际一致确认 token 没有过期。如果是 Claude Code 这类工具检查认证方式是不是选对了有些工具支持 API Key 和 OAuth 两种模式混用会报错。5.5 模型名不存在报错类似model not found。原因是 Model ID 写错了。TaoToken 的模型名以控制台和文档为准不要凭记忆写。常见错误是把deepseek-v4写成deepseek-v4.0或DeepSeek-V4大小写和版本号都要对。排查完这些模型接入基本就通了。接入文档在 https://taotoken.net/doc API Keys 管理在 https://taotoken.net/api-keys 遇到问题先查文档。6. 把 Demo 推进到生产分层协作与持续维护回到最开始的问题Devin 生成的脚本为什么跑一周就崩因为它生成的是快照不是流程。快照假设环境不变流程假设环境会变并为此做好准备。工程化落地的核心是建立分层协作的架构。AI 层负责生成和自愈RPA 层负责稳定执行和调度配置层负责参数和版本管理。三层各司其职脚本的存活周期才能从几天延长到几个月。具体到日常维护我的习惯是每周检查一次日志看 WARNING 和 ERROR 的分布每月跑一次稳定性验证清单每次目标站点改版后第一时间更新候选定位并提交 git。这些动作不复杂但坚持下来脚本的稳定性会有质的提升。如果你正在做类似的项目建议从最小可用开始先用 Devin 生成原型验证思路然后按这篇的步骤补上多候选定位、重试、日志、版本管理最后打包交付。不要一上来就追求完美架构迭代着来更实际。需要长期跑编码和 Agent 任务的团队可以了解下 Coding Plan地址是 https://taotoken.net/coding-plan?utm_sourcetaotoken_aicg_blog_endutm_contentcoding_planutm_campaignrewrite 。想先验证模型效果的可以直接在模型对话页面试地址是 https://taotoken.net/chat?utm_sourcetaotoken_aicg_blog_endutm_contentmodel_chatutm_campaignrewrite 。接入配置和 API Keys 管理分别在 https://taotoken.net/doc?utm_sourcetaotoken_aicg_blog_endutm_contentdocutm_campaignrewrite 和 https://taotoken.net/api-keys?utm_sourcetaotoken_aicg_blog_endutm_contentapi_keysutm_campaignrewrite 。最后说一个实操细节脚本里的 AI 调用一定要设超时和降级。我见过太多脚本因为一次模型调用卡住整个流程挂起半小时。超时设 30 秒失败降级到本地规则这样即使模型侧有波动流程也不会停。这个细节不起眼但它是生产级和 Demo 级的分水岭。