documentation

$npx mdskill add EpicenterHQ/epicenter/documentation

Writes clear in-code documentation and READMEs explaining the why, not the what

  • Solves the problem of unclear code intent and missing rationale in documentation
  • Uses JSDoc, code comments, and folder READMEs to explain decisions and architecture
  • Focuses on non-obvious context, boundaries, and relationships in the codebase
  • Delivers structured explanations that help developers understand and maintain the code

SKILL.md

.github/skills/documentationView on GitHub ↗
---
name: documentation
description: 'In-code documentation, folder READMEs, code comments. Use when: "document this", "add JSDoc", "write a README", "explain this code", or writing README.md/JSDoc.'
metadata:
  author: epicenter
  version: '1.0'
---

# Documentation

Follow [writing-voice](../writing-voice/SKILL.md) for tone.
For architecture walkthroughs, folder mental models, or newcomer explanations, use [notebook-explanation](../notebook-explanation/SKILL.md) for the shape.

Documentation explains **why**, not **what**. Users can read code to see what it does. They need you to explain the reasoning.

## When to Apply This Skill

Use this pattern when you need to:

- Write or update folder `README.md` files with architecture intent.
- Add JSDoc to public APIs with usage context and examples.
- Review docs/comments that currently restate code without rationale.
- Add code comments for non-obvious decisions, constraints, or workarounds.

## Folder READMEs

Primary job: explain **why** this folder exists and the mental model.

Notebook style is often the clearest README opening:

```txt
Question:
  Why does this folder exist?

Model:
  file group = responsibility
  boundary = owner

Flow:
  input
    -> module
    -> output

Rule:
  when adding code here, preserve this boundary
```

### Can Include

- ASCII art diagrams for complex relationships
- Overview of key exports or entry points
- Brief file descriptions IF they add context beyond the filename
- Relationships to other folders

### Avoid

- Exhaustive file listings that just duplicate `ls`
- Descriptions that repeat the filename ("auth.ts - authentication")
- Implementation details better expressed in code

### Good

````markdown
# Converters

Transform field schemas into format-specific representations.

```
┌─────────────┐     ┌──────────────┐
│ Field Schema│────▶│  to-arktype  │────▶ Runtime validation
└─────────────┘     ├──────────────┤
                    │  to-drizzle  │────▶ SQLite columns
                    └──────────────┘
```

Field schemas are pure JSON Schema objects with `x-component` hints. Each converter takes the same input and produces output for a specific consumer.
````

### Bad

```markdown
# Converters

- `to-arktype.ts` - Converts to ArkType
- `to-drizzle.ts` - Converts to Drizzle
- `index.ts` - Exports
```

The bad example just lists files without explaining the pattern or when to add new converters.

## JSDoc Comments

JSDoc explains **when and why** to use something, not just what it does.

### Good

````typescript
/**
 * Get all table helpers as an array.
 *
 * Useful for providers and indexes that need to iterate over all tables.
 * Returns only the table helpers, excluding utility methods like `clearAll`.
 *
 * @example
 * ```typescript
 * for (const table of tables.defined()) {
 *   console.log(table.name, table.count());
 * }
 * ```
 */
defined() { ... }
````

### Bad

```typescript
/** Returns all table helpers as an array. */
defined() { ... }
```

### Rules

- Include `@example` blocks with realistic usage
- Explain WHEN to use it, not just WHAT it does
- Document non-obvious behavior or edge cases
- Public APIs get detailed docs; internal helpers can be minimal

## Code Comments

Comments explain **why**, not **what**.

### Good

```typescript
// Y.Doc clientIDs are random 32-bit integers, so we can't rely on ordering.
// Use timestamps from the entries themselves for deterministic sorting.
const sorted = entries.sort((a, b) => a.timestamp - b.timestamp);
```

### Bad

```typescript
// Sort the entries
const sorted = entries.sort((a, b) => a.timestamp - b.timestamp);
```

### Rules

- If the code is clear, don't comment it
- Comment the "why" when it's not obvious
- Comment workarounds with links to issues/docs
- Delete commented-out code; that's what git is for

More from EpicenterHQ/epicenter

SkillDescription
agent-goalWrite `/goal` prompts for long-running agent work in Codex or Claude Code. Use for slash goal, agent goal, durable objective, autonomous coding run.
approachability-auditReview code as a new TypeScript developer. Use when code feels indirect, clever, hard to follow, or needs a pass on abstractions, names, first-read clarity.
arktypeArktype: runtime validation, discriminated unions with .merge()/.or(), spread keys. Use when mentioning arktype, type(), union types, command/event schemas.
attach-primitiveContract and invariants for `attach*` composition primitives in `packages/workspace` (side-effectful building blocks like attachIndexedDb, attachSqlite, attachBroadcastChannel, attachEncryption, attachTable, openCollaboration), and when to use `create*` (pure construction) instead. Use when writing or reviewing an `attach*` or `create*` function, naming a new workspace primitive, composing inside a workspace builder, or deciding whether a primitive registers listeners at call time.
authEpicenter auth packages: `@epicenter/auth`, `@epicenter/auth-svelte`, OAuth sessions, identity state, auth-owned fetch/WebSocket, and workspace lifecycle binding. Use when editing Epicenter auth clients, session state, hosted sign-in, or auth/workspace integration.
autumnAutumn billing in Epicenter: `autumn.config.ts`, `autumn-js` credit checks, `atmn` CLI, plan gates, and metered AI usage. Use when changing billing, pricing, credits, plan access, refunds, or usage events.
better-auth-best-practicesBetter Auth server/client setup: `auth.ts`, generated schema, DB adapters, sessions, cookies, env vars, and plugins. Use when mentioning Better Auth, betterauth, auth handlers, OAuth, email/password, or session configuration.
better-auth-security-best-practicesBetter Auth security hardening: rate limits, secrets, CSRF, trusted origins, cookies, sessions, OAuth tokens, and audit logging. Use when reviewing auth security, brute-force protection, token handling, or deployment safety.
change-proposalPresent proposed code changes visually before implementing. Use when: "show me options", "compare approaches", "what should we do", or when changes need before/after comparison.
claude-code-consultUse this skill when the user asks to consult Claude, ask Claude Code, get another model's take, run a taste check, find cleaner options, or prepare a Claude prompt. Create a bounded second-opinion prompt or run a read-only Claude Code consult, then verify Claude's claims against local files.