agentleFS
tamesystemstamesystems/intent-engineering-skills/skills/design-module/SKILL.md

design-module

Skill0 starsChanged 39 days agoMITView on GitHub

Design or reshape a module around an independently changing decision or capability, with a small supported surface and substantial hidden complexity. Use when ownership is clear but the module boundary, public API, internal responsibilities, or seams are not.

The file

We split this skill into the rules it gives an agent

4 rules. About 0 are common, 3 are distinctive, and 1 is very specific to this project.

  • ≈0

    Common · estimate

    Many files like this have a rule of this kind.

  • ≈3

    Distinctive · estimate

    This author's own choices. Worth a look.

  • 1

    Very specific

    Tied to their project's names, files or tools. Probably skip.

  • Common
  • Distinctive
  • Very specific
  1. Distinctive:

    Create a deep change boundary: substantial coherent behavior behind a small supported surface.

    line 8
  2. Distinctive:

    Design the smallest useful public surface: Prefer operations in domain language that express what callers need, not wrappers exposing …

    line 14
  3. Very specific:

    Protect locality: Keep behavior that changes together together.

    line 17
  4. Distinctive:

    Apply the deletion/change test: If the module disappeared or its hidden implementation changed, would complexity remain contained behind …

    line 20

≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.

Keep what fits and drop the rest. Your version, ready for your agents.
Files
SKILL.md

Design Module

Create a deep change boundary: substantial coherent behavior behind a small supported surface. A module is not a folder; it is a controlled dependency surface around something that should be able to change independently.

Work

  1. Name the decision/capability being hidden. Explain what should be independently changeable and why callers should not need to know its implementation decisions.
  2. Recover real callers and changes. Inspect current call sites, tests, adjacent modules, relevant history, and the intended change. Design for demonstrated needs; do not invent generic interfaces for hypothetical consumers.
  3. Design the smallest useful public surface. Prefer operations in domain language that express what callers need, not wrappers exposing implementation steps. Keep public types and errors explicit enough to preserve evidence.
  4. Put complexity behind the surface. Identify policies, workflows, persistence coordination, provider details, internal state, and helpers that the module owns and should hide.
  5. Choose seams only where they buy something. Introduce an adapter/interface when there is a real environmental boundary, test seam, volatility, or multiple implementations. Do not wrap every library or create an interface merely because one could exist.
  6. Protect locality. Keep behavior that changes together together. Avoid global horizontal layers that scatter one capability across controllers/services/repositories unless the system's dominant unit of change genuinely follows that pipeline.
  7. Define visibility and direction. State which entry points are public, which internals are private, what the module may depend on, and who may depend on it. Prefer language/package/build visibility over naming conventions when available.
  8. Test through the supported surface. Behavioral tests should primarily exercise the interface real callers use. Internal tests are allowed when they prove meaningful internal invariants, but testability alone is not a reason to leak helpers.
  9. Apply the deletion/change test. If the module disappeared or its hidden implementation changed, would complexity remain contained behind its surface? If deleting the abstraction merely moves equivalent ceremony to callers, it may be shallow.
  10. Hand enforcement to ratchets. Once the boundary is justified, use pave-path to make correct use easy and harden-boundary/ratchet to make invalid access difficult or impossible.

Evaluate the reader's burden on a representative operation and, when the capability is stateful, a representative transition. Compare the proposed design with the current or simplest credible alternative:

  • Tracing burden: which calls, layers, and files must a reader follow to understand the behavior? Each hop should hide a meaningful decision or enforce a real boundary. Collapse forwarding-only indirection when it adds no such value; preserve useful security, runtime, and ownership boundaries. File count alone is not the criterion.
  • State burden: which independent facts, flags, mirrored values, ordering rules, and lifecycle relationships must the reader hold simultaneously? Give coordinated transitions a clear owner, derive values when possible, and represent meaningful states with their required data. Splitting coupled state across helpers or hooks does not reduce the burden if callers still coordinate it.

Judge the design by what a caller or maintainer no longer needs to know. A justified boundary may add a hop or retain necessary complexity while reducing leaked knowledge, risk, or change scope. Avoid replacing a straightforward flow with a generic state-machine framework or another abstraction unless it demonstrably improves the overall tradeoff.

Return

  • Module / capability
  • Decision hidden
  • Public surface
  • Owned internals
  • Reader burden — representative trace and transition; knowledge eliminated and necessary complexity retained
  • Dependencies / seams
  • Visibility and dependency direction
  • Testing surface
  • Enforcement opportunities

Failure signals

Watch for interface-per-class ceremony, one-line pass-through modules, giant barrels, speculative adapters, premature micro-packages, generic shared ownership, leaking persistence/provider types through the public API, and maximizing boundaries instead of the value of boundaries.

Done when

The module has a small caller-oriented surface, coherent hidden responsibilities, justified seams, explicit visibility/direction, and a credible story for keeping likely future changes local. A representative trace and, when relevant, state transition show that the boundary improves the overall reader and change burden rather than merely redistributing code.

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.