ROME Framework

Processing user requirements into a set of formal designs with AORDL

Overview

This paper explains how ROME turns a sponsor's raw input into finished requirements, and the mechanism by which it does so. It walks through one small example from start to finish to show that mechanism in practice. It is not technical documentation — the aim is to give the reader a working appreciation of how ROME actually performs, not a reference to its internals.

The challenge

ROME encompasses three separate phases to produce a set of formal, computer-legible requirements from whatever the sponsor hands it — documents of varying formats, varying levels of completion, sometimes contradictory, sometimes missing critical detail, sometimes written against different standards entirely.

PhaseNameWhat happens
0.5 Intake The first phase grades what has arrived. Surveyor reads every input, sorts it by type (document, existing code, a running app, an idea, a formal spec), and scores each one for completeness, consistency and how current it is. Where a document carries a reliability marker, that marker is read and honoured; where it doesn't, Surveyor assesses it. If the material is thin, ROME does not guess at what's missing — it raises the gap as a question back to the sponsor. Only when the material clears that bar does the phase resolve into a single structured record ready to hand forward.
1 Requirements The second phase takes that graded material and forces it into one common shape. Every distinct piece of intent, however it arrived, becomes an AORDL requirement — a fixed thirteen-field structure that leaves no room for the ambiguity or informality of the source documents. Anti-patterns are caught here, and any requirement that reads as ambiguous is flagged for resolution rather than carried forward unresolved.
2 Analysis The third phase breaks each formal requirement down into Features, User Stories and Acceptance Criteria, and traces every one of them across eight dimensions back to its origin. By the end of this phase, what began as a folder of uneven source material has become a fully decomposed, traceable set of requirements a formal software architecture can be built from.

The problem this solves

The person who wants the software is called the sponsor. The sponsor's description is usually a product requirements document (PRD) or business requirements document (BRD). It is prose: sentences written for a human reader, who fills gaps from experience.

ROME builds software with several AI agents, each a separate instance of Claude Code with its own narrow job. One agent writes requirements, another designs, others write code. None of them remembers what the previous one was thinking. Each works only from the files the previous one left behind.

That arrangement exposes a weakness in prose. When an agent reads "a bike that is non-compliant cannot be returned to service", it must decide what "non-compliant" means. The next agent decides again, perhaps slightly differently. Across five phases the small differences add up, and the finished code can do something the sponsor never asked for.

ROME's answer is to rewrite the sponsor's prose, once and early, into a strict structured form called AORDL. After that, every agent reads the same fields and nobody reinterprets a sentence. A program checks each requirement before anyone builds on it.

This paper shows that rewriting on a small example, then shows how the structured requirements drive the design that follows.

The raw input

The example is a fleet manager for a small bike-tour company, called FOB Fleet in the repository. The sponsor's brief is a single file, _user_input/raw-requirements/fleet-slice.md, cut from a larger PRD. Here it is in full, with its heading and three journey reference codes removed:

Scope: a self-contained Fleet & Equipment management service for a small
bike-tour operator. No external services. Three capabilities:

1. Onboard a bike to the fleet: register a bike with a unique asset id,
   make/model, purchase date. A new bike starts in service.
2. Flagged-bike workflow: a bike moves InService -> OutOfService (flagged)
   -> Maintenance -> back InService. Only these transitions are allowed.
3. Track compliance dates: each bike has an insurance-expiry and a
   service-due date; the system reports which bikes are "renewal due"
   (date within 30 days or past). A bike that is non-compliant cannot be
   returned to service.

Operator: FleetManager. Tech: runnable Node/TypeScript service + a data
store + a simple dashboard read. Mobile not required (operator desktop).

The brief is clear by everyday standards, yet it leaves real questions open. Is the purchase date mandatory? Can a bike in maintenance go straight back to out of service? Is the 30-day window fixed, or can the operator change it? It says "non-compliant" without ever defining it. It also mixes in technology choices (Node, TypeScript, a data store) that belong to a later phase.

A human developer would ask about these points over coffee or guess. ROME's first phase exists to make each one explicit and to record the answer.

Step one: requirements

Phase P1 turns the brief into AORDL requirements, one file per requirement. The agent that does it is called Talib. ROME gives each agent a short name so that people and other agents can refer to it.

What an AORDL requirement is

An AORDL requirement describes one person, in one named role, doing one thing. It is written in YAML (a plain-text format of labelled fields) and must contain thirteen fields in a fixed order. The fields answer the questions a careful analyst would ask:

  • Actor: who acts. It must be a specific role, such as FleetManager. Generic words such as User or Admin are rejected.
  • Intent: what they do, as one approved verb and one business object, such as create bike.
  • Preconditions, Conditions, Postconditions: what must be true before, during and after.
  • Outcomes: what the actor can see afterwards.
  • Invariants: rules that always hold, whatever happens.
  • NonFunctional: speed, security and similar qualities, stated as measurable targets.
  • Errors: each way the action can fail, with the message the person sees.
  • ScopeBoundary: what is included and, as important, what is not.
  • OpenQuestions: anything the brief left unclear, with the answer and who gave it.
  • ID and CopilotMode: an identifier and the strictness level for checking.

