asciinema-analyzer

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

asciinema-analyzer

asciinema-analyzer

Semantic analysis of converted .txt recordings for Claude Code consumption. Uses tiered analysis: ripgrep (primary, 50-200ms) -> YAKE (secondary, 1-5s) -> TF-IDF (optional).
Platform: macOS, Linux (requires ripgrep, optional YAKE)
针对Claude Code的转换后.txt录屏文件语义分析工具。采用分层分析机制:ripgrep(核心工具,耗时50-200ms)-> YAKE(次要工具,耗时1-5s)-> TF-IDF(可选)。
平台支持: macOS、Linux(需要安装ripgrep,YAKE为可选依赖)

When to Use This Skill

适用场景

Use this skill when:
  • Searching for keywords or patterns in converted recordings
  • Extracting topics or themes from session transcripts
  • Finding specific commands or errors in session history
  • Auto-discovering unexpected terms in recordings
  • Analyzing session content for documentation or review

在以下场景中使用本工具:
  • 在转换后的录屏文件中搜索关键词或模式
  • 从会话转录文本中提取主题或核心内容
  • 在会话历史中查找特定命令或错误信息
  • 自动发现录屏文件中的异常术语
  • 分析会话内容用于文档编写或复盘评审

Analysis Tiers

分层分析机制

TierToolSpeed (4MB)When to Use
1ripgrep50-200msAlways start here (curated)
2YAKE1-5sAuto-discover unexpected terms
3TF-IDF5-30sTopic modeling (optional)
Decision: Start with Tier 1 (ripgrep + curated keywords). Only use Tier 2 (YAKE) when auto-discovery is explicitly requested.

层级工具处理速度(4MB文件)适用场景
1ripgrep50-200ms优先使用(精准匹配预设关键词)
2YAKE1-5s自动发现未预设的异常术语
3TF-IDF5-30s主题建模(可选功能)
决策建议:从第1层级开始(ripgrep + 预设关键词集)。仅当明确需要自动发现功能时,才使用第2层级(YAKE)。

Requirements

依赖要求

ComponentRequiredInstallationNotes
ripgrepYes
brew install ripgrep
Primary search tool
YAKEOptional
uv run --with yake
For auto-discovery tier

组件是否必需安装方式说明
ripgrep
brew install ripgrep
核心搜索工具
YAKE可选
uv run --with yake
用于自动发现层级的分析

Workflow Phases (ALL MANDATORY)

工作流阶段(全部为必填步骤)

IMPORTANT: All phases are MANDATORY. Do NOT skip any phase. AskUserQuestion MUST be used at each decision point.
重要提示:所有阶段均为必填,请勿跳过任何步骤。在每个决策点必须使用AskUserQuestion交互。

Phase 0: Preflight Check

阶段0:前置检查

Purpose: Verify input file exists and check for .txt (converted) format.
bash
/usr/bin/env bash << 'PREFLIGHT_EOF'
INPUT_FILE="${1:-}"

if [[ -z "$INPUT_FILE" ]]; then
  echo "NO_FILE_PROVIDED"
elif [[ ! -f "$INPUT_FILE" ]]; then
  echo "FILE_NOT_FOUND: $INPUT_FILE"
elif [[ "$INPUT_FILE" == *.cast ]]; then
  echo "WRONG_FORMAT: Convert to .txt first with /asciinema-tools:convert"
elif [[ "$INPUT_FILE" == *.txt ]]; then
  SIZE=$(ls -lh "$INPUT_FILE" | awk '{print $5}')
  LINES=$(wc -l < "$INPUT_FILE" | tr -d ' ')
  echo "READY: $INPUT_FILE ($SIZE, $LINES lines)"
else
  echo "UNKNOWN_FORMAT: Expected .txt file"
fi
PREFLIGHT_EOF
If no .txt file found, suggest running
/asciinema-tools:convert
first.

目的:验证输入文件是否存在,并检查是否为.txt(转换后)格式。
bash
/usr/bin/env bash << 'PREFLIGHT_EOF'
INPUT_FILE="${1:-}"

