Theme 06 · Agent-Aware
Standards written for coding agents
Explanation
Standards written for coding agents
Plain Human Explanation
Standards written for coding agents turn team preferences into instructions an agent can actually follow. “Keep it simple” is a value. “Do not add a shared abstraction for one route; edit the feature module only” is an operating rule.
For users, this lowers the chance that an automated change creates broad churn, skips verification, or applies the right idea in the wrong part of the product.
Technical Explanation
Agent-facing standards should include scope, paths, commands, constraints, and examples of acceptable changes. They should also say what not to touch when that matters.
The best standards are local and concrete. A repo-level note can set defaults, but a feature module should still document its own invariants, test command, data boundaries, and risky files.
Why It Matters
- User impact: agent changes are less likely to alter unrelated behavior.
- Product behavior: product-specific rules survive handoffs between humans and agents.
- Risk: vague standards sound good but do not constrain the next edit.
- Decision point: write agent-facing standards when repeated agent work touches important behavior, shared code, data migrations, or release steps.
The Core Move
Replace values-only guidance with concrete instructions: where to work, what to preserve, how to verify, and when to stop.
Small Example
Standards written for coding agents: Small Example
Bad TypeScript Example
export const agentStandards = [
"write clean code",
"avoid overengineering",
"be careful with billing",
];
Good TypeScript Example
type AgentStandard = {
area: "billing";
allowedPaths: string[];
mustPreserve: string[];
verificationCommands: string[];
};
export const billingAgentStandard: AgentStandard = {
area: "billing",
allowedPaths: ["src/billing/**", "tests/billing/**"],
mustPreserve: [
"Stripe remains the source of truth",
"Subscription status changes return typed results",
],
verificationCommands: ["pnpm test tests/billing", "pnpm typecheck"],
};
type AgentStandard = {
area: "billing";
allowedPaths: string[];
mustPreserve: string[];
verificationCommands: string[];
};
export const billingAgentStandard: AgentStandard =
{
area: "billing",
allowedPaths: [
"src/billing/**",
"tests/billing/**",
],
mustPreserve: [
"Stripe remains the source of truth",
"Subscription status changes return typed results",
],
verificationCommands: [
"pnpm test tests/billing",
"pnpm typecheck",
],
};
What Changed
- The bad version states values but gives no usable constraints.
- The good version tells an agent where to work, what product rules to preserve, and which checks to run.
- The standard is specific to billing instead of pretending one sentence can guide every change.
Realistic Example
Standards written for coding agents: Realistic Example
A task brief that says “fix account deletion” is not enough. Account deletion touches access, billing, data retention, support expectations, and tests.
Bad TypeScript Example
type AgentTask = {
prompt: string;
};
export function createDeletionTask(): AgentTask {
return {
prompt: "Fix account deletion. Keep the code good and test it.",
};
}
type AgentTask = {
prompt: string;
};
export function createDeletionTask(): AgentTask {
return {
prompt:
"Fix account deletion. Keep the code good and test it.",
};
}
Good TypeScript Example
type AgentTaskBrief = {
goal: string;
allowedPaths: string[];
productRules: string[];
requiredEvidence: string[];
stopIf: string[];
};
export function createDeletionTaskBrief(): AgentTaskBrief {
return {
goal: "Update account deletion without changing normal subscription cancellation.",
allowedPaths: ["src/account/delete-account.ts", "tests/account/delete-account.test.ts"],
productRules: [
"Delete-account removes access immediately",
"Normal cancellation still ends at the paid-through date",
],
requiredEvidence: [
"Regression test for delete-account access removal",
"Regression test for normal cancellation behavior",
],
stopIf: [
"A billing migration is required",
"The change needs policy copy that is not in scope",
],
};
}
type AgentTaskBrief = {
goal: string;
allowedPaths: string[];
productRules: string[];
requiredEvidence: string[];
stopIf: string[];
};
export function createDeletionTaskBrief(): AgentTaskBrief {
return {
goal: "Update account deletion without changing normal subscription cancellation.",
allowedPaths: [
"src/account/delete-account.ts",
"tests/account/delete-account.test.ts",
],
productRules: [
"Delete-account removes access immediately",
"Normal cancellation still ends at the paid-through date",
],
requiredEvidence: [
"Regression test for delete-account access removal",
"Regression test for normal cancellation behavior",
],
stopIf: [
"A billing migration is required",
"The change needs policy copy that is not in scope",
],
};
}
What Changed
- The bad version leaves the agent to infer scope and product rules.
- The good version separates goal, paths, rules, evidence, and stop conditions.
- The brief protects adjacent behavior by saying what must not change.
System Example
Standards written for coding agents: System Example
At system scale, agent standards should travel with the workflow. They should help an agent make a narrow change, verify it, and avoid unrelated churn.
Larger System-Level Bad TypeScript Example
type AgentRequest = {
title: string;
notes: string;
};
export function buildAgentRequest(title: string): AgentRequest {
return {
title,
notes: "Follow best practices. Update anything needed. Run tests if possible.",
};
}
type AgentRequest = {
title: string;
notes: string;
};
export function buildAgentRequest(
title: string,
): AgentRequest {
return {
title,
notes:
"Follow best practices. Update anything needed. Run tests if possible.",
};
}
Larger System-Level Good TypeScript Example
type ChangeSurface = {
editablePaths: string[];
protectedPaths: string[];
};
type VerificationGate = {
command: string;
required: boolean;
failureMeaning: string;
};
type AgentWorkOrder = {
title: string;
userImpact: string;
changeSurface: ChangeSurface;
codingRules: string[];
verificationGates: VerificationGate[];
};
export function buildInvoiceEmailWorkOrder(): AgentWorkOrder {
return {
title: "Update overdue invoice email copy",
userImpact: "Customers should receive clearer payment recovery instructions without changing billing state.",
changeSurface: {
editablePaths: ["src/billing/emails/overdue-invoice.ts", "tests/billing/overdue-invoice.test.ts"],
protectedPaths: ["src/billing/subscriptions/**", "migrations/**"],
},
codingRules: [
"Do not change subscription status rules",
"Keep email rendering behind the existing billing email interface",
"Add or update the focused email snapshot test",
],
verificationGates: [
{
command: "pnpm test tests/billing/overdue-invoice.test.ts",
required: true,
failureMeaning: "The email contract changed unexpectedly",
},
{
command: "pnpm typecheck",
required: true,
failureMeaning: "The email template no longer matches the billing interface",
},
],
};
}
type ChangeSurface = {
editablePaths: string[];
protectedPaths: string[];
};
type VerificationGate = {
command: string;
required: boolean;
failureMeaning: string;
};
type AgentWorkOrder = {
title: string;
userImpact: string;
changeSurface: ChangeSurface;
codingRules: string[];
verificationGates: VerificationGate[];
};
export function buildInvoiceEmailWorkOrder(): AgentWorkOrder {
return {
title:
"Update overdue invoice email copy",
userImpact:
"Customers should receive clearer payment recovery instructions without changing billing state.",
changeSurface: {
editablePaths: [
"src/billing/emails/overdue-invoice.ts",
"tests/billing/overdue-invoice.test.ts",
],
protectedPaths: [
"src/billing/subscriptions/**",
"migrations/**",
],
},
codingRules: [
"Do not change subscription status rules",
"Keep email rendering behind the existing billing email interface",
"Add or update the focused email snapshot test",
],
verificationGates: [
{
command:
"pnpm test tests/billing/overdue-invoice.test.ts",
required: true,
failureMeaning:
"The email contract changed unexpectedly",
},
{
command: "pnpm typecheck",
required: true,
failureMeaning:
"The email template no longer matches the billing interface",
},
],
};
}
What Changed
- The bad version gives broad permission and weak verification language.
- The good version names the user impact, editable paths, protected paths, coding rules, and gates.
- The work order lets an agent act independently while still staying inside the intended product boundary.
When To Use It
Standards written for coding agents: When To Use It
Use This When
- Agents repeatedly work in a repo, module, or product area.
- The work has important scope limits, protected behavior, or required verification.
- A vague instruction could cause broad refactors, unrelated cleanup, or missed tests.
Avoid This When
- The rule is obvious from a nearby example and does not need separate guidance.
- The standard would duplicate stale process notes nobody maintains.
- The team is still deciding the rule and should not freeze it yet.
Tradeoffs
Agent standards add maintenance cost. Keep them short, concrete, and close to the work. Delete or update standards that no longer match the repo, because stale guidance is worse than no guidance.
Related Concepts
- Discoverability
- Local conventions
- Checklists
Practice Prompt
Standards written for coding agents: Practice Prompt
Beginner Exercise
Find one vague repo rule such as “keep changes small.” Rewrite it as one concrete instruction with a path, constraint, or command.
Intermediate Exercise
Write an agent task brief for a risky feature area. Include goal, allowed paths, protected behavior, required evidence, and stop conditions.
Stretch Exercise
Move one broad repo-level instruction closer to the module it governs. Add a tiny example of an acceptable change and an unacceptable change.
Reflection Question
Would a coding agent know exactly what to edit, what not to edit, and how to prove the change worked?
Suggest an edit
Leave a private editorial note. This creates a GitHub issue for this curriculum page.