Skip to content

Releases: studiogo/skill-router

v0.3.0 — priority boost + rules corpus + auto-skill-rules

Choose a tag to compare

@studiogo studiogo released this 23 Apr 03:28

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

Choose a tag to compare

@studiogo studiogo released this 23 Apr 03:08

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

Choose a tag to compare

@studiogo studiogo released this 22 Apr 15:21

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 starter skill-rules.json in 30 seconds.
  • install.sh — idempotent installer. Backs up settings.json before touching it, refuses to duplicate the hook registration, works from a local clone or curl | 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).