飞书(Lark)MCP function call 全场景 AI Agent 来啦 - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
爱意满满的作品展示区。
cvcat
V2EX    分享创造

飞书(Lark)MCP function call 全场景 AI Agent 来啦

  cvcat
cv-cat 224 天前 3597 次点击
这是一个创建于 224 天前的主题,其中的信息可能已经有所发展或是发生改变。

Lark MCP - 飞书全场景 Function Call AI 助手

一个基于飞书(Lark)的全场景 MCP Function Call AI Agent ,实现大模型通过飞书进行函数调用和消息处理。

欢迎 star 和 fork

项目地址https://github.com/cv-cat/LarkAgentX

无需配置飞书机器人,你的飞书账号即是 AI 助手。

只需定义函数和注释,你的飞书机器人会自动根据场景调用。

项目概述

Lark MCP 是一个现代化的 Python 应用程序,能够:

  • 逆向飞书 Protobuf 格式传输的 Websockets 和 API ,监听并记录消息
  • 提供自定义函数供大模型调用
  • 实现基于 MCP (Model Context Protocol) 的函数调用框架
  • 使用 SQLAlchemy 将消息存储到 MySQL 数据库

效果图

后台日志
图 1: 后台日志
聊天数据库查询
图 2: 聊天数据库查询
天气查询
图 3: 天气查询
注册函数
图 4: 简单注册函数,只需定义函数和注释

功能特点

  • 函数注册机制: 简单直观的函数注册装饰器
  • 消息自动处理: 记录所有接收到的消息(私聊和群聊)
  • 异步处理: 采用 async/await 模式进行异步通信
  • 数据持久化: 使用 SQLAlchemy 将消息存储在 MySQL 数据库中
  • 灵活配置: 通过环境变量进行配置
  • 容器化部署: 支持 Docker 快速部署
  • 智能函数调用: AI 会根据用户输入的文字自动分析并调用最匹配的函数,开发者只需添加函数及其注释描述

当前支持的函数

项目目前内置了以下函数供大模型调用:

函数名 描述
tell_joke 讲一个随机笑话
get_time 获取当前时间
roll_dice 掷一个指定面数的骰子
make_todo_list 从逗号分隔的任务创建待办清单
translate_to_chinese 将英文单词翻译成中文
countdown 创建一个从指定数字开始的倒计时
random_color 生成一个随机的十六进制颜色代码
fortune 抽取一个随机运势
count_daily_speakers 获取今天发言的人数统计
get_top_speaker_today 获取今天发言最多的用户
send_message 给指定用户发送消息
list_tools 列出所有可用的工具及其描述

你可以通过在飞书中输入触发指令后跟要执行的操作来调用这些功能,例如: /run 讲个笑话

项目结构

project/ ├── app/ # 应用程序模块 │ ├── api/ # API 相关模块 │ │ ├── auth.py # 认证模块 │ │ └── lark_client.py # 飞书客户端 │ ├── config/ # 配置模块 │ │ └── settings.py # 应用配置 │ ├── core/ # 核心业务逻辑 │ │ ├── mcp_server.py # MCP 服务器 │ │ └── message_service.py # 消息处理服务 │ ├── db/ # 数据库相关 │ │ ├── models.py # 数据模型 │ │ └── session.py # 数据库会话管理 │ └── utils/ # 工具函数 ├── builder/ # 请求构建器 ├── static/ # 静态资源 │ ├── resource/ # 图片资源 │ ├── proto_pb2.py # 协议定义 │ └── lark_decrypt.js # 飞书解密工具 ├── .env # 环境变量 ├── main.py # 应用入口 └── Dockerfile # Docker 配置 

自定义函数开发

app/core/mcp_server.py 文件中,您可以使用 @register_tool 装饰器添加您自己的自定义函数:

@register_tool(name="tell_joke", description="讲一个随机笑话") def tell_joke() -> str: jokes = [ "为什么程序员都喜欢黑色?因为他们不喜欢 bug 光。", "Python 和蛇有什么共同点?一旦缠上你就放不下了。", "为什么 Java 开发者很少被邀去派对?因为他们总是抛出异常。", ] return random.choice(jokes) @register_tool(name="send_message", description="给指定用户发送消息 {user:用户名称 content:消息内容}") def send_message(user: str, content: str) -> str: """给指定用户发送私信""" lark_client = LarkClient(get_auth()) # ... 实现逻辑 ... return f"成功向 {user} 发送了私信: '{content}'" 

重要: 只需添加函数和对应的描述,AI 会根据用户的文字自动分析并调用最匹配的函数,无需手动实现函数匹配逻辑。

关于我

正在实习的一名研二学生,有问题欢迎加群或者加 V 交流,联络方式在 github 上哈,感谢 star

10 条回复    2025-11-24 12:55:46 +08:00
cvcat
    1
cvcat  
OP
   224 天前
没人 star 、评论 ┭┮┭┮
kid1412621
    2
kid1412621  
   224 天前 via iPhone
飞书 != lark
cvcat
    3
cvcat  
OP
   224 天前
kid1412621
    4
kid1412621  
   224 天前 via iPhone
@cvcat #3 账号不相通
cvcat
    5
cvcat  
OP
   224 天前
@kid1412621 加密是通的
liewstar
    6
liewstar  
   223 天前 via iPhone
能调到用户加入的群组信息吗
cvcat
    7
cvcat  
OP
   223 天前 via Android
@liewstar 这个暂时不支持,需要逆向一个新结构的消息,可以实现
hugetimors
    8
hugetimors  
   222 天前
想了解咋逆向的
cvcat
    9
cvcat  
OP
   216 天前
@hugetimors protobuf js 逆向
cvcat
    10
cvcat  
OP
   4 天前
@hugetimors 这个是 protobuf 的
关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     4442 人在线   最高记录 6679       Select Language
创意工作者们的社区
World is powered by solitude
VERSION: 3.9.8.5 23ms UTC 09:58 PVG 17:58 LAX 01:58 JFK 04:58
Do have faith in what you're doing.
ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86