skills/assistant/type-system-audit/SKILL.md
Audit a repository for type-system weaknesses using recent bug-fix commits as hard evidence. Produces prioritized findings tied to specific commits showing which types allowed real bugs. Use when: reviewing type safety, auditing types, analyzing type bugs. Triggers on: type audit, type system review, audit types, type safety audit.
npx skillsauth add ravnhq/ai-toolkit type-system-auditInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Audit a repository for type-system weaknesses using bug-fix commits as hard evidence—not speculation. Identify which types allowed invalid states that caused real bugs, and recommend stricter types that would prevent entire defect classes. All findings are tied to specific commits for credibility.
Determine the primary language(s) and type system in use. Use the table below to adapt the audit approach:
| Language | Nullability patterns | Sum types | Boundary validation | File extensions |
|----------|---------------------|-----------|--------------------|-----------------|
| TypeScript | T \| null \| undefined, optional chaining | Discriminated unions, literal types | zod, io-ts, yup | .ts, .tsx |
| Swift | Optional<T> / ?, force-unwrap ! | enum with associated values | Codable, custom init | .swift |
| Kotlin | T?, !!, null-safe operators | sealed class / when | @Serializable, require() | .kt |
| Python | Optional[T], None checks | Union, Literal, TypedDict | pydantic, attrs | .py, .pyi |
Run Stage 1 first (high-signal conventional commits):
# Stage 1: conventional commits (high signal)
git log --oneline --since="90 days ago" | grep -iE "^[0-9a-f]+ (fix|bugfix|hotfix|patch)[\(:]"
# Stage 2: broader keyword sweep (fallback)
git log --oneline --since="90 days ago" | grep -iE "fix|bug|crash|error|null|undefined|invalid|wrong|closes|resolves|#[0-9]+"
Decision points:
--since="180 days ago" if total candidates are still fewer than 5.git log --format="%H %s%n%b" --since="90 days ago" to surface original PR messages.Select 10–20 candidates. Prefer commits touching domain logic, data models, or API boundaries.
For each candidate commit, inspect the diff:
git show {sha} --stat # Overview: which files changed
git show {sha} -- '*.ts' # Scope to language-specific files
Large-diff guidance (>500 lines): use --stat to identify type-definition files, then read only those files. Skip auto-generated files (e.g., *.generated.ts, schema.graphql.ts).
Look for: type definitions and interfaces changed, added guards or normalization logic, null checks added, validation added at API boundaries, test changes that hint at a shape mismatch.
Apply the "What to Look For" patterns to each commit. Record every match as a candidate finding.
Discard criteria — skip a commit if:
For each confirmed finding, fill out the per-finding template. Cite the specific commit SHA and the exact file and type involved.
To check if a weakness persists today:
git show HEAD:path/to/type.ts # Read current version of the type file
Cross-validation gate — before finalizing a finding, answer:
[partial].Produce all required output sections. Prioritize findings by blast radius: how many call sites or bugs would a stricter type prevent?
Quality gate before finalizing: verify all 7 template fields are filled for every finding. A finding with empty fields is not ready.
Refer to references/common-type-weakness-patterns.md for detailed explanations and examples of each weakness type. Core patterns to recognize:
null or absent but aren't encoded in the type"", "null", -1, 0 used where null | T would be correctstatus: "complete" with completedAt: null)any as a workaround — type issues solved with any instead of fixing the underlying type| Field | Content | |-------|---------| | Commit | SHA and one-line message | | Bug fixed | What the bug was and how it manifested | | Invalid state allowed | The exact invalid value or combination the type permitted | | Type weakness | Which type, field, or signature was too permissive | | Stricter design | The proposed type that would make the invalid state unrepresentable | | Fix location | File and line range (type definition or function signature) | | Benefit | What defects or guards the stricter type eliminates |
[inferred].## Commits Reviewed
| SHA | Date | Message |
|-----|------|---------|
| {sha1} | {date1} | {message1} |
| {sha2} | {date2} | {message2} |
## Strongest Findings
### Finding 1
| Field | Content |
|-------|---------|
| **Commit** | {sha} — {one-line message} |
| **Bug fixed** | {what the bug was and how it manifested} |
| **Invalid state allowed** | {exact invalid value or combination the type permitted} |
| **Type weakness** | {which type, field, or signature was too permissive} |
| **Stricter design** | {proposed type that makes the invalid state unrepresentable} |
| **Fix location** | `{file}:{line-range}` |
| **Benefit** | {defects or guards the stricter type eliminates} |
### Finding 2
| Field | Content |
|-------|---------|
| **Commit** | {sha} — {one-line message} |
| **Bug fixed** | {what the bug was and how it manifested} |
| **Invalid state allowed** | {exact invalid value or combination the type permitted} |
| **Type weakness** | {which type, field, or signature was too permissive} |
| **Stricter design** | {proposed type that makes the invalid state unrepresentable} |
| **Fix location** | `{file}:{line-range}` |
| **Benefit** | {defects or guards the stricter type eliminates} |
<!-- Repeat Finding N block for each finding (target 5–8 total) -->
## Bugs Better Types Would Have Prevented
- `{sha1}` — {description of the bug}. A stricter type (`{proposed type}`) would have {caught this at compile time / made this state unrepresentable / forced callers to handle the missing case explicitly}.
- `{sha2}` — {description of the bug}. {How the stricter type catches it at compile time}.
## Tests / Guards Better Types Could Replace
| File | Guard / Test | Type Weakness It Compensates | Replacement |
|------|-------------|------------------------------|-------------|
| `{file}` | `{guard or test description}` | `{type}` is too permissive — allows `{invalid value}` | Narrow to `{proposed type}`; remove guard |
| `{file}` | `{guard or test description}` | `{type}` is too permissive — allows `{invalid value}` | Narrow to `{proposed type}`; remove guard |
## Priority Type Refactors
1. **`{TypeName}`** — `{file}` — Change `{current type}` to `{proposed type}`. Addresses commits: {sha1}, {sha2}.
2. **`{TypeName}`** — `{file}` — Change `{current type}` to `{proposed type}`. Addresses commits: {sha1}.
3. **`{TypeName}`** — `{file}` — Change `{current type}` to `{proposed type}`. Addresses commits: {sha1}, {sha2}, {sha3}.
User: "audit the type system in this repo for weaknesses in recent bug-fix commits"
Expected behavior: Use type-system-audit to run git log for recent fix commits, inspect each for type-related weaknesses, generate findings using the per-finding template, and produce all required output sections.
User: "review type safety — we've been having a lot of null crashes"
Expected behavior: Use type-system-audit to mine bug-fix commits for evidence of null/optional type weaknesses, produce findings tied to specific commits, and recommend priority refactors.
User: "enable strict mode in tsconfig.json"
Expected behavior: Do not use type-system-audit. The user wants a configuration change, not a commit-based audit. Apply the change directly.
User: "what types does this module export?"
Expected behavior: Do not use type-system-audit. The user wants to understand the existing API surface, not audit it for weaknesses.
--since window or adjust the grep pattern to match the project's commit style (e.g., closes, resolves, patch).git log --oneline.git log --format="%H %s%n%b" --since="90 days ago" to surface original PR messages. Use --stat to scope large squash diffs to type-definition files before reading.git log returns commits spanning many packages and languages, making signal extraction hard.git log --oneline --since="90 days ago" -- packages/my-service/.git show {sha} --stat to identify type-definition files, then read only those with git show {sha} -- path/to/types.ts. Skip auto-generated files (e.g., *.generated.ts).testing
Transform user requests into detailed, precise prompts for AI models. Use when users say 'promptify', 'promptify this', 'rewrite this prompt', 'make this prompt better/more specific', or explicitly request prompt engineering or improvement of their request for better AI responses.
tools
Manage AI skills from the Ravn AI Toolkit via corvus CLI — install, update, remove, search, and configure skills for any project. Use when: (1) Installing AI skills into a project, (2) Updating installed skills to latest versions, (3) Browsing or searching available skills, (4) Configuring global or per-project skill sets, (5) Troubleshooting corvus setup. Triggers on: "install skills", "add skills", "update skills", "corvus", "skill manager", "browse skills", "set up AI rules".
development
Generate a gallery of design variations for a UI component. Takes an existing component (referenced by name, pasted code, or screenshot) and produces N distinct rendered alternatives in a single comparison page. Use when exploring visual directions, generating mockups, comparing design approaches for a component, creating A/B candidates, or when anyone says "show me options" or "give me variations" for a UI element.
tools
Create custom QA agent personalities for project-specific testing needs. Guided builder that asks about the specialty, tools, and test scenarios, then generates a personality file and registers it in the QA config. Trigger on "create a QA personality", "add a custom test agent", "build a webhook tester", or when the user needs a project-specific QA agent. Also triggered by /qa-create-personality.