if [[ -z "$INPUT_FILE" ]]; then
  echo "NO_FILE_PROVIDED"
elif [[ ! -f "$INPUT_FILE" ]]; then
  echo "FILE_NOT_FOUND: $INPUT_FILE"
elif [[ "$INPUT_FILE" == *.cast ]]; then
  echo "WRONG_FORMAT: Convert to .txt first with /asciinema-tools:convert"
elif [[ "$INPUT_FILE" == *.txt ]]; then
  SIZE=$(ls -lh "$INPUT_FILE" | awk '{print $5}')
  LINES=$(wc -l < "$INPUT_FILE" | tr -d ' ')
  echo "READY: $INPUT_FILE ($SIZE, $LINES lines)"
else
  echo "UNKNOWN_FORMAT: Expected .txt file"
fi
PREFLIGHT_EOF
如果未找到.txt文件,建议先运行
/asciinema-tools:convert
进行格式转换。

Phase 1: File Selection (MANDATORY)

阶段1:文件选择(必填)

Purpose: Discover .txt files and let user select which to analyze.
目的:发现当前目录下的.txt文件,并让用户选择要分析的文件。

Step 1.1: Discover .txt Files

步骤1.1:发现.txt文件

bash
/usr/bin/env bash << 'DISCOVER_TXT_EOF'
bash
/usr/bin/env bash << 'DISCOVER_TXT_EOF'

Find .txt files that look like converted recordings

查找看起来是转换后录屏的.txt文件

for file in $(fd -e txt . --max-depth 3 2>/dev/null | head -10); do SIZE=$(ls -lh "$file" 2>/dev/null | awk '{print $5}') LINES=$(wc -l < "$file" 2>/dev/null | tr -d ' ') BASENAME=$(basename "$file") echo "FILE:$file|SIZE:$SIZE|LINES:$LINES|NAME:$BASENAME" done DISCOVER_TXT_EOF
undefined
for file in $(fd -e txt . --max-depth 3 2>/dev/null | head -10); do SIZE=$(ls -lh "$file" 2>/dev/null | awk '{print $5}') LINES=$(wc -l < "$file" 2>/dev/null | tr -d ' ') BASENAME=$(basename "$file") echo "FILE:$file|SIZE:$SIZE|LINES:$LINES|NAME:$BASENAME" done DISCOVER_TXT_EOF
undefined

Step 1.2: Present File Selection (MANDATORY AskUserQuestion)

步骤1.2:展示文件选择选项(必须使用AskUserQuestion)

Question: "Which file would you like to analyze?"
Header: "File"
Options:
  - Label: "{filename}.txt ({size})"
    Description: "{line_count} lines"
  - Label: "{filename2}.txt ({size2})"
    Description: "{line_count2} lines"
  - Label: "Enter path"
    Description: "Provide a custom path to a .txt file"
  - Label: "Convert first"
    Description: "Run /asciinema-tools:convert before analysis"

问题: "你想分析哪个文件?"
标题: "文件选择"
选项:
  - 标签: "{filename}.txt ({size})"
    描述: "{line_count} 行"
  - 标签: "{filename2}.txt ({size2})"
    描述: "{line_count2} 行"
  - 标签: "输入路径"
    描述: "提供自定义的.txt文件路径"
  - 标签: "先转换格式"
    描述: "在分析前运行 /asciinema-tools:convert 转换格式"

Phase 2: Analysis Type (MANDATORY)

阶段2:分析类型选择(必填)

Purpose: Let user choose analysis depth.
Question: "What type of analysis do you need?"
Header: "Type"
Options:
  - Label: "Curated keywords (Recommended)"
    Description: "Fast search (50-200ms) with domain-specific keyword sets"
  - Label: "Auto-discover keywords"
    Description: "YAKE unsupervised extraction (1-5s) - finds unexpected patterns"
  - Label: "Full analysis"
    Description: "Both curated + auto-discovery for comprehensive results"
  - Label: "Density analysis"
    Description: "Find high-concentration sections (peak activity windows)"

