From outfitter
Systematic debugging process for @outfitter/* package issues. Use when debugging Result handling, MCP problems, CLI output, exit codes, logging, or unexpected behavior. Produces structured investigation reports with root cause analysis.
npx claudepluginhub outfitter-dev/outfitter --plugin outfitterThis skill is limited to using the following tools:
Systematic debugging process for @outfitter/\* package issues.
Generates design tokens/docs from CSS/Tailwind/styled-components codebases, audits visual consistency across 10 dimensions, detects AI slop in UI.
Records polished WebM UI demo videos of web apps using Playwright with cursor overlay, natural pacing, and three-phase scripting. Activates for demo, walkthrough, screen recording, or tutorial requests.
Delivers idiomatic Kotlin patterns for null safety, immutability, sealed classes, coroutines, Flows, extensions, DSL builders, and Gradle DSL. Use when writing, reviewing, refactoring, or designing Kotlin code.
Systematic debugging process for @outfitter/* package issues.
Investigate issues methodically and produce a structured report documenting:
DO:
outfitter-atlas for correct patternsDON'T:
outfitter-atlas skill to gain expertise in the Outfitter packages.outfitter-issueGather symptoms before forming hypotheses.
# Check package versions
bun pm ls | grep @outfitter
# Find Result usage patterns
rg "Result\.(ok|err)" --type ts -A 2
# Find error handling
rg "isErr\(\)|isOk\(\)" --type ts -A 3
# Check for thrown exceptions (anti-pattern)
rg "throw new" --type ts
Based on symptoms, identify the issue category:
| Category | Symptoms | Common Causes |
|---|---|---|
| Result Handling | Wrong value, type errors | Missing await, reassignment breaking narrowing |
| MCP Issues | Tool not appearing, invocation failing | Registration order, missing schema descriptions |
| CLI Output | Wrong format, missing data | Mode detection, await on output |
| Exit Codes | Wrong exit code | Not using exitWithError, manual process.exit |
| Logging | Missing logs, sensitive data exposed | Wrong level, redaction disabled |
| Validation | Unexpected validation errors | Schema mismatch, missing .describe() |
Always getting error:
// Check: Missing await?
const result = getUser(id); // ❌ Promise, not Result!
const result = await getUser(id); // ✅
// Check: Validation failing?
const validated = validate(input);
if (validated.isErr()) {
console.log("Validation failed:", validated.error.context);
}
Type narrowing broken:
// ❌ Reassigning breaks narrowing
let result = await getUser(id);
if (result.isOk()) {
result = await updateUser(result.value); // Breaks!
}
// ✅ Separate variables
const getResult = await getUser(id);
if (getResult.isErr()) return getResult;
const updateResult = await updateUser(getResult.value);
Error type lost:
// Use _tag for narrowing
if (result.isErr()) {
switch (result.error._tag) {
case "ValidationError":
console.log(result.error.context);
break;
case "NotFoundError":
console.log(result.error.resourceId);
break;
}
}
Tool not appearing:
Verify registration happens before start():
server.registerTool(myTool);
server.start(); // After registration!
Check schema has .describe() on all fields:
const schema = z.object({
query: z.string().describe("Required for AI"),
});
Tool invocation failing:
Handler must be async:
handler: async (input) => {
// Not sync!
return Result.ok(data);
};
Must return Result:
// ❌ return { data: "value" };
// ✅ return Result.ok({ data: "value" });
JSON not printing:
// Force mode
await output(data, { mode: "json" });
// Check environment
// OUTFITTER_JSON=1 forces JSON
// OUTFITTER_JSON=0 forces human when no explicit mode is set
// Await output before exit
await output(data); // ✅
// process.exit(0); // May exit before output completes
Wrong exit code:
// ❌ process.exit(1);
// ✅ exitWithError(result.error);
Exit code reference:
| Category | Exit |
|---|---|
| validation | 1 |
| not_found | 2 |
| conflict | 3 |
| permission | 4 |
| timeout | 5 |
| rate_limit | 6 |
| network | 7 |
| internal | 8 |
| auth | 9 |
| cancelled | 130 |
Redaction not working:
const logger = createLogger({
redaction: { enabled: true }, // Must be true!
// Custom patterns
redaction: {
enabled: true,
patterns: ["password", "apiKey", "myCustomSecret"],
},
});
Missing context:
const requestLogger = createChildLogger(ctx.logger, {
requestId: ctx.requestId,
handler: "myHandler",
});
requestLogger.info("Processing", { data }); // Includes requestId
Wrong level:
// Hierarchy: trace < debug < info < warn < error < fatal
// "info" hides trace and debug
const logger = createLogger({
level: process.env.LOG_LEVEL || "info",
});
Assess confidence in your diagnosis:
| Confidence | Meaning |
|---|---|
| High | Clear pattern violation or bug found with evidence |
| Medium | Likely cause identified, may need verification |
| Low | Multiple possibilities remain, needs more investigation |
Based on diagnosis, recommend:
outfitter-issueProduce a Debug Report using TEMPLATE.md.
If investigation reveals an issue in @outfitter/* packages themselves (not user code):
outfitter-issue skill to file an issueoutfitter-atlas — Correct patterns referenceoutfitter-check — Compliance verificationoutfitter-issue — Report issues to Outfitter team