The form also bans certain words. A requirement may not mention buttons, screens or forms, because the user interface is decided later, at design. It may not mention databases, endpoints or SQL, because the implementation is decided later still. A requirement states business intent and nothing else.

How the files are checked

Talib writes the files into ARTIFACTS/_requirements/, named REQ-001.yaml upward. A program, validate-aordl.js, then checks each one. It confirms that all thirteen fields are present, that the actor is specific, that the verb is on the approved list, and that no banned words appear. No AI model is involved in this check. It gives the same answer every time.

The unclear points from the brief are handled through OpenQuestions. Talib asks the sponsor, records the answer in the file, and marks the question RESOLVED. A requirement with an unresolved question cannot pass.

The gate

Each ROME phase ends at a Quality Gate. P1 ends at GATE-P1. Two separate things must happen before the project moves on. A reviewing agent called Sarah must record an approval. A program called the guard must confirm that the required checks have run and passed. For P1 the central check is that every requirement passes the checker in its strictest mode, called STRICT. The guard also confirms that each requirement is recorded for tracing and that any business workflows have been confirmed by the sponsor. Talib cannot approve its own work, and Sarah's approval alone is not enough.

The example: three requirements

Talib turned the three capabilities in the brief into three requirements:

  • REQ-001: FleetManager, create bike
  • REQ-002: FleetManager, update bike-state
  • REQ-003: FleetManager, view fleet-compliance

Here is REQ-002, the flagged-bike workflow, exactly as it stands in the repository:

ID: REQ-002
Actor: FleetManager
Intent: update bike-state
Preconditions:
  - FleetManager authenticated
  - Bike exists in the fleet
Conditions:
  - Requested transition is permitted from the current state
Postconditions:
  - Bike recorded in the new state
Outcomes:
  - Bike state reflects the requested change in the fleet list
Invariants:
  - A bike moves only in-service to out-of-service, out-of-service to maintenance, or maintenance to in-service
  - A non-compliant bike cannot return to in-service
NonFunctional:
  Performance:
    - State change completes within two seconds
  Security:
    - Only an authenticated FleetManager may change a bike state
Errors:
  - error: If the requested transition is not permitted from the current state
    message: That state change is not allowed
  - error: If returning a non-compliant bike to in-service
    message: Bike cannot return to service while non-compliant
ScopeBoundary:
  InScope:
    - The flagged-bike lifecycle transitions
  OutOfScope:
    - Maintenance cost tracking
OpenQuestions:
  - question: Can maintenance go straight to out-of-service?
    status: RESOLVED
    resolution: No, only the defined transitions
CopilotMode: STRICT

Set the requirement beside the brief and the changes show.

The permitted moves became an invariant. The brief drew them as an arrow diagram. The requirement states them as a rule that always holds. A later agent does not have to interpret the diagram.

Failures became explicit. The brief stated the two rules but not what happens when someone breaks them. The requirement names each failure and gives the exact message the fleet manager sees.

An open question was asked and answered. The brief did not say whether a bike in maintenance could go straight back to out of service. The requirement records the question and the answer: no.

Scope was fenced. Maintenance cost tracking is ruled out in writing. Nobody can later assume it was included.

Technology dropped out. Node, TypeScript and the data store appear nowhere in the three requirements. They are not lost. They wait for the design phases, where such choices belong.

The other two requirements do the same work. REQ-001 records that the purchase date is optional, a question the brief left open. REQ-003 defines "renewal-due" once, as an invariant, and fixes the 30-day window for this release. All three files pass the checker in STRICT mode. The check was re-run against the repository on 24 September 2026.

Step two: analysis

Phase P2 reads the requirements and works out what the system must hold and how its parts relate. Talib does this work too, but under a different set of instructions. P2 still makes no technology choices.

In the FOB Fleet run, P2 produced one file, ARTIFACTS/_analysis/entities.md. It does three things.

It names the entities. An entity is a thing the system keeps records about. Here there is one, the Bike, with its fields gathered from all three requirements:

### Bike (REQ-001, REQ-002, REQ-003)
- assetId (unique), make, model, purchaseDate?
- state: InService | OutOfService | Maintenance
- insuranceExpiry (date?), serviceDue (date?)

The question mark marks an optional field. The optional purchase date comes straight from the answer recorded in REQ-001.

It turns rules into precise definitions. The analysis writes the state machine (the permitted moves between states) as one line, taken from the invariant in REQ-002. It also settles a gap that no single requirement closed. REQ-003 defined "renewal-due" but not "non-compliant". The analysis defines non-compliant as either date being in the past. Each design decision after this point builds on that definition.

It records the trail. A final section links each requirement to what it produced. REQ-001 leads to creating a bike, REQ-002 to the state machine, and REQ-003 to the compliance report.

The framework's instructions for P2 describe a larger set of files than this run produced. They include a requirements matrix across eight dimensions (functional, data, security, performance and others), user stories and acceptance criteria. This slice was deliberately small, and a single entity file was enough to design from. The larger set has not yet been shown in a published run, so this paper does not describe it as though it had.

Step three: design

