Skill1.3k estrellas del repoactualizado today
spec-kitty-bulk-edit-classification
spec-kitty-bulk-edit-classification recognizes when a user requests changes that affect the same string across multiple locations, such as renaming identifiers, migrating terminology, or moving file paths, and activates a classification workflow to prevent silent breakage from context-dependent meaning shifts. Use this skill during specify or plan phases when the user describes renames, feature relabels, path moves, or config key changes, or when runtime gates print bulk edit blocking messages.
Instalar en Claude Code
Copiargit clone --depth 1 https://github.com/Priivacy-ai/spec-kitty /tmp/spec-kitty-bulk-edit-classification && cp -r /tmp/spec-kitty-bulk-edit-classification/src/doctrine/skills/spec-kitty-bulk-edit-classification ~/.claude/skills/spec-kitty-bulk-edit-classificationDespués abre una sesión nueva de Claude Code; el skill carga automáticamente.
Definición
SKILL.md
# spec-kitty-bulk-edit-classification
Drive the occurrence-classification guardrail (shipped in #393, DIRECTIVE_035)
so users never have to know it exists. A bulk edit is any change that touches
the **same string** in many places — a rename, a terminology migration, a
package-path move, a feature-label swap. Those changes look mechanical but
aren't: the same token carries different meaning depending on where it appears
(code symbol, import path, filesystem literal, serialized key, CLI command,
user-facing string, test fixture, log/telemetry label). Treating them uniformly
is how silent breakage happens.
**The user will not say "bulk edit".** They will say "rename Coffee to Tea" or
"the Blue feature is now the Red feature." Your job is to recognize that
shape, turn on `change_mode: bulk_edit`, and drive the classification workflow
before any code changes.
---
## When to activate
Apply this skill during **specify** or **plan** when the user's description
matches any of these patterns:
| Pattern | Example phrasing |
|---|---|
| Explicit rename | "Rename `Customer` to `Account` across the codebase" |
| Terminology migration | "We're calling it 'channels' now, not 'streams'" |
| Feature relabel | "The Blue feature is now the Red feature" |
| Path/module move | "Move `src/legacy/auth` to `src/auth`" |
| API surface rename | "Rename the `/users` endpoint to `/accounts`" |
| Config key rename | "Change `max_connections` to `connection_limit` everywhere" |
| Brand / product rename | "Replace ACME with GlobalCorp in all docs and UI" |
Also apply when the implement or review command prints a message starting
with **"Bulk Edit Gate: BLOCKED"** or **"Bulk Edit Review: Diff Compliance"** —
these are the runtime gates' failure output; this skill tells you how to
respond.
**Do NOT apply when** the user is:
- Adding a genuinely new feature (new identifiers, new files) — no existing
identifiers change
- Refactoring the internals of one file or one function — no cross-cutting
string change
- Fixing a bug where the surface names stay the same
---
## The core decision tree
At the start of `specify` or `plan`, after you understand the user's intent,
ask yourself this one question:
> Does fulfilling this request require changing the **same existing string**
> (identifier, path, key, label) in more than one file?
If **yes**: this is a bulk edit. Set `change_mode: bulk_edit` and run the
classification workflow below.
If **no**: proceed normally. The guardrail stays dormant.
If **uncertain**: treat as bulk edit. The cost of a false positive is drafting
an occurrence map the user can approve in one pass. The cost of a false
negative is the silent-breakage class of bugs #393 was created to prevent.
---
## What to do during specify
1. **Detect intent.** Read the user's feature description. If it matches the
patterns above, you have a bulk edit.
2. **Set `change_mode` in `meta.json`.** Use the CLI helper — do not hand-edit
JSON:
```python
from specify_cli.mission_metadata import set_change_mode
set_change_mode(feature_dir, "bulk_edit")
```
Or via shell after `mission create`:
```bash
python -c "from specify_cli.mission_metadata import set_change_mode; \
set_change_mode('<feature_dir>', 'bulk_edit')"
```
3. **Name the target in the spec.** In `spec.md`, state explicitly what's
being renamed and to what:
> "This mission renames `Customer` (old term) to `Account` (new term)
> across the codebase, with per-category rules captured in
> `occurrence_map.yaml`."
Do NOT rely on the reviewer inferring the rename from prose. Make it an
explicit claim that the occurrence map must satisfy.
4. **Tell the user, briefly**, that you're turning on the classification
workflow. Use plain language — they don't need to know the field name:
> "This is a cross-cutting rename, so I'm going to produce an
> `occurrence_map.yaml` during planning that decides which kinds of
> occurrences get renamed vs. left alone (API response keys, CLI commands,
> and metric labels are typically left alone to avoid breaking consumers).
> You'll review and approve that map before any code changes."
---
## What to do during plan
Produce `kitty-specs/<mission>/occurrence_map.yaml` with **all 8 standard
categories present**. Leaving a category out is an error the gate rejects —
every standard risk surface must have an explicit action assignment.
### The template to fill
The starter template lives in `src/doctrine/templates/occurrence-map-template.yaml`
and the machine-enforced schema lives in `src/doctrine/schemas/occurrence-map.schema.yaml`.
Do not copy the shape from prose — load the actual file so you never drift from
the contract that the runtime gate enforces:
```python
from specify_cli.bulk_edit.occurrence_map import (
load_template_text, # starter YAML text to seed occurrence_map.yaml
load_schema, # JSON Schema dict (Draft 2020-12)
validate_against_schema, # raw dict -> ValidationResult
)
# Seed the file:
(feature_dir / "occurrence_map.yaml").write_text(load_template_text())
```
The template is a complete, syntactically valid occurrence map with sane
category defaults and placeholders only for `target.term`/`target.replacement`.
Adjust per-category actions to fit the mission, then validate:
```python
import yaml
from specify_cli.bulk_edit.occurrence_map import validate_against_schema
raw = yaml.safe_load((feature_dir / "occurrence_map.yaml").read_text())
result = validate_against_schema(raw)
assert result.valid, result.errors
```
### Valid actions (exact strings — the gate rejects typos)
| Action | When to use |
|---|---|
| `rename` | Safe to mechanically replace old → new |
| `manual_review` | Each occurrence needs case-by-case judgment |
| `do_not_change` | Must not be modified; renaming breaks external consumers |
| `rename_if_user_visible` | Rename where the string is shown to a user; preserve otherwise