#!/usr/bin/env python3 """生成服务层已发布技能(fmode-vision/listen/ffmpeg/qiwei/storage) + inventory.json""" import os, json BASE = '/opt/data/projects/fmode-skills/skills' skills = [ {"dir":"fmode-vision","slug":"fmode-skill-fmode-vision","ver":"0.1.1","title":"视觉识别","summary":"图片/视频结构化视觉分析:宿主多模态优先,回落 Fmode API(豆包/Doubao)。","triggers":"看图、识图、截图分析、UI截图、视觉识别、图片文字、图像分析、doubao、vision","src":"npm fmode-vision","endpoint":"POST https://api.fmode.cn/v1/chat/completions"}, {"dir":"fmode-listen","slug":"fmode-skill-fmode-listen","ver":"0.1.2","title":"录音转写","summary":"录音/视频音轨转文字(讯飞 LFASR × Fmode 网关),多语种/方言/说话人分离,服务端计费。","triggers":"转写、录音、语音转文字、ASR、讯飞、说话人分离、meeting转写","src":"npm fmode-listen","endpoint":"POST https://server.fmode.cn/api/listen/transcribe"}, {"dir":"fmode-ffmpeg","slug":"fmode-skill-fmode-ffmpeg","ver":"0.1.1","title":"音视频处理","summary":"FFmpeg 音视频处理:抽音轨、转码、压缩、裁剪、截图。捆绑静态二进制零系统依赖。","triggers":"ffmpeg、抽音轨、转码、压缩、裁剪视频、截图、音视频处理、media","src":"npm fmode-ffmpeg","endpoint":"CLI 本地执行"}, {"dir":"fmode-qiwei","slug":"fmode-skill-fmode-qiwei","ver":"0.5.2","title":"企微网关 SDK","summary":"企业微信网关:消息收发、通讯录、应用管理封装。","triggers":"企微、企业微信、WeCom、qiwei、公众号、消息推送、通讯录","src":"npm fmode-qiwei","endpoint":"gateway"}, {"dir":"fmode-storage","slug":"fmode-skill-fmode-storage","ver":"1.1.0","title":"对象存储与公开分享","summary":"二进制大文件上云,本地零占用,一键生成公开分享链接(S3/OBS)。","triggers":"上传、存储、对象存储、S3、OBS、分享链接、公开URL、托管文件","src":"skill-storage 1.1.0","endpoint":"https://s3.fmode.cn/"}, ] inven = [] for s in skills: d = os.path.join(BASE, s['dir']) os.makedirs(os.path.join(d,'scripts'),exist_ok=True) os.makedirs(os.path.join(d,'references'),exist_ok=True) skill_md = f"""--- slug: {s['slug']} displayName: {s['dir']} version: {s['ver']} name: {s['dir']} description: {s['summary']} 触发词:{s['triggers']} tags: [FmodeAgent, FmodeCode, 服务级, {s['dir'].replace('fmode-','')}] platform: Both level: 服务级 category: 平台基础设施 icon: 🛠️ license: MPL-2.0 author: Fmode (未来飞马) --- # {s['title']} ## 触发词 {s['triggers']} ## 快速开始 ```bash node scripts/index.mjs ``` 或按 {s['src']} 的官方命令(`npx --yes {s['src'].split(' ')[-1]}@latest workspace`)。 ## 端点 - {s['endpoint']} ## 来源 - {s['src']} ## License MPL-2.0 © 2026 Fmode (未来飞马) """ open(os.path.join(d,'SKILL.md'),'w',encoding='utf-8').write(skill_md) open(os.path.join(d,'references','source.md'),'w',encoding='utf-8').write(f"# 来源\n{s['src']}\n端点: {s['endpoint']}\n") inven.append({"name":s['dir'],"slug":s['slug'],"version":s['ver'],"tier":"service","source":s['src']}) print(f"✅ {s['dir']}") # 汇总全部技能到 inventory.json all_skills = sorted(os.listdir(BASE)) inventory = { "name": "fmode-skills", "version": "0.1.0", "generatedAt": __import__('datetime').datetime.now().isoformat(), "format": "esm", "skills": [], } for name in all_skills: full = os.path.join(BASE, name) if not os.path.isdir(full): continue # 读 SKILL.md frontmatter 的 slug/version/level slug=version=level="" try: md = open(os.path.join(full,'SKILL.md'),encoding='utf-8').read() for line in md.split('\n')[:20]: if line.startswith('slug:'): slug = line.split(':',1)[1].strip() if line.startswith('version:'): version = line.split(':',1)[1].strip() if line.startswith('level:'): level = line.split(':',1)[1].strip() except: pass inventory["skills"].append({"name":name,"slug":slug or f"fmode-skill-{name}","version":version,"level":level}) with open('/opt/data/projects/fmode-skills/skills/inventory.json','w',encoding='utf-8') as f: json.dump(inventory, f, ensure_ascii=False, indent=2) print(f"\n📊 inventory.json 生成: {len(inventory['skills'])} 个子技能") print("🎉 服务层已发布技能补齐")