feat: Add /kb-add command for quick video addition

- Add cmd_add() function to support adding single videos to inbox
- Support BV IDs, full URLs, and short links (with friendly warning)
- Add --process flag to immediately process after adding
- Add --yes flag to skip confirmation prompts
- Update SKILL.md with /kb-add command documentation
This commit is contained in:
OpenClaw Agent
2026-02-06 20:42:11 +08:00
parent 7e0acef4f9
commit ee18cde745
2 changed files with 168 additions and 0 deletions
+38
View File
@@ -11,6 +11,7 @@
| 命令 | 描述 | 用法 |
|------|------|------|
| `/kb-add` | 添加单个视频 | `/kb-add <URL> [--process] [--yes]` |
| `/kb-subscribe` | 订阅内容源 | `/kb-subscribe <source>:<type>:<id>` |
| `/kb-inbox` | 查看收件箱 | `/kb-inbox [--limit N]` |
| `/kb-process` | 处理内容 | `/kb-process [content_id]` |
@@ -20,6 +21,43 @@
## 命令详解
### /kb-add
快速添加单个视频到收件箱。
**用法:**
```
/kb-add BV1xx411c7mD
/kb-add "https://www.bilibili.com/video/BV1xx411c7mD"
/kb-add "https://www.bilibili.com/video/BV1xx411c7mD" --process
/kb-add BV1xx411c7mD --yes
```
**参数:**
- `<URL>` - 视频URL或BV号
- 完整URL: `https://www.bilibili.com/video/BVxxxxx`
- BV号: `BVxxxxx`
- 短链接: `https://b23.tv/xxxxx`(显示友好提示)
- `--process` - 添加后立即处理
- `--yes` - 跳过确认提示
**输出示例:**
```
📥 正在添加视频: BV1xx411c7mD
→ 标题: Python编程入门教程
→ UP主: CodeMaster
→ 时长: 3600秒
→ 获取字幕... ✅
✅ 视频已添加到收件箱!
Content ID: abc123def456
💡 使用以下命令处理:
python3 src/cli.py process abc123def456
或:
python3 src/cli.py process all
```
### /kb-subscribe
订阅一个内容源,支持自动获取更新。
+130
View File
@@ -18,6 +18,7 @@ try:
from src.storage import Storage
from src.pipeline import ProcessingPipeline
from src.models import ContentStatus
from src.sources.bilibili import BilibiliAdapter
CONFIG_AVAILABLE = True
except ImportError as e:
print(f"Import warning: {e}", file=sys.stderr)
@@ -102,6 +103,110 @@ def cmd_subscribe(args: argparse.Namespace):
return 0
def cmd_add(args: argparse.Namespace):
"""Handle add command - add a single video to inbox."""
print_header("Add Video to Inbox")
if not CONFIG_AVAILABLE:
print("Error: Required modules not available. Please check installation.")
return 1
# Import here to avoid issues if not available
from src.models import ContentStatus
url = args.url
# Handle short links (b23.tv)
if 'b23.tv' in url:
print(f" ⚠️ 检测到短链接: {url}")
print(f" 💡 B站对短链接有反爬虫保护,请提供:")
print(f" 1. 完整URL: https://www.bilibili.com/video/BVxxxxx")
print(f" 2. 或BV号: BVxxxxx")
print(f"\n 提示: 可以在浏览器打开短链接,从地址栏复制完整URL")
return 1
# Create adapter
adapter = BilibiliAdapter()
# Extract video metadata
print(f" → 正在获取视频信息: {url}")
content = adapter.extract_content(url)
if not content:
print(" ❌ 无法提取视频信息")
return 1
print(f" → 标题: {content.title}")
print(f" → UP主: {content.author}")
print(f" → 时长: {content.duration}秒")
# Get transcript
print(" → 正在获取字幕...")
transcript = adapter.get_transcript(content)
if transcript:
content.transcript = transcript
print(f" ✓ 字幕已获取 ({len(transcript)} 字符)")
else:
print(" ⚠️ 无法获取字幕")
# Set status to CONFIRMED (ready to process)
content.status = ContentStatus.CONFIRMED
# Confirm before saving (unless --yes)
if not args.yes:
print(f"\n📋 准备添加到收件箱:")
print(f" 标题: {content.title}")
print(f" UP主: {content.author}")
print(f" 时长: {content.duration}秒")
print(f" 字幕: {'有' if transcript else '无'}")
if args.process:
print(f" 操作: 添加并立即处理")
else:
print(f" 操作: 仅添加到收件箱")
confirm = input("\n确认添加? [Y/n]: ").strip().lower()
if confirm and confirm not in ('y', 'yes'):
print("❌ 已取消")
return 0
# Save to inbox
print("\n → 保存到收件箱...")
storage = Storage()
storage.save_content(content)
print(f"\n✅ 视频已添加到收件箱!")
print(f" Content ID: {content.id}")
# Process immediately if --process flag is set
if args.process:
print(f"\n🔄 开始处理内容...")
try:
from src.pipeline import ProcessingPipeline
from src.models import ContentStatus
pipeline = ProcessingPipeline()
content_text = content.transcript or content.summary or ""
result = pipeline.process_full(content, content_text)
storage.save_content(result)
print(f" ✅ 处理完成")
print(f" 📄 笔记: {result.output_path or 'N/A'}")
print(f" 🏷️ 标签: {', '.join(result.tags)}")
except Exception as e:
print(f" ❌ 处理失败: {e}")
import traceback
traceback.print_exc()
return 1
else:
print(f"\n💡 使用以下命令处理:")
print(f" python3 src/cli.py process {content.id}")
print(f" 或:")
print(f" python3 src/cli.py process all")
return 0
def cmd_inbox(args: argparse.Namespace):
"""Handle inbox command - display pending items."""
print_header("Inbox Contents")
@@ -427,6 +532,9 @@ def main():
formatter_class=argparse.RawDescriptionHelpFormatter,
epilog="""
Examples:
%(prog)s add "BV1xx411c7mD"
%(prog)s add "https://www.bilibili.com/video/BV1xx411c7mD" --process
%(prog)s add "https://b23.tv/xxxxx" --yes
%(prog)s subscribe bilibili fav 12345 --name="Tech Favorites"
%(prog)s inbox --limit 10 --sort date
%(prog)s process all --yes
@@ -439,6 +547,28 @@ Examples:
subparsers = parser.add_subparsers(dest='command', help='Available commands')
# add 子命令
add_parser = subparsers.add_parser(
'add',
aliases=['a'],
help='Add a single video to inbox'
)
add_parser.add_argument(
'url',
help='Video URL or BV ID (supports: BVxxxxx, full URL)'
)
add_parser.add_argument(
'--process',
action='store_true',
help='Process immediately after adding'
)
add_parser.add_argument(
'--yes',
action='store_true',
help='Skip confirmation prompts'
)
add_parser.set_defaults(func=cmd_add)
# subscribe 子命令
subscribe_parser = subparsers.add_parser(
'subscribe',