Phase P3 is where technology choices are finally made. The design agent is called PMA. A second agent, Clara, checks the design independently. Clara can report problems but cannot approve the phase; only Sarah can. In the FOB Fleet run, P3 produced five files under ARTIFACTS/_design/.

architecture.md: the parts and how they connect

The architecture splits the system into three components (separately built parts), stacked in layers:

  • schema: the shape of the data and the rules for storing it.
  • service: the business logic, with one function per requirement: onboardBike for REQ-001, transitionBike for REQ-002 and complianceReport for REQ-003.
  • ui: a single read-only dashboard page that lists the bikes, their states and a warning badge for renewal-due or non-compliant bikes.

The requirements shape the design directly. The invariant in REQ-002 becomes a four-row table of allowed moves. The two error messages from REQ-002 appear word for word, as the text the service returns. "Renewal-due", defined once in REQ-003, becomes a precise date rule: a date is due if it falls on or before today plus 30 days. Each component section ends with the requirement IDs it serves.

data-dictionary.md: every stored field

The data dictionary lists each field of the Bike record with its type, whether it is required, its constraints, and the requirement it came from. For example, assetId is a required text field, unique across the fleet, traced to REQ-001. It also lists two computed values, renewalDue and nonCompliant, which are worked out when needed rather than stored.

component-graph.json: the build order

This file is for machines, not people. It records the three components and which depends on which:

{"nodes":[
  {"id":"schema","type":"shared-lib"},
  {"id":"service","type":"service","dependsOn":["schema"]},
  {"id":"ui","type":"ui","dependsOn":["service"]}]}

Later, in phase P5, ROME reads this graph to decide what to build first and what can be built in parallel.

contracts/fleet-api.json: the agreement between parts

The contract names which component provides functions to which, and which functions they are. Here the service provides onboardBike, transitionBike and complianceReport, and the ui consumes them. Once code exists, a program compares it with the contract and blocks the final gate if the two have drifted apart.

validation-report.md: the independent check

Clara read the four design files against the three requirements and the analysis, and reported under six headings. Every requirement is covered. The state machine and compliance rule match the requirements exactly. The data dictionary is consistent with the analysis. The contract has one function per requirement. Nothing out of scope has crept in. That last check matters: the requirements ruled out equipment, maintenance costs and renewal reminders, and Clara confirmed that none of them appear in the design. The verdict was PASS.

Only after that did Sarah approve GATE-P3. The project's state file records the approval at 09:02 UTC on 19 June 2026, with the note "design complete, PMA+Clara, contract defined".

Keeping the trail

The identifier given at P1 travels through every later file unchanged. Follow REQ-002 and it appears in five places:

  1. REQ-002.yaml, where the rule about permitted moves is written.
  2. entities.md, where the rule becomes a one-line state machine.
  3. architecture.md, where it becomes a table of allowed moves and the transitionBike function.
  4. data-dictionary.md, where the state field is traced to it.
  5. The code itself, in the comment // Allowed state transitions (REQ-002). in SOURCE/service/index.js.

That trail runs both ways. From a requirement, anyone can find every design decision and line of code it caused. From a line of code, anyone can find the requirement that justifies it. When the sponsor later asks for a change, ROME uses the same trail to work out which files the change will touch.

The trail is also checked, not merely kept. The project's state file, ARTIFACTS/_orchestration/state.json, records each link from requirement to file as it is made. Since version 3.5.0 of the framework, code links are no longer written down by the agent that wrote the code. A program scans the source files for requirement IDs in comments and builds the links itself, so an agent cannot claim a link that is not there.

The companion article, AORDL: Why, Where, How and What, covers the format's history, its full rule set, and why ROME chose it over EARS (Easy Approach to Requirements Syntax), a widely used alternative. [ Not yet published on this site ]


Sources

All paths are in the ROME framework repository.

The example, under testapps/fob-fleet/

  • _user_input/raw-requirements/fleet-slice.md: the sponsor's brief
  • ARTIFACTS/_requirements/REQ-001.yaml, REQ-002.yaml, REQ-003.yaml: the requirements
  • ARTIFACTS/_analysis/entities.md: the analysis
  • ARTIFACTS/_design/architecture.md, data-dictionary.md, component-graph.json, contracts/fleet-api.json, validation-report.md: the design
  • ARTIFACTS/_orchestration/state.json: the gate approvals and requirement links
  • SOURCE/service/index.js: the code comment quoted

The framework

  • ROME/rome-core/docs/standards/aordl-standard.md: the AORDL standard
  • ROME/rome-core/lib/aordl-parser/validate-aordl.js and ROME/rome-core/lib/registry/validate-aordl.yaml: the checker and its rules
  • ROME/agents/talib/modes/P1-aordl.md and P2-analysis.md: Talib's instructions for each phase
  • ROME/rome-core/docs/standards/gate-decision-standard.md: the Quality Gates and what each requires
  • ROME_framework_maintenance/reviews/ROME-PLAN-035-E2E-result.md: the record of the FOB Fleet run

About this document

FieldValue
Document IDROME-ART-002
AuthorWilliam Paulton
Converted25 September 2026

← Back to ROME Framework