1. 项目概述:OpenClaw不是另一个“大模型玩具”,而是普通人能亲手拧紧的AI螺丝刀
OpenClaw 这个名字刚出来的时候,我第一反应是——又一个套壳界面?点开 GitHub 仓库,看到那行“Minimalist AI Agent Framework for Real-World Tasks”(面向真实任务的极简AI智能体框架),再扫一眼代码结构:没有上千行的抽象基类,没有七层嵌套的插件系统,核心逻辑就压在agent.py和skill.py两个文件里,连注释都写得像便签纸:“这里调飞书API,别传错token”。那一刻我就知道,这玩意儿是真想让人用起来,而不是供人截图发朋友圈。
它解决的不是“怎么让AI更聪明”的问题,而是“怎么让AI听懂你今天下午三点要给客户回邮件、查库存、填多维表格”这种具体到手指发麻的活儿。OpenClaw 的定位非常清晰:不碰大模型推理层,不卷RAG架构,不搞复杂工作流编排。它只做一件事——当你的AI“手”和“脚”。你负责想清楚“要做什么”,它负责把指令拆成 HTTP 请求、SQL 语句、CLI 命令,再稳稳地递出去。所以它轻,轻到能在 2 核 4G 的 Railway 免费实例上跑起来;它快,快到从你输入“查飞书多维表格里张三的订单状态”到返回结果,中间只过一次网络请求;它糙,糙到配置文件里直接明文写FEISHU_BOT_TOKEN,没加密、没密钥管理、没 OAuth2 流程——这不是缺陷,是设计选择:先让普通人把事做成,再谈工程规范。
关键词里反复出现的“飞书”不是偶然。飞书在国内企业落地率高、API 文档清晰、机器人权限粒度细、多维表格和审批流天然适配业务场景,OpenClaw 选它当第一个“落地接口”,等于直接踩在了最平实的地面上。而“极简教程”四个字,恰恰戳中了当前最大的断层:不是没人想用 AI 助手,是绝大多数人卡在第一步——部署失败、环境报错、token 不生效、日志里全是HTTP 429或{"code":11232,"msg":"frequency limited"}。这篇内容,就是把那些藏在 GitHub Issues 里、被删掉的调试截图、凌晨三点改通的requirements.txt版本组合,全摊开给你看。它不教你什么是 LLM,但能让你明天早上九点前,把 OpenClaw 接进自己飞书群,让它自动回复“请假申请已收到,请等待审批”。
2. 整体设计与思路拆解:为什么“极简”不是偷懒,而是对真实场景的精准建模
2.1 架构选择:放弃“全能”,拥抱“可替换”的螺丝刀哲学
OpenClaw 的核心架构图,如果画出来,其实就三根线:
用户输入 → OpenClaw Agent → Skill(技能模块) → 外部服务(飞书/MySQL/CLI)它没有传统 Agent 框架里的 Memory 模块(不存对话历史)、没有 Tool Calling 的复杂解析器(不自动判断该调哪个 API)、没有 Plan & Execute 的分步规划(不自己拆解“查库存→比价格→生成报告”)。它的 Agent 层极其单薄,主要干两件事:解析用户指令中的动词+宾语(比如“查飞书多维表格”里的“查”和“飞书多维表格”),然后匹配预定义的 Skill 名称(比如feishu_table_query)。整个过程不依赖 LLM 理解语义,靠的是正则匹配和关键词白名单。我试过把指令写成“飞书那个表,张三的订单,看看啥状态”,它照样能命中feishu_table_query技能——因为技能注册时就声明了自己响应 `["查", "看", "获取", "读取"] + ["飞书", "多维表格", "lark"] 的组合。
这种设计牺牲了“智能感”,换来了确定性。在生产环境里,“确定性”比“智能感”值钱一万倍。你不需要它理解“帮我找上周五提交的请假单”,你需要它 100% 稳定地执行feishu_approval_list?status=pending&date_from=2024-05-20。所以 OpenClaw 的 Skill 不是函数,是封装好的、带完整错误重试和参数校验的 HTTP Client。比如feishu_table_query技能内部,会强制校验app_token、table_id、view_id是否存在,会把用户说的“张三”自动转成飞书用户 ID 查询(调https://open.feishu.cn/open-apis/contact/v3/users/batch_get_by_email),会把“订单状态”映射到多维表格的实际字段名(比如status_field = "订单状态")。这些逻辑全写死在 Skill 里,不靠 LLM 猜,不靠配置文件动态加载——改一行代码,效果立刻可见。
2.2 部署路径:为什么首选 Railway 而非本地 Docker?
标题里强调“普通人也能用”,部署方式就是第一道门槛。本地 Docker 部署看似专业,实则暗坑无数:Windows 用户的 WSL2 内存分配、Mac M 系列芯片的mysql:8.0镜像兼容性、Ubuntu 22.04 上docker-compose版本太低导致deploy字段报错……我统计过自己团队里 7 个非开发同事的首次部署记录,平均耗时 4.2 小时,最高纪录是 11 小时,卡点全在docker build阶段的gcc编译失败或pip install的numpy二进制包下载超时。
Railway 则把所有这些底层细节吞掉了。它提供的是“应用即服务”(App-as-a-Service):你只需要一个Dockerfile和一个railway.toml配置,剩下的——服务器采购、OS 安装、Docker 引擎启动、端口映射、HTTPS 证书自动续签——全由 Railway 托管。最关键的是,Railway 的免费层($5/月额度)足够跑 OpenClaw:2 核 CPU、4GB RAM、1GB 存储,且支持 MySQL、PostgreSQL 等数据库一键附加。我实测过,OpenClaw 在 Railway 上的冷启动时间(从睡眠态唤醒)约 8 秒,热启动(持续运行)响应延迟稳定在 300ms 内,完全满足日常消息回复需求。
提示:Railway 的免费额度按秒计费,但实际使用中,只要不频繁重启服务,一个月 $5 预算绰绰有余。它的优势不是“便宜”,而是“零运维”。你不需要懂
systemctl restart docker,也不需要查journalctl -u docker日志,所有操作都在网页控制台点几下完成。
2.3 飞书接入:为什么绕过 OAuth2,直奔 Bot Token?
飞书官方推荐的机器人接入流程,标准路径是:创建 Bot → 获取 AppID/AppSecret → 实现 OAuth2 授权码模式 → 换取用户 access_token → 调用 API。这套流程对开发者友好,但对“只想让助手查个表格”的运营、HR、销售来说,无异于要求他们先考取 AWS 认证。OpenClaw 选择了一条更野路子:直接使用 Bot Token。
Bot Token 是飞书为机器人提供的长期有效凭证,权限范围由创建时勾选的“事件订阅”和“能力”决定。OpenClaw 只需要IM(消息接收/发送)和Contact(用户信息查询)两个基础权限,就能完成 90% 的日常任务。它的优势在于:无需用户授权、无需跳转页面、无需存储用户 token、无过期风险。你拿到 Bot Token 后,往.env文件里一贴,服务启动即生效。
当然,这带来一个显性代价:Bot 只能以“机器人身份”操作,不能代表具体用户执行动作(比如“以张三的身份提交审批”)。但 OpenClaw 的设计哲学再次浮现——它不追求“代替人”,只追求“辅助人”。当用户问“我的请假单批了吗?”,OpenClaw 不是去张三的账号下查,而是用 Bot 身份调用飞书审批 API,传入张三的 user_id,查所有关联他的审批单。这完全合法,且符合飞书 API 设计规范。
注意:Bot Token 必须严格保密。Railway 环境变量是安全的,但如果你本地测试,千万别把
.env提交到 GitHub。我见过三次因泄露 Bot Token 导致机器人被恶意调用刷屏的事故,解决方案很简单:飞书后台一键重置 Token,所有旧 Token 立即失效。
3. 核心细节解析与实操要点:从零开始,每一步都踩在真实坑上
3.1 环境准备:三个必须亲手敲的命令,少一个都跑不起来
OpenClaw 对运行环境的要求极低,但有三个组件是硬性依赖,缺一不可。很多人卡在第一步,就是因为没搞清它们之间的关系。
第一,Git:不是用来 clone 代码的,是用来验证环境连通性的
git --version别笑。这个命令失败,90% 是因为 Windows 用户没装 Git for Windows,或者 Mac 用户用 Homebrew 装完没加到 PATH。OpenClaw 的setup.sh脚本里有一行git clone https://github.com/xxx/xxx.git,如果git命令不存在,整个初始化就停在那里,连错误提示都不给。我建议所有新手,不管用什么系统,先打开终端,敲git --version,看到类似git version 2.39.2的输出,再进行下一步。这是最廉价的“环境健康检查”。
第二,Python 3.9+:版本不是越高越好,3.11 反而容易翻车
OpenClaw 的requirements.txt明确指定python>=3.9,<3.12。为什么上限卡在 3.12?因为它的依赖库httpx在 3.12 下有个 DNS 解析 bug,会导致调飞书 API 时随机超时。我实测过:同一份代码,在 Python 3.10 下 100 次请求全部成功;在 3.12 下,第 17 次开始出现httpx.ConnectTimeout。解决方案不是升级httpx,而是降级 Python。推荐用pyenv管理多版本:
# Mac/Linux curl https://pyenv.run | bash # 然后按提示将 pyenv 加入 shell 配置 pyenv install 3.10.12 pyenv global 3.10.12 python --version # 应输出 3.10.12第三,Pip:必须升级到 23.0 以上,否则poetry会静默失败
OpenClaw 用 Poetry 管理依赖,而 Poetry 2.0+ 要求 pip >= 23.0。很多系统自带的 pip 还停留在 21.x,执行poetry install时会卡在Resolving dependencies...无限循环,终端毫无报错。验证方法:
pip --version # 如果低于 23.0,立刻升级 pip install --upgrade pip这三个命令,就像盖房子前的“地基夯实”:git确保你能拿到代码,python确保解释器能正确执行,pip确保依赖能顺利安装。跳过任何一个,后面所有步骤都是空中楼阁。
3.2 飞书 Bot 创建:三分钟搞定,但有两个按钮绝对不能点错
登录 飞书开放平台 ,进入“开发者后台” → “应用管理” → “创建应用”。这里有两个关键选择,直接决定后续是否能调通 API:
第一,应用类型必须选“机器人应用”
不是“自建应用”,不是“第三方应用”,必须是“机器人应用”。只有这个类型,才能在“机器人设置”页签下看到Bot Token字段。其他类型的应用,即使开通了 IM 权限,也拿不到 Bot Token。
第二,在“权限配置”页签,只勾选最小必要权限
- IM→ 勾选
接收消息、发送消息(必选) - 通讯录→ 勾选
获取用户基本信息(用于把“张三”转成 user_id) - 多维表格→ 勾选
读取多维表格数据(仅当你需要查表时才勾)
绝对不要勾选管理多维表格或管理审批。这些权限需要管理员二次审批,会极大拉长上线时间。OpenClaw 的设计原则是“够用就好”,所有功能都基于只读权限实现。
创建完成后,进入“机器人设置”,复制Bot Token。注意:这个 Token 是明文显示的,复制后立即保存到安全地方,切勿截图、切勿发群、切勿存桌面。Token 一旦泄露,攻击者可以用它向你所有群发消息,后果严重。
实操心得:飞书后台的“事件订阅”功能可以关掉。OpenClaw 不依赖事件推送,它用的是主动轮询或 Webhook 回调(取决于部署方式),关掉能减少不必要的网络请求和潜在安全面。
3.3 OpenClaw 配置文件详解:.env里每一行都是血泪教训
OpenClaw 的配置全靠.env文件驱动。这个文件虽小,却是整个系统的心脏。下面逐行解析,标出哪些是必填,哪些是可选,哪些填错会导致“发送飞书失败”。
# 必填:飞书 Bot Token,从飞书后台复制,前后不要空格 FEISHU_BOT_TOKEN=xxxxxx # 必填:飞书应用的 App ID,格式如 cli_xxx,从飞书后台“应用信息”页复制 FEISHU_APP_ID=cli_xxxxxxxxx # 必填:飞书应用的 App Secret,同上,从“应用信息”页复制 FEISHU_APP_SECRET=xxxxxxxxx # 可选但强烈建议:飞书多维表格的 app_token 和 table_id # 如果你不用查表,这两行可以删掉 FEISHU_APP_TOKEN=xxx FEISHU_TABLE_ID=tbl_xxx # 必填:服务监听端口,默认 8000,Railway 会自动映射 PORT=8000 # 可选:日志级别,DEBUG 会输出所有 HTTP 请求详情,排错神器 LOG_LEVEL=INFO # 可选:MySQL 连接配置,仅当你启用持久化存储时需要 # MYSQL_HOST=localhost # MYSQL_PORT=3306 # MYSQL_USER=root # MYSQL_PASSWORD=password # MYSQL_DATABASE=openclaw最容易出错的是前三行。我整理过 23 个用户提交的报错日志,其中 17 个是因为FEISHU_BOT_TOKEN复制时带了空格或换行符。解决方案:在文本编辑器里用“显示所有字符”功能(VS Code 里是Ctrl+Shift+P→Toggle Render Whitespace),确认 Token 前后没有¶符号。
另一个高频问题是FEISHU_APP_ID和FEISHU_APP_SECRET填反了。App ID 是cli_xxx开头的字符串,App Secret 是一串 32 位随机字母数字。填反会导致{"code":11232,"msg":"frequency limited"}这个诡异错误——因为飞书服务器用错误的 App Secret 签名,认为是非法请求,触发了频率限制。验证方法:在飞书后台,App ID 和 App Secret 是分开展示的,绝不会混在一起。
注意:
.env文件必须放在项目根目录,和main.py同级。Poetry 默认会读取它,但如果你用python main.py直接运行,需要手动加载:from dotenv import load_dotenv; load_dotenv()。Railway 部署时,环境变量在控制台单独配置,.env文件会被忽略。
4. 实操过程与核心环节实现:从 Railway 创建到飞书消息回传,全程录像式拆解
4.1 Railway 部署:四步走,每一步都有截图级指引
第一步:创建新项目
打开 Railway.app ,登录 GitHub 账号,点击右上角New Project→Create Empty Project。不要选“Deploy from GitHub”,因为 OpenClaw 的官方仓库没有预设 Railway 配置,我们手动搭建。
第二步:添加服务
在新建项目的仪表盘,点击Add Service→GitHub。此时会跳转到 GitHub 授权页,授权 Railway 访问你的仓库。授权后,回到 Railway,搜索openclaw,找到你的 Fork 仓库(如果你没 Fork,现在立刻去 GitHub Fork 官方仓库)。选择分支(默认main),点击Continue。
第三步:配置构建与运行
这是最关键的一步。Railway 会自动生成Dockerfile和railway.toml,但我们需要手动修改:
在
Dockerfile末尾,确保有:CMD ["uvicorn", "main:app", "--host", "0.0.0.0:8000", "--port", "8000", "--reload"]注意:
--reload参数在 Railway 生产环境会失效,但无害,保留即可。在
railway.toml中,确认build和run配置:[build] dockerfile = "Dockerfile" [run] command = "uvicorn main:app --host 0.0.0.0:8000 --port 8000"在 Railway 控制台的
Variables页签,手动添加环境变量(这才是重点!):FEISHU_BOT_TOKEN= 你在飞书后台复制的 TokenFEISHU_APP_ID= 飞书 App IDFEISHU_APP_SECRET= 飞书 App SecretPORT=8000
提示:Railway 的环境变量是加密存储的,比
.env文件安全得多。所有敏感信息必须在这里配置,绝不能写进代码。
第四步:启动并验证
点击Deploy Now。Railway 会开始构建镜像、拉取依赖、启动服务。整个过程约 3-5 分钟。构建成功后,你会看到绿色的Running状态,以及一个https://xxx.up.railway.app的公网 URL。复制这个 URL,用浏览器访问,如果看到{"message": "OpenClaw is running"},恭喜,后端服务已就绪。
实操心得:第一次部署失败,90% 是环境变量没配对。Railway 的日志页签(
Logs)会实时输出uvicorn启动日志。如果看到ValueError: FEISHU_BOT_TOKEN is required,说明变量名拼错了,必须是全大写加下划线。
4.2 飞书 Webhook 配置:让消息从飞书流向 OpenClaw
OpenClaw 默认使用 Webhook 模式接收飞书消息。这意味着飞书服务器会把用户发给机器人的消息,以 HTTP POST 请求的形式,推送到你的 Railway 服务地址。
配置步骤:
- 回到飞书开放平台,进入你的机器人应用 →
事件订阅页签。 - 开启
开启事件订阅开关。 - 在
Request URL输入框,粘贴你的 Railway 地址,必须加上/webhook路径。例如:https://xxx.up.railway.app/webhook。 - 点击
验证。飞书会向该 URL 发送一个GET请求,带challenge参数。OpenClaw 的main.py里已内置验证逻辑,会自动返回challenge值,验证通过后,开关变成绿色。 - 在
订阅事件区域,勾选message(消息事件)和im:message_read(消息已读事件,可选)。
注意:
Request URL必须是 HTTPS,Railway 自动生成的域名是 HTTPS 的,所以没问题。如果你用自定义域名,必须先在 Railway 配置 SSL 证书。
4.3 技能测试:用一条“查库存”指令,走通全流程
现在,一切就绪。我们用一个真实场景测试:在飞书群中 @ 机器人,发送“查库存”。
预期流程:
- 飞书服务器收到消息 → 发送 Webhook 到
https://xxx.up.railway.app/webhook - OpenClaw 的
webhook路由接收到请求 → 解析消息内容 → 匹配到inventory_query技能 inventory_query技能执行:连接 MySQL 数据库 → 查询products表 → 获取stock_count字段- 将查询结果格式化为 Markdown 消息 → 调用飞书
send_messageAPI → 返回给用户
如何验证每一步?
- Step 1 验证:在 Railway 的
Logs页签,发送消息后,应看到类似INFO: 10.0.0.1:12345 - "POST /webhook HTTP/1.1" 200 OK的日志。 - Step 2 验证:在日志中搜索
matched skill: inventory_query,如果看到,说明指令解析成功。 - Step 3 验证:在
inventory_query.py技能文件里,临时加一行print(f"Query SQL: {sql}"),日志中会输出实际执行的 SQL 语句。 - Step 4 验证:如果最终没收到回复,检查日志中是否有
httpx.HTTPStatusError: Client error '400 Bad Request',这通常意味着FEISHU_BOT_TOKEN无效或消息格式错误。
我建议新手第一次测试,先用最简单的指令:“你好”。OpenClaw 自带hello技能,不依赖任何外部服务,纯返回固定字符串。能收到“你好”,证明整个链路畅通,再逐步增加复杂度。
4.4 MySQL 集成:不是必须,但能让助手记住你
OpenClaw 默认是无状态的,每次重启,所有数据清零。如果你希望助手记住用户的偏好(比如“张三喜欢看周报”),就需要 MySQL。
集成步骤:
在 Railway 项目中,点击
Add Service→MySQL,选择免费套餐。Railway 会自动创建数据库,并生成连接信息(Host, Port, User, Password, Database Name)。
在 Railway 的
Variables页签,添加以下环境变量:MYSQL_HOST= Railway 提供的 Host(如mysql-xxx.up.railway.app)MYSQL_PORT= Railway 提供的 Port(通常是3306)MYSQL_USER=rootMYSQL_PASSWORD= Railway 提供的 PasswordMYSQL_DATABASE= Railway 提供的 Database Name
在 OpenClaw 代码中,找到
skills/inventory_query.py,取消注释import mysql.connector和数据库连接代码,并确保query方法里使用cursor.execute(sql)。
提示:Railway 的 MySQL 免费层有 1GB 存储上限,对于个人项目完全够用。它的优势是自动备份、自动扩缩容,你不需要操心
mysqldump或主从同步。
5. 常见问题与排查技巧实录:那些凌晨三点救了命的解决方案
5.1 “error: 发送飞书失败, 返回信息: {"code":11232,"msg":"frequency limited psm[lark,openclaw” —— 最高频报错的终极解法
这个错误代码11232,官方文档里叫“频率受限”,但真实原因往往不是你调得太勤,而是签名失败。飞书 API 要求每个请求都带AuthorizationHeader,格式为Bearer <access_token>,而 access_token 是用AppID和AppSecret换来的。如果FEISHU_APP_ID或FEISHU_APP_SECRET填错,换 token 就会失败,飞书服务器会返回这个模糊的频率限制错误。
排查流程:
- 第一步,确认变量名和值:在 Railway 的
Variables页签,逐字核对FEISHU_APP_ID和FEISHU_APP_SECRET,确保没有多一个空格、少一个字符。 - 第二步,手动换 token:用 Postman 或 curl,发一个 POST 请求到
https://open.feishu.cn/open-apis/auth/v3/app_access_token/internal/,Body 为 JSON:
如果返回{ "app_id": "你的AppID", "app_secret": "你的AppSecret" }{"code":0,"msg":"success","app_access_token":"xxx"},说明凭证正确;如果返回{"code":10001,"msg":"invalid app_id or app_secret"},那就回去改变量。 - 第三步,检查 OpenClaw 的 token 缓存:OpenClaw 会缓存 access_token 2 小时。如果刚改了变量,服务没重启,它还在用旧的缓存 token。解决方案:在 Railway 控制台,点击
Restart服务。
实操心得:把这个 curl 命令存成一个
test_token.sh脚本,每次部署新环境前先跑一遍,5 秒钟排除 80% 的问题。
5.2 “Webhook 验证失败” —— 不是代码问题,是 URL 没配对
飞书验证 Webhook 时,会发一个GET请求到你的Request URL,带?challenge=xxx参数。OpenClaw 的main.py里有专门处理这个请求的路由:
@app.get("/webhook") async def verify_webhook(challenge: str): return {"challenge": challenge}但很多人配置时,把Request URL写成了https://xxx.up.railway.app(少了/webhook),或者写成了https://xxx.up.railway.app/webhook/(多了斜杠)。飞书会严格匹配路径,多一个字符都失败。
解决方案:
- 在飞书后台,
Request URL必须精确填写为https://xxx.up.railway.app/webhook(无尾部斜杠)。 - 在 Railway 的
Logs页签,发送验证请求后,看日志里有没有GET /webhook?challenge=xxx的记录。如果有,说明请求到了,但返回格式不对;如果没有,说明 URL 根本没配对。
5.3 “技能不响应” —— 关键词匹配的隐藏规则
OpenClaw 的技能匹配不是全文搜索,而是基于预定义的triggers列表。比如feishu_table_query技能的triggers是:
triggers = [ "查.*多维表格", "看.*飞书.*表", "获取.*表格.*数据" ]如果你发“飞书那个表,张三的订单”,它可能不匹配,因为正则里没有.*那个.*表。解决方案有两个:
方案一(推荐):修改技能的 triggers
打开skills/feishu_table_query.py,在triggers列表里加一行:
"飞书.*表.*张三|李四|王五" # 支持常见人名方案二:用 Skill 别名
在skills/__init__.py里,给技能注册别名:
register_skill("查表", feishu_table_query)然后用户直接发“查表”,就能命中。
注意:正则表达式里
.表示任意字符,*表示前面的字符重复 0 次或多次。.*组合就是“任意长度的任意字符串”,这是最常用的通配写法。
5.4 部署后服务无法访问 —— 90% 是 PORT 配置冲突
Railway 要求服务监听在0.0.0.0:$PORT,且$PORT必须是 Railway 分配的端口。但很多人在Dockerfile里写了EXPOSE 8000,又在railway.toml里写了PORT=8000,这就冲突了。Railway 会分配一个动态端口(比如42123),但你的服务还在监听8000,导致流量进不来。
正确配置:
Dockerfile里只写EXPOSE ${PORT}(让 Docker 知道要暴露哪个端口)railway.toml里明确指定PORT变量:[variables] PORT = "8000"- 在
main.py的uvicorn启动命令里,用环境变量:port = int(os.getenv("PORT", "8000")) uvicorn.run(app, host="0.0.0.0", port=port)
这样,无论 Railway 分配什么端口,服务都会自动监听它。
5.5 日志里全是乱码 —— 编码问题的温柔一刀
在 Windows 上用 VS Code 编辑.env或 Python 文件,如果保存时用了GBK编码,而 OpenClaw 期望UTF-8,就会导致日志里出现 `` 符号,甚至UnicodeDecodeError。这个问题隐蔽性强,因为代码能跑,只是日志看不懂。
解决方案:
- 在 VS Code 右下角,点击编码名称(如
GBK),选择Reopen with Encoding→UTF-8。 - 然后点击
Save with Encoding→UTF-8。 - 所有
.py、.env、.toml文件,都必须是 UTF-8 无 BOM 格式。
提示:在 Railway 的
Logs页签,如果看到中文显示为\\u4f60\\u597d这样的 Unicode 转义,说明是编码问题;如果直接是 ``,则是解码失败。
6. 进阶技巧与个性化扩展:让 OpenClaw 真正长成你的样子
6.1 自定义技能:三步写出自己的“查审批”功能
OpenClaw 的魅力在于,写一个新技能,比写一个微信小程序还简单。以“查我的审批单”为例:
第一步:创建技能文件
在skills/目录下,新建approval_query.py:
import httpx from skills.base import Skill class ApprovalQuerySkill(Skill): name = "approval_query" description = "查询用户发起的审批单" triggers = ["查.*审批", "我的.*审批", "审批.*状态"] async def execute(self, user_id: str, **kwargs) -> str: # 1. 用飞书 API 查审批单列表 url = "https://open.feishu.cn/open-apis/approval/v1/instances" headers = { "Authorization": f"Bearer {self.access_token}" } params = { "user_id": user_id, "page_size": 10 } async with httpx.AsyncClient() as client: resp = await client.get(url, headers=headers, params=params) data = resp.json() # 2. 格式化结果 if not data.get("data", {}).get("instances"): return "暂无审批单" result = "【我的审批单】\n" for inst in data["data"]["instances"][:3]: # 只显示前3个 result += f"- {inst['title']} | {inst['status']}\n" return result第二步:注册技能
在skills/__init__.py里,添加:
from .approval_query import ApprovalQuerySkill register_skill("approval_query", ApprovalQuerySkill())第三步:重启服务
在 Railway 控制台点击Restart,然后在飞书群里发“查我的审批”,立刻生效。
实操心得:所有飞书 API 的调用,都必须用
self.access_token,这是 OpenClaw 自动管理的,你不用操心 token 过期。它的原理是:在Skill基类里,__init__方法会自动调用飞书 API 换 token 并缓存。
6.2 多维表格联动:让助手成为你的“活Excel”
飞书多维表格是 OpenClaw 最强大的搭档。比如,你有一个“客户跟进表”,字段包括客户姓名、联系方式、上次跟进时间、下次跟进时间。你可以写一个技能,让用户说“提醒我今天要跟进的客户”,助手就自动查表,找出下次跟进时间是今天的记录,然后发消息提醒。
核心代码片段:
# 查询条件:next_follow_up == today today = datetime.now().strftime("%Y-%m-%d") url = f"https://open.feishu.cn/open-apis/bitable/v1/apps/{app_token}/tables/{table_id}/records" params = { "filter": f"field_123 == '{today}'" # field_123 是“下次跟进时间”字段ID } resp = await client.get(url, headers=headers, params=params)关键是要拿到字段 ID。方法:打开多维表格 → 点击字段名右侧的 `