目的:让用户选择分析的深度。
问题: "你需要哪种类型的分析?"
标题: "分析类型"
选项:
  - 标签: "预设关键词分析(推荐)"
    描述: "基于领域专属关键词集的快速搜索(耗时50-200ms)"
  - 标签: "自动发现关键词"
    描述: "YAKE无监督提取(耗时1-5s)- 发现未预设的模式"
  - 标签: "全面分析"
    描述: "同时进行预设关键词分析和自动发现,获取完整结果"
  - 标签: "密度分析"
    描述: "查找关键词浓度最高的段落(活跃峰值区间)"

Phase 3: Domain Selection (MANDATORY)

阶段3:领域选择(必填)

Purpose: Let user select which keyword domains to search.
Question: "Which domain keywords to search?"
Header: "Domain"
multiSelect: true
Options:
  - Label: "Trading/Quantitative"
    Description: "sharpe, sortino, calmar, backtest, drawdown, pnl, cagr, alpha, beta"
  - Label: "ML/AI"
    Description: "epoch, loss, accuracy, sota, training, model, validation, inference"
  - Label: "Development"
    Description: "iteration, refactor, fix, test, deploy, build, commit, merge"
  - Label: "Claude Code"
    Description: "Skill, TodoWrite, Read, Edit, Bash, Grep, iteration complete"
See Domain Keywords Reference for complete keyword lists.

目的:让用户选择要搜索的关键词领域。
问题: "你想搜索哪个领域的关键词?"
标题: "领域选择"
支持多选: 是
选项:
  - 标签: "交易/量化金融"
    描述: "sharpe、sortino、calmar、backtest、drawdown、pnl、cagr、alpha、beta"
  - 标签: "机器学习/人工智能"
    描述: "epoch、loss、accuracy、sota、training、model、validation、inference"
  - 标签: "软件开发"
    描述: "iteration、refactor、fix、test、deploy、build、commit、merge"
  - 标签: "Claude Code"
    描述: "Skill、TodoWrite、Read、Edit、Bash、Grep、iteration complete"
完整关键词列表请参考 领域关键词参考文档

Phase 4: Execute Curated Analysis

阶段4:执行预设关键词分析

Purpose: Run Grep searches for selected domain keywords.
目的:针对选中的领域运行Grep搜索。

Step 4.1: Trading Domain

步骤4.1:交易领域

bash
/usr/bin/env bash << 'TRADING_EOF'
INPUT_FILE="${1:?}"
echo "=== Trading/Quantitative Keywords ==="

