1. 从一条热搜说起:为什么“把民法典做成skill”这件事值得聊
前几天刷到一条动态,标题是“第一个把《民法典》做成skill的人简直是个天才”。乍一看像标题党,但仔细琢磨,这个思路确实有点东西。它背后牵扯出来的,是一整套关于AI Agent技能封装、知识库结构化、book-to-skill转换的玩法。热搜词里还夹着豆包、GitHub、book-to-skill、skill插件、agent skill这些关键词,说明大家关注的不是“民法典”本身,而是“把一本厚重的书变成一个可调用的AI技能”这件事。
我自己折腾AI Agent和技能封装有一段时间了,从最早的prompt模板,到后来的function calling,再到现在的skill机制,踩过的坑不算少。看到这个标题的第一反应是:这人把“知识封装”这件事想透了。民法典是什么?一千两百多条法条,普通人查起来头大,律师用起来也要翻半天。但如果把它做成一个skill,用户只需要问“楼上漏水把我家天花板泡了,我该找谁赔”,skill就能直接定位到物权编相关条款,给出侵权责任分析。这就是从“查书”到“问人”的体验跃迁。
这篇文章我想聊的不是民法典本身,而是book-to-skill这套方法论。它适用于任何一本工具书、手册、规范、指南。你手里有一本PDF,怎么把它变成一个AI能调用的skill?中间要经过哪些步骤?有哪些坑?豆包的skill机制和GitHub上的开源方案有什么区别?我会把整个流程拆开讲,包括知识切片、意图路由、参数设计、测试验证这些环节。适合谁看?适合手里有大量文档想做成AI助手的产品经理、想给自己领域做知识库的从业者、以及单纯好奇“skill到底怎么玩”的技术爱好者。哪怕你之前没接触过Agent skill,看完也能自己动手做一个。
2. 核心思路拆解:book-to-skill到底在解决什么问题
2.1 从“塞进上下文”到“按需调用”的范式转变
早期做知识库问答,最直接的办法是把整本书塞进大模型的上下文窗口。民法典全文大概10万字左右,按token算差不多15万token,现在有些模型能吃下,但成本高、延迟大,而且每次提问都要重新读一遍,纯属浪费。后来有了RAG,把书切成片段,用向量检索找相关段落,再喂给模型。这个方案成熟,但有个问题:检索是模糊匹配,不是逻辑调用。用户问“租房押金不退怎么办”,向量检索可能找到“押金”相关的段落,但不一定能精准定位到“租赁合同”章节下的具体条款。
skill的思路不一样。它把书里的知识结构化成一个个可调用的功能单元。比如民法典skill可以设计成:输入一个法律问题,输出相关法条、适用解释、维权建议。这中间不是简单的检索,而是意图识别+条款映射+推理生成的三段式流程。book-to-skill的核心,就是把这个流程固化下来,让AI知道“遇到什么问题该翻哪一页、该用哪条逻辑”。
提示:skill和RAG不是替代关系,而是互补。RAG负责“找到相关材料”,skill负责“按正确流程处理材料”。两者结合效果最好。
2.2 为什么是民法典?选材背后的逻辑
民法典特别适合做skill,原因有三。第一,结构清晰。七编加附则,编下面有章,章下面有节,节下面是条,层级分明,天然适合做知识切片。第二,查询高频。普通人遇到法律问题第一反应是搜,但搜出来的结果往往不准确,需要专业解读。第三,答案有标准。法条是确定的,解释有通说,不像文学鉴赏那样见仁见智。这三点决定了民法典skill的输入输出边界很清晰,做起来容易验证效果。
反过来,如果你想把一本小说做成skill,那就难了。小说没有明确的功能边界,用户问“主角为什么这么做”,答案依赖上下文和读者理解,很难结构化。所以选材的时候要判断:这本书是不是工具属性大于叙事属性。手册、规范、指南、教科书、操作手册,这些都适合。散文、小说、传记,就不太适合。
2.3 skill的本质:把“人翻书”的过程编码成“AI执行”的流程
我打个比方。你找一个资深律师咨询,他不会一上来就翻法条。他会先听你说情况,判断这属于民事还是刑事,是合同纠纷还是侵权纠纷,然后定位到相关法律领域,再回忆具体条款,最后结合你的实际情况给出建议。这个过程是分层过滤的:先定领域,再定章节,再定条款,最后生成建议。
book-to-skill要做的就是把这个过程拆解成AI能执行的步骤。第一步,意图分类:用户的问题属于哪个法律领域?第二步,条款检索:该领域下有哪些相关法条?第三步,条款筛选:哪几条最贴合用户描述的场景?第四步,解释生成:用法条+通俗语言回答用户。每一步都可以设计成独立的skill模块,也可以串成一个完整流程。关键在于每一步的输入输出要定义清楚,不能含糊。
3. 核心细节解析:知识切片与意图路由的实操要点
3.1 知识切片:怎么切才不丢信息又不冗余
把民法典切成skill可用的知识单元,不是简单按条切。一条法条可能包含多个要件,比如“当事人订立合同,可以采用书面形式、口头形式或者其他形式”,这里面有三个要素:书面、口头、其他。如果整条作为一个切片,检索时可能匹配到“合同”但匹配不到“口头”,效果就打折。我的做法是按“条-款-项”三级切分,再按语义合并。
具体操作:先把民法典全文按“第X条”切分,得到1260个基本单元。然后对每一条做语义分析,如果一条包含多个独立规则,就拆成多个子切片。比如“第X条”讲的是“合同生效条件”,里面分了“依法成立”“意思表示真实”“不违反强制性规定”三个要件,那就拆成三个切片,每个切片标注所属条款号。拆完之后,再做一个反向合并:把语义相近的切片合并成一个“知识簇”,比如所有关于“违约责任”的条款放在一起,形成一个簇。这样检索时先定位簇,再定位具体条款,效率更高。
注意:切片不是越细越好。切得太细,检索时容易丢失上下文;切得太粗,又不够精准。我的经验是每个切片控制在200-500字,包含一个完整的规则单元。如果一条法条超过500字,就按自然段拆;如果多条法条讲同一件事,就合并成一个切片。
3.2 意图路由:让AI知道“该翻哪一章”
意图路由是book-to-skill里最容易被忽视但最关键的一环。用户问“公司拖欠工资怎么办”,AI需要先判断这属于“劳动纠纷”还是“合同纠纷”。如果路由错了,后面检索再准也没用。我的做法是建一个领域分类表,把民法典的七编拆成更细的领域标签,比如“合同编”下面分“买卖合同”“租赁合同”“借款合同”“劳动合同”等。每个标签配一组触发词和排除词。
触发词就是用户问题里出现这些词,大概率属于这个领域。比如“工资”“加班费”“辞退”触发“劳动合同”;“押金”“租金”“转租”触发“租赁合同”。排除词就是出现这些词,说明不属于这个领域。比如“工资”出现在“离婚财产分割”的语境里,就不该路由到劳动合同。排除词的设计需要一些实际测试,我一开始没做排除,结果“离婚后对方不给抚养费”被路由到了“借款合同”,因为出现了“不给”这个触发词。后来加了“离婚”“抚养”作为排除词,才修正过来。
3.3 参数设计:skill的输入输出要像函数一样明确
一个skill好不好用,看它的参数设计。民法典skill的输入应该是什么?最理想的是自然语言问题+可选的地域信息。因为有些法律问题各地执行标准不同,比如“最低工资标准”“交通事故赔偿标准”。输出应该包含:相关法条原文、适用解释、维权建议、注意事项。这四块缺一不可。只给法条,用户看不懂;只给建议,用户不信任;没有注意事项,用户可能踩坑。
我在设计输出格式时,会强制要求AI按固定结构返回。比如:
{ "relevant_articles": ["第X条", "第Y条"], "article_text": "法条原文...", "explanation": "通俗解释...", "suggestions": ["建议1", "建议2"], "caveats": ["注意事项1", "注意事项2"] }这样前端展示的时候可以分块渲染,用户看起来清晰。如果让AI自由发挥,它可能把法条和建议混在一起,读起来费劲。结构化输出是skill可复用的前提。
4. 实操过程:从PDF到可调用skill的完整流程
4.1 第一步:文档预处理与格式清洗
拿到民法典PDF后,第一件事不是急着切片,而是清洗格式。PDF里的换行、页眉页脚、脚注、表格,都会干扰后续处理。我的做法是先用Python的pdfplumber提取文本,然后写正则去掉页码、页眉、多余空行。民法典的条文格式比较规整,基本都是“第X条 内容”的形式,所以可以用正则第[一二三四五六七八九十百千]+条来定位每一条的起始位置。
清洗完之后,把文本转成结构化数据。我一般用JSON格式,每条法条存成:
{ "article_number": "第X条", "chapter": "第X章", "section": "第X节", "content": "法条原文", "keywords": ["关键词1", "关键词2"] }关键词可以用TF-IDF或者TextRank自动提取,也可以人工标注。人工标注更准,但费时间。我的做法是自动提取+人工校验,先跑一遍算法,再把明显不对的改掉。这一步大概花了我两个晚上,但后面检索准确率提升很明显。
4.2 第二步:知识切片与向量化存储
清洗完的数据按前面说的规则切片。切完之后,每个切片生成一个向量。向量化模型我试过几种,OpenAI的text-embedding-3-small性价比不错,国产的BGE-M3也可以。选哪个看你的部署环境。如果数据敏感,就用本地部署的模型;如果追求效果,就用API。我自己的项目用的是BGE-M3,因为民法典数据不算敏感,但本地跑更可控。
向量存到向量数据库里,我用的是Chroma,轻量、易用、支持元数据过滤。每个切片存的时候带上article_number、chapter、keywords这些元数据,检索时可以按章节过滤。比如用户问“合同编里的违约责任”,就可以先过滤chapter="合同编",再在子集里做向量检索。这样比全库检索快很多,也准很多。
4.3 第三步:意图路由模块的实现
意图路由我用了两层。第一层是规则匹配,用关键词表快速判断领域。第二层是模型分类,用一个小模型(比如BERT微调)做兜底。规则匹配快但覆盖不全,模型分类慢但泛化好。两层结合,先规则后模型,大部分问题第一层就能解决,少数模糊的交给第二层。
规则匹配的实现很简单,维护一个领域-触发词映射表:
domain_triggers = { "劳动合同": ["工资", "加班", "辞退", "社保", "工伤"], "租赁合同": ["租金", "押金", "转租", "房东", "租客"], "买卖合同": ["货款", "交货", "质量", "退货", "违约金"], # ... }用户问题进来后,遍历每个领域的触发词,统计命中数量,命中最多的领域就是路由结果。如果所有领域命中数都为0,就交给模型分类。模型分类我用的是豆包的API,因为它对中文法律文本的理解还不错,而且调用方便。这里有个细节:豆包的请求格式是input而不是message,和OpenAI的格式不一样,写代码的时候要注意适配。
4.4 第四步:skill封装与豆包/GitHub方案对比
skill封装有两种路线。一种是平台原生skill,比如豆包的skill插件机制,你按照它的规范写好配置文件,上传上去就能用。另一种是开源方案,比如GitHub上的book-to-skill项目,你自己部署服务,通过API调用。两种路线各有优劣。
| 对比项 | 豆包原生skill | GitHub开源方案 |
|---|---|---|
| 部署难度 | 低,上传配置即可 | 中,需要自己搭服务 |
| 定制程度 | 受平台限制 | 高,想怎么改就怎么改 |
| 调用方式 | 平台内调用 | API调用,可集成到任意应用 |
| 数据隐私 | 数据在平台 | 数据在自己服务器 |
| 适合场景 | 快速验证、轻量使用 | 深度定制、企业级应用 |
我两个都试过。豆包原生skill适合快速做个demo,验证想法。GitHub方案适合长期迭代,尤其是需要接入自己业务系统的时候。热搜里提到的book-to-skill项目,核心思路就是把书转成skill的流程标准化,提供了一套工具链。你可以直接clone下来,改改配置就能用。
4.5 第五步:测试验证与效果调优
skill做完不是终点,测试才是。我设计了三类测试用例。第一类直接匹配:问题里包含明确的法律术语,比如“民法典第X条怎么规定的”,看skill能不能直接定位。第二类场景描述:用户用生活语言描述问题,比如“我租的房子漏水,房东不管”,看skill能不能路由到租赁合同并找到相关条款。第三类边界情况:问题涉及多个领域,比如“离婚时公司股权怎么分”,看skill能不能同时处理婚姻和公司两个领域。
测试的时候记录每个用例的路由准确率和条款召回率。路由准确率就是领域判断对不对,条款召回率就是相关法条有没有被检索到。我第一版的路由准确率只有70%左右,主要问题是触发词覆盖不够。后来加了200多个触发词,又调整了排除词,才提到90%以上。条款召回率一开始也不高,原因是切片太粗,一条法条包含多个规则时只切了一个片。后来改成按要件切分,召回率明显提升。
5. 常见问题与排查技巧实录
5.1 路由错误:为什么AI总是“答非所问”
路由错误是最常见的问题。用户问“公司不给交社保”,AI回答“劳动合同解除条件”,这就是路由错了。排查思路:先看触发词表里“社保”有没有被正确映射到“劳动合同”领域。如果没有,加上。如果有,看是不是被其他领域的触发词抢走了。比如“公司”这个词可能同时出现在“劳动合同”和“公司治理”两个领域,如果“公司治理”的权重更高,就会路由错。解决办法是给触发词加权重,核心词权重高,边缘词权重低。
还有一种情况是用户问题太短,比如“押金不退”,只有四个字。触发词“押金”能命中“租赁合同”,但如果用户实际问的是“买车押金不退”,那就该路由到“买卖合同”。这时候需要结合上下文,如果skill支持多轮对话,就看上一轮聊的是什么。如果不支持,就在输出里加一个澄清问句:“您说的是租房押金还是购车押金?”让用户确认。
5.2 条款召回不全:为什么相关法条没被检索到
条款召回不全的原因通常有三个。第一,切片粒度不对。前面说过,切太粗会丢细节,切太细会丢上下文。我的经验是按要件切分,但保留条款号作为元数据。这样检索到要件切片后,可以通过条款号回溯到完整法条。第二,向量模型不适合法律文本。通用向量模型对法律术语的区分度不够,比如“定金”和“订金”在法律上完全不同,但向量距离很近。解决办法是用法律领域微调过的向量模型,或者加一层关键词过滤。第三,检索策略太单一。只用向量检索不够,要结合关键词检索。我一般用混合检索:向量检索取Top 20,关键词检索取Top 20,然后合并去重,再按相关性排序。
5.3 输出格式不稳定:为什么AI有时给法条有时不给
输出格式不稳定,是因为prompt里没有强制约束。我的做法是在system prompt里写死输出结构,并且给一个示例。比如:
你是一个民法典查询助手。用户提问后,你必须按以下格式返回: 1. 相关法条:列出条款号 2. 法条原文:引用原文 3. 通俗解释:用大白话解释 4. 维权建议:给出可操作的建议 5. 注意事项:提醒用户可能的风险 如果找不到相关法条,返回“暂无直接相关条款,建议咨询专业律师”。这样约束之后,输出格式基本稳定。但还有一个坑:AI有时会编造法条。明明民法典里没有这条,它硬编一个“第X条”出来。解决办法是在prompt里加一句“只引用检索结果中出现的法条,不得自行编造”,并且在代码层面做校验,如果AI引用的条款号不在检索结果里,就拦截并重新生成。
5.4 常见问题速查表
| 问题现象 | 可能原因 | 排查方法 | 解决措施 |
|---|---|---|---|
| 路由到错误领域 | 触发词覆盖不足或权重不对 | 检查触发词表和权重配置 | 补充触发词,调整权重 |
| 相关法条没召回 | 切片粒度或检索策略问题 | 检查切片粒度和检索Top K | 调整切片规则,改用混合检索 |
| 输出格式混乱 | prompt约束不够 | 检查system prompt | 写死输出结构,加示例 |
| AI编造法条 | 未限制引用来源 | 检查prompt和校验逻辑 | 加引用限制,代码层校验 |
| 响应太慢 | 向量检索或模型调用耗时 | 分段计时 | 加缓存,优化检索策略 |
| 多领域问题处理不好 | 路由只支持单领域 | 检查路由逻辑 | 支持多标签路由,分别处理 |
提示:排查问题时,先看日志。把每次请求的路由结果、检索结果、模型输出都记下来,出问题的时候一目了然。我一开始没记日志,排查全靠猜,效率极低。后来加了日志,排查时间从半小时缩短到五分钟。
5.5 几个踩过的坑和独家技巧
第一个坑:不要用整本法条做few-shot示例。我一开始在prompt里塞了十几条法条作为示例,结果token消耗巨大,而且模型被示例带偏,总是往示例的方向回答。后来改成只给输出格式示例,不给具体法条示例,效果好很多。
第二个坑:向量数据库的元数据过滤要慎用。Chroma支持按元数据过滤,但过滤条件太复杂时性能下降明显。我试过同时按章节、条款号、关键词三个条件过滤,检索时间从50ms涨到500ms。后来改成只按章节过滤,关键词在应用层做二次筛选,速度快了很多。
第三个技巧:用缓存加速高频问题。民法典里高频问题就那么几十个,比如“离婚财产分割”“交通事故赔偿”“劳动合同解除”。我把这些问题的答案缓存起来,用户再问直接返回,响应时间从2秒降到50毫秒。缓存用Redis就行,设置合理的过期时间。
第四个技巧:定期更新知识库。法律会修订,民法典虽然刚颁布,但司法解释会更新。我设置了一个定时任务,每月检查一次最高人民法院的司法解释更新,如果有新内容,就重新切片、重新向量化。这个流程自动化之后,维护成本很低。
6. 从民法典skill延伸:book-to-skill的通用方法论
6.1 哪些书适合做成skill
不是所有书都适合。我总结了一个判断标准:工具属性强、查询频率高、答案有标准。工具属性强,意味着书里的内容是拿来用的,不是拿来读的。查询频率高,意味着用户会反复问同类问题。答案有标准,意味着对错分明,不依赖主观判断。按这个标准,适合做skill的书包括:法律法规、行业规范、操作手册、产品文档、教科书、诊疗指南、财务准则。不适合的包括:小说、散文、传记、哲学著作、艺术评论。
6.2 通用流程的五个阶段
不管什么书,book-to-skill的流程都可以归纳为五个阶段。阶段一:文档解析,把PDF/Word/HTML转成结构化文本。阶段二:知识切片,按语义单元切分,标注元数据。阶段三:索引构建,向量化存储,建关键词索引。阶段四:skill封装,定义输入输出,写路由逻辑,接模型。阶段五:测试迭代,设计测试用例,记录指标,持续优化。每个阶段都有工具可以用,但核心还是对书的理解。你得知道这本书的知识结构是什么样的,用户会怎么问,答案该怎么组织。这些是工具替代不了的。
6.3 多AI协作的可能性
热搜里有个词叫“多AI协作”,这在book-to-skill里很有用。比如民法典skill可以拆成多个子skill:一个负责合同编,一个负责侵权编,一个负责婚姻家庭编。用户提问后,先由一个路由AI判断该调用哪个子skill,再由子skill生成答案。如果问题跨多个领域,就并行调用多个子skill,最后合并结果。这样做的好处是每个子skill可以独立优化,互不干扰。坏处是架构复杂,调试麻烦。我的建议是先做单skill,跑通之后再拆。一上来就搞多AI协作,容易陷入架构泥潭。
6.4 从skill到agent:下一步怎么走
skill是静态的,agent是动态的。skill是你问它答,agent是它主动帮你做事。民法典skill再往前走一步,可以做成法律agent:用户描述一个纠纷,agent自动分析法律关系、检索法条、生成起诉状草稿、计算诉讼时效、提醒证据清单。这就不是简单的问答了,而是任务执行。实现方式是把skill作为agent的工具之一,agent根据任务需要调用不同的skill。比如需要查法条就调民法典skill,需要算诉讼费就调计算器skill,需要写文书就调模板skill。这个方向我觉得是接下来一年比较有意思的探索。
我自己在实际操作中的体会是,book-to-skill最难的不是技术,而是对知识的理解。你得先把自己当成这本书的专家,知道用户会问什么、该怎么回答,然后才能设计出好用的skill。技术只是实现手段,领域知识才是核心。如果你对自己要做的书不够熟悉,建议先花时间读透它,再动手做skill。否则做出来的东西,用户一问就露馅。
最后分享一个小技巧:做skill的时候,先手动模拟一遍。拿几个典型问题,自己翻书找答案,把过程记下来。这个手动过程就是你skill的逻辑原型。然后再把这个过程翻译成代码和prompt。这样做出来的skill,逻辑最顺,效果最好。我做过好几个skill,凡是先手动模拟过的,上线后问题都很少;凡是直接写代码的,后面都要大改。