Releases: studiogo/skill-router
Release list
v0.3.0 — priority boost + rules corpus + auto-skill-rules
Three tightly-linked upgrades that plug the most obvious gaps in v0.2:
1. Priority-weighted context rules
Every rule file can now declare its urgency in YAML frontmatter:
```yaml
name: Firewall Practima
description: Klauzula §9.4 — wabienie klientów Zamawiającego
priority: critical
```
BM25 final score gets multiplied by:
| priority | multiplier |
|---|---|
| critical | ×10 |
| high | ×3 |
| medium | ×1 (default) |
| low | ×0.3 |
Effect: safety rules (contracts, pricing, irreversible actions) practically never fall out of the top 3, even when a prompt matches something else more densely.
2. rules/*.md joined the corpus
Work-mode rules (`core.md`, `tools.md`, `research.md`, `content.md`, `kwiga.md`) were previously only read at session start. Now they compete for context slots alongside `feedback_*.md` — bumped to `priority: critical` so their longer prose doesn't lose to shorter feedback files via BM25 length normalization.
3. scripts/gen-skill-rules.py — auto-map from SKILL.md
One script inflates skill coverage from ~20% to ~94% without manually curating keyword lists:
```bash
python3 scripts/gen-skill-rules.py
```
- Walks `~/.claude/skills/*/SKILL.md`
- Extracts quoted trigger phrases from each skill's `description:` frontmatter (`"napisz post"`, `"zrób karuzelę"`)
- Adds the skill name itself as a fallback keyword
- Preserves existing manual `priority` values across regenerations
- Writes a timestamped `.bak-YYYYMMDD-HHMMSS` backup before overwriting
Run it once after installing a new skill or tweaking a description.
Upgrade path
```bash
curl -fsSL https://raw.githubusercontent.com/studiogo/skill-router/main/install.sh | bash
```
Idempotent — safe to rerun. Existing `skill-rules.json` is preserved (won't be overwritten), so your manual priorities stay.
What's next (v0.4 ideas)
- Deprecation support: `deprecated: true` in frontmatter, skip those during ranking
- Corpus caching (avoid re-tokenizing on every prompt — matters at > 200 rule files)
- Usage telemetry: track which rules Claude actually applied, surface dead/unused rules
Inspired by the public diet103/claude-code-infrastructure-showcase (MIT).
v0.2.0 — BM25 context rules
New in v0.2: The router now injects a second section — 📋 CONTEXT RULES — with up to 3 historical lessons from your memory/feedback_*.md files, ranked by a stdlib BM25 implementation. Claude sees them alongside the v0.1 skill suggestions and applies them automatically.
What it looks like
```
$ echo '{"prompt":"Zrób karuzelę na LinkedIn o AI agentach"}' | python3 skill-router.py
🎯 SKILL ACTIVATION: Rozważ użycie skilla `create-carousel`
📋 CONTEXT RULES (relevant memory):
→ feedback_carousel_default_style_b.md: Style B jest domyślny dla nowych karuzel LinkedIn od 18.04...
→ feedback_carousel_linkedin_style.md: Jak pisać teksty do karuzel i postów LinkedIn...
→ feedback_linkedin_api.md: Nie publikować przez Postiz — używać LinkedIn API bezpośrednio...
```
Why BM25, not a custom scorer?
BM25 (Best Matching 25) is the de-facto ranking standard in search engines — used by Google, Elasticsearch, Lucene for ~40 years. Battle-tested beats ad-hoc every time.
Implementation stays zero-deps: ~70 lines of pure Python stdlib (Okapi formula + IDF + length normalization + light Polish stemmer for inflections like wagę / waga / wagi). No MCP server, no pip install, no extra setup.
Noise suppression
- Filename + description boost (3×) — matches in high-signal fields rank higher than incidental words in prose
- Min 2 hits — doc must contain at least 2 different query terms (prevents one incidental word scoring high)
- Min score 3.0 — below threshold means the match is weak, drop it
- Stopword filter — trivial words (polskie i/a/na/to, English the/of/is) don't count
Backward compatibility
If you don't keep feedback notes in `~/.claude/projects//memory/feedback_.md`, v0.2 behaves exactly like v0.1 — just the SKILL ACTIVATION block. Nothing to configure.
What's next (v0.3 ideas)
- Corpus caching (avoid re-tokenizing all feedback files on every prompt)
- Priority field in frontmatter for manually boosted "pinned" rules
- `--test` mode for querying the corpus without triggering the hook
Inspired by the public diet103/claude-code-infrastructure-showcase (MIT).
v0.1.0 — initial release
First public release of skill-router — a drop-in UserPromptSubmit hook for Claude Code that suggests the right skill based on keywords in your prompt.
What's in
skill-router.py— 130-line Python hook, stdlib only. Normalizes Polish diacritics so"Zrób karuzelę"matches the keyword stem"karuzel". Auto-rotates its own log after 1 MB. Validates the config and degrades gracefully — never blocks your prompt.skill-router-stats.py— CLI log analyzer. Match rate %, top skills, and dead keywords (configured but never matched — the first thing to fix when suggestions feel off).skill-router-config-init.py— interactive wizard. Pick categories (content / inbox / scheduling / image-gen / dev / personal), get a starterskill-rules.jsonin 30 seconds.install.sh— idempotent installer. Backs upsettings.jsonbefore touching it, refuses to duplicate the hook registration, works from a local clone orcurl | bash.
Quick install
```bash
curl -fsSL https://raw.githubusercontent.com/studiogo/skill-router/main/install.sh | bash
```
Then in a new Claude Code session, type something with a keyword from your config and watch the reminder appear. Full docs in README.md.
What's next (v0.2 ideas)
- Auto-discovery of installed skills from `~/.claude/skills/` frontmatter
- `--dry-run` mode for testing keywords without triggering the hook
- Per-skill case sensitivity flag for proper nouns
Concept inspired by the public diet103/claude-code-infrastructure-showcase (MIT).