KEYWORDS="sharpe sortino calmar backtest drawdown pnl cagr alpha beta roi volatility"
for kw in $KEYWORDS; do
  COUNT=$(rg -c -i "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done
TRADING_EOF
bash
/usr/bin/env bash << 'TRADING_EOF'
INPUT_FILE="${1:?}"
echo "=== 交易/量化金融关键词分析 ==="

KEYWORDS="sharpe sortino calmar backtest drawdown pnl cagr alpha beta roi volatility"
for kw in $KEYWORDS; do
  COUNT=$(rg -c -i "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done
TRADING_EOF

Step 4.2: ML/AI Domain

步骤4.2:机器学习/人工智能领域

bash
/usr/bin/env bash << 'ML_EOF'
INPUT_FILE="${1:?}"
echo "=== ML/AI Keywords ==="

KEYWORDS="epoch loss accuracy sota training model validation inference tensor gradient"
for kw in $KEYWORDS; do
  COUNT=$(rg -c -i "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done
ML_EOF
bash
/usr/bin/env bash << 'ML_EOF'
INPUT_FILE="${1:?}"
echo "=== 机器学习/人工智能关键词分析 ==="

KEYWORDS="epoch loss accuracy sota training model validation inference tensor gradient"
for kw in $KEYWORDS; do
  COUNT=$(rg -c -i "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done
ML_EOF

Step 4.3: Development Domain

步骤4.3:软件开发领域

bash
/usr/bin/env bash << 'DEV_EOF'
INPUT_FILE="${1:?}"
echo "=== Development Keywords ==="

KEYWORDS="iteration refactor fix test deploy build commit merge debug error"
for kw in $KEYWORDS; do
  COUNT=$(rg -c -i "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done
DEV_EOF
bash
/usr/bin/env bash << 'DEV_EOF'
INPUT_FILE="${1:?}"
echo "=== 软件开发关键词分析 ==="

KEYWORDS="iteration refactor fix test deploy build commit merge debug error"
for kw in $KEYWORDS; do
  COUNT=$(rg -c -i "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done
DEV_EOF

Step 4.4: Claude Code Domain

步骤4.4:Claude Code领域

bash
/usr/bin/env bash << 'CLAUDE_EOF'
INPUT_FILE="${1:?}"
echo "=== Claude Code Keywords ==="

KEYWORDS="Skill TodoWrite Read Edit Bash Grep Write"
for kw in $KEYWORDS; do
  COUNT=$(rg -c "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done
bash
/usr/bin/env bash << 'CLAUDE_EOF'
INPUT_FILE="${1:?}"
echo "=== Claude Code关键词分析 ==="

KEYWORDS="Skill TodoWrite Read Edit Bash Grep Write"
for kw in $KEYWORDS; do
  COUNT=$(rg -c "$kw" "$INPUT_FILE" 2>/dev/null || echo "0")
  if [[ "$COUNT" -gt 0 ]]; then
    echo "  $kw: $COUNT"
  fi
done

Special patterns

特殊模式匹配

ITERATION=$(rg -c "iteration complete" "$INPUT_FILE" 2>/dev/null || echo "0") echo " 'iteration complete': $ITERATION" CLAUDE_EOF

---
ITERATION=$(rg -c "iteration complete" "$INPUT_FILE" 2>/dev/null || echo "0") echo " 'iteration complete': $ITERATION" CLAUDE_EOF

---

Phase 5: YAKE Auto-Discovery (if selected)

阶段5:YAKE自动发现分析(若选中)

Purpose: Run unsupervised keyword extraction.
bash
/usr/bin/env bash << 'YAKE_EOF'
INPUT_FILE="${1:?}"
echo "=== Auto-discovered Keywords (YAKE) ==="

uv run --with yake python3 -c "
import yake

kw = yake.KeywordExtractor(
    lan='en',
    n=2,           # bi-grams
    dedupLim=0.9,  # dedup threshold
    top=20         # top keywords
)

with open('$INPUT_FILE') as f:
    text = f.read()

keywords = kw.extract_keywords(text)
for score, keyword in keywords:
    print(f'{score:.4f}  {keyword}')
"
YAKE_EOF

目的:运行无监督关键词提取。
bash
/usr/bin/env bash << 'YAKE_EOF'
INPUT_FILE="${1:?}"
echo "=== YAKE自动发现关键词 ==="

uv run --with yake python3 -c "
import yake

kw = yake.KeywordExtractor(
    lan='en',
    n=2,           # 提取双词组合
    dedupLim=0.9,  # 去重阈值
    top=20         # 提取前20个关键词
)

with open('$INPUT_FILE') as f:
    text = f.read()

keywords = kw.extract_keywords(text)
for score, keyword in keywords:
    print(f'{score:.4f}  {keyword}')
"
YAKE_EOF

Phase 6: Density Analysis (if selected)

阶段6:密度分析(若选中)

Purpose: Find sections with highest keyword concentration.
bash
/usr/bin/env bash << 'DENSITY_EOF'
INPUT_FILE="${1:?}"
KEYWORD="${2:-sharpe}"
WINDOW_SIZE=100  # lines

echo "=== Density Analysis: '$KEYWORD' ==="
echo "Window size: $WINDOW_SIZE lines"
echo ""

TOTAL_LINES=$(wc -l < "$INPUT_FILE" | tr -d ' ')
TOTAL_MATCHES=$(rg -c -i "$KEYWORD" "$INPUT_FILE" 2>/dev/null || echo "0")

echo "Total matches: $TOTAL_MATCHES in $TOTAL_LINES lines"
echo "Overall density: $(echo "scale=4; $TOTAL_MATCHES / $TOTAL_LINES * 1000" | bc) per 1000 lines"
echo ""
目的:查找关键词浓度最高的段落。
bash
/usr/bin/env bash << 'DENSITY_EOF'
INPUT_FILE="${1:?}"
KEYWORD="${2:-sharpe}"
WINDOW_SIZE=100  # 窗口大小(行数)

echo "=== 密度分析: '$KEYWORD' ==="
echo "窗口大小: $WINDOW_SIZE 行"
echo ""

TOTAL_LINES=$(wc -l < "$INPUT_FILE" | tr -d ' ')
TOTAL_MATCHES=$(rg -c -i "$KEYWORD" "$INPUT_FILE" 2>/dev/null || echo "0")

echo "总匹配次数: $TOTAL_MATCHES 次,共 $TOTAL_LINES 行"
echo "整体密度: $(echo "scale=4; $TOTAL_MATCHES / $TOTAL_LINES * 1000" | bc) 次/千行"
echo ""

Find peak windows

查找峰值窗口

echo "Top 5 densest windows:" awk -v ws="$WINDOW_SIZE" -v kw="$KEYWORD" ' BEGIN { IGNORECASE=1 } { lines[NR] = $0 if (tolower($0) ~ tolower(kw)) matches[NR] = 1 } END { for (start = 1; start <= NR - ws; start += ws/2) { count = 0 for (i = start; i < start + ws && i <= NR; i++) { if (matches[i]) count++ } if (count > 0) { printf "Lines %d-%d: %d matches (%.1f per 100)\n", start, start+ws-1, count, count*100/ws } } } ' "$INPUT_FILE" | sort -t: -k2 -rn | head -5 DENSITY_EOF

---
echo "关键词密度最高的5个窗口:" awk -v ws="$WINDOW_SIZE" -v kw="$KEYWORD" ' BEGIN { IGNORECASE=1 } { lines[NR] = $0 if (tolower($0) ~ tolower(kw)) matches[NR] = 1 } END { for (start = 1; start <= NR - ws; start += ws/2) { count = 0 for (i = start; i < start + ws && i <= NR; i++) { if (matches[i]) count++ } if (count > 0) { printf "第 %d-%d 行: %d 次匹配 (每百行 %.1f 次)\n", start, start+ws-1, count, count*100/ws } } } ' "$INPUT_FILE" | sort -t: -k2 -rn | head -5 DENSITY_EOF

---

Phase 7: Report Format (MANDATORY)

阶段7:报告格式选择(必填)

Purpose: Let user choose output format.
Question: "How should results be presented?"
Header: "Output"
Options:
  - Label: "Summary table (Recommended)"
    Description: "Keyword counts + top 5 peak sections"
  - Label: "Detailed report"
    Description: "Full analysis with timestamps and surrounding context"
  - Label: "JSON export"
    Description: "Machine-readable output for further processing"
  - Label: "Markdown report"
    Description: "Save formatted report to file"

目的:让用户选择结果的展示格式。
问题: "你希望结果以什么格式展示?"
标题: "输出格式"
选项:
  - 标签: "汇总表格(推荐)"
    描述: "关键词统计结果 + 前5个密度峰值段落"
  - 标签: "详细报告"
    描述: "包含时间戳和上下文的完整分析结果"
  - 标签: "JSON导出"
    描述: "机器可读格式,便于后续处理"
  - 标签: "Markdown报告"
    描述: "保存为格式化的Markdown文件"

Phase 8: Follow-up Actions (MANDATORY)

阶段8:后续操作选择(必填)

Purpose: Guide user to next action.
Question: "Analysis complete. What's next?"
Header: "Next"
Options:
  - Label: "Jump to peak section"
    Description: "Read the highest-density section in the file"
  - Label: "Search for specific keyword"
    Description: "Grep for a custom term with context"
  - Label: "Cross-reference with .cast"
    Description: "Map findings back to original timestamps"
  - Label: "Done"
    Description: "Exit - no further action needed"

目的:引导用户进行后续操作。
问题: "分析完成。接下来要做什么?"
标题: "后续操作"
选项:
  - 标签: "跳转至峰值段落"
    描述: "查看文件中关键词密度最高的段落"
  - 标签: "搜索自定义关键词"
    描述: "使用Grep搜索自定义术语并展示上下文"
  - 标签: "与.cast文件关联"
    描述: "将分析结果映射回原始录屏的时间戳"
  - 标签: "完成"
    描述: "退出 - 无需进一步操作"

TodoWrite Task Template

TodoWrite任务模板

1. [Preflight] Check input file exists and is .txt format
2. [Preflight] Suggest /convert if .cast file provided
3. [Discovery] Find .txt files with line counts
4. [Selection] AskUserQuestion: file to analyze
5. [Type] AskUserQuestion: analysis type (curated/auto/full/density)
6. [Domain] AskUserQuestion: keyword domains (multi-select)
7. [Curated] Run Grep searches for selected domains
8. [Auto] Run YAKE if auto-discovery selected
9. [Density] Calculate density windows if requested
10. [Format] AskUserQuestion: report format
11. [Next] AskUserQuestion: follow-up actions

1. [前置检查] 验证输入文件存在且为.txt格式
2. [前置检查] 若提供的是.cast文件,建议先运行/convert进行转换
3. [发现] 查找带行数统计的.txt文件
4. [选择] 询问用户:要分析的文件
5. [类型] 询问用户:分析类型(预设/自动/全面/密度)
6. [领域] 询问用户:关键词领域(支持多选)
7. [预设分析] 针对选中领域运行Grep搜索
8. [自动分析] 若选中自动发现,则运行YAKE
9. [密度分析] 若请求则计算密度窗口
10. [格式] 询问用户:报告格式
11. [后续] 询问用户:后续操作

Post-Change Checklist

修改后检查清单

After modifying this skill:
  1. All bash blocks use heredoc wrapper
  2. Curated keywords match references/domain-keywords.md
  3. Analysis tiers match references/analysis-tiers.md
  4. YAKE invocation uses
    uv run --with yake
  5. All AskUserQuestion phases are present
  6. TodoWrite template matches actual workflow

在修改本工具后,请检查以下内容:
  1. 所有bash代码块均使用heredoc包装
  2. 预设关键词与
    references/domain-keywords.md
    保持一致
  3. 分层分析机制与
    references/analysis-tiers.md
    保持一致
  4. YAKE调用使用
    uv run --with yake
    命令
  5. 所有AskUserQuestion交互阶段均已包含
  6. TodoWrite模板与实际工作流一致

Reference Documentation

参考文档



Troubleshooting

故障排查

IssueCauseSolution
"WRONG_FORMAT" error.cast file providedRun /asciinema-tools:convert first to create .txt
ripgrep not foundNot installed
brew install ripgrep
YAKE import errorPackage not installed
uv run --with yake
handles this automatically
No keywords foundWrong domain selectedTry different domain or auto-discovery mode
Density analysis emptyKeyword not in fileUse curated search first to find valid keywords
File too large for YAKEMemory constraintsUse Tier 1 (ripgrep) only for large files
Zero matches in all domainsFile is binary or corruptedVerify file is plain text with
file
command
fd command not foundNot installed
brew install fd
or use
find
alternative
问题原因解决方案
出现"WRONG_FORMAT"错误提供了.cast格式文件先运行/asciinema-tools:convert转换为.txt格式
找不到ripgrep未安装ripgrep执行
brew install ripgrep
进行安装
YAKE导入错误未安装YAKE依赖
uv run --with yake
会自动处理依赖安装
未找到任何关键词选择的领域不正确尝试更换领域或使用自动发现模式
密度分析结果为空文件中无该关键词先使用预设搜索找到有效的关键词
YAKE处理大文件失败内存限制仅使用第1层级(ripgrep)处理大文件
所有领域均无匹配结果文件为二进制或已损坏使用
file
命令验证文件是否为纯文本格式
找不到fd命令未安装fd执行
brew install fd
或使用
find
命令替代