characterization-test-generator — independently scanned and version-tracked by SaferSkills.
SaferSkills independently audited characterization-test-generator (Plugin) and scored it 100/100 (green). The audit ran 55 deterministic rules across Security, Supply Chain, Maintenance, Transparency, and Community; it found 0 high-severity and 0 lower-severity findings. The full rule-by-rule trace and per-finding evidence are below. Free, methodology-open.
Findings & checks · 0 flagged
Every scanned point with the score it earned and what moved between them.
First recorded scan — no prior version to compare against.
The primary manifest — the file an agent reads to learn what this artifact does.
Lock your legacy code behavior before AI touches it.
A Claude Code plugin that generates characterization tests (also known as approval tests, golden master tests, or snapshot tests) for existing code. These tests document what your code actually does — not what it should do — creating a safety net before refactoring or AI-assisted modification.
AI coding agents are powerful but dangerous with legacy code:
Characterization tests prevent all three by locking current behavior before any changes.
"When a system goes into production, it becomes its own specification." — Michael Feathers, Working Effectively with Legacy Code
/plugin install characterization-test-generatorgit clone https://github.com/duybv/characterization-test-generator.git
cp -r characterization-test-generator/skills/characterize ~/.claude/skills//add-plugin characterization-test-generatorIn Claude Code, invoke:
/characterize src/services/optimizer.goOr describe what you need:
Generate characterization tests for the route optimization service before I refactor itThe skill will:
| Language | Test Framework | Snapshot Method |
|---|---|---|
| Go | testing | Golden files (testdata/golden/) |
| Python | pytest | approvaltests or manual golden files |
| TypeScript | jest | toMatchSnapshot() |
| JavaScript | jest | toMatchSnapshot() |
| Kotlin | JUnit | ApprovalTests |
| Java | JUnit | ApprovalTests |
Based on the Feathers Method (Michael Feathers, 2004):
1. Write test named "x" with expected = null
2. Run test → fails, revealing actual output
3. Paste actual output as expected value
4. Rename test to describe discovered behavior
5. Repeat for different inputs and code pathsThis plugin automates steps 1-5 using AI:
┌─────────────────┐ ┌──────────────────┐ ┌─────────────────┐
│ AI reads code │────▶│ Generates tests │────▶│ Human reviews │
│ (understands │ │ with realistic │ │ and approves │
│ all paths) │ │ inputs + scrubbing│ │ the tests │
└─────────────────┘ └──────────────────┘ └────────┬────────┘
│
┌──────────────────┐ │
│ Safe to refactor │◀────────────┘
│ or use AI agents │
└──────────────────┘func TestCharacterize_OptimizeRoute_BasicInput(t *testing.T) {
input := loadFixture(t, "testdata/10_stops_2_warehouses.json")
result, err := solver.Optimize(input)
require.NoError(t, err)
golden := filepath.Join("testdata", "golden", t.Name()+".json")
actual := toJSON(t, scrub(result))
if *update {
os.WriteFile(golden, actual, 0644)
return
}
expected, _ := os.ReadFile(golden)
assert.JSONEq(t, string(expected), string(actual))
}from approvaltests import verify_as_json
def test_characterize_calculate_distance():
result = calculate_distance(lat1=10.7, lon1=106.7, lat2=21.0, lon2=105.8)
verify_as_json(scrub(result))test("characterize formatAddress", () => {
const result = formatAddress({ street: "Nguyen Hue", city: "HCM" });
expect(scrub(result)).toMatchSnapshot();
});| Characterization Test | Unit Test | E2E Test | |
|---|---|---|---|
| Purpose | Document current behavior | Verify correctness | Verify user flow |
| When | Before changing legacy code | When building new features | After building features |
| Fail means | Behavior changed | Code is wrong | User flow broken |
| Written by | AI (reviewed by human) | Developer | QA/Developer |
From understandlegacycode.com:
Phase 1: PROTECT
/characterize src/services/ ← this plugin
Commit characterization tests
Phase 2: CHANGE
AI refactors code
Run characterization tests
→ All pass? ✅ Behavior preserved
→ Some fail? ⚠️ Review what changed
Phase 3: EVOLVE
Write proper unit tests (TDD) ← use superpowers/test-driven-development
Gradually replace characterization tests with intent-based testsThis plugin is based on research and practices from:
characterization-test-generator/
├── .claude-plugin/
│ └── plugin.json # Plugin metadata
├── skills/
│ └── characterize/
│ ├── SKILL.md # Main skill instructions
│ └── references/
│ ├── theory.md # Background theory & citations
│ └── language-patterns.md # Code patterns per language
├── docs/
│ └── workflow.md # Detailed workflow guide
├── tests/ # Plugin tests
├── README.md
└── LICENSE (MIT)MIT — see LICENSE for details.
Built for developers who maintain legacy code in the age of AI.
If AI is going to touch your code, make sure you have a safety net first.
~30 seconds. Free. No account. Every finding cites a rule and a line of evidence.