| 1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586 |
- #!/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/<key>"},
- ]
- 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 <action>
- ```
- 或按 {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("🎉 服务层已发布技能补齐")
|