Skip to content
Riot Docs

Search is only available in production builds. Try building and previewing the site to test it out locally.

Install Riot GitHub

RFD0000 - Template

  • Feature Name: <fill_me_in_with_a_unique_ident>
  • Start Date: <YYYY-MM-DD>
  • Status: <presented|accepted|rejected|implemented>
  • RFD PR: leostera/riot#0000
  • Riot Issue: leostera/riot#0000

Write this so someone can decide whether to read the rest of the RFD.

Answer these questions in one short paragraph plus 3-5 bullets:

  • What is being proposed?
  • What kind of thing is it? For example: a new package, a runtime change, a protocol contract, a workflow change, or a snapshot of the current system.
  • What are the 3-5 defining properties or constraints?
  • What is explicitly out of scope?

This section should read like an abstract, not like an outline of the document.

Good summaries:

  • lead with the proposal in one sentence
  • group by big ideas and externally meaningful properties
  • say what kind of thing this is before talking about how it works
  • compress many low-level constraints into 3-5 memorable traits
  • leave detailed proof, invariants, and implementation mechanics for later

Avoid writing the summary as:

  • a checklist of every architectural rule
  • a mini changelog of all sections that follow
  • a dense mechanism-first paragraph about internal data structures

Prefer a value-minded summary that explains why this matters before it dives into mechanism.

For snapshot RFDs, keep the same shape but describe the current system instead of a proposed change.

Any changes to Riot should focus on solving a real problem for Riot users or contributors.

This section should explain that problem in detail, including the current baseline and why that baseline is not good enough.

The most useful way to write Motivation is usually:

  1. state the current situation
  2. name the concrete costs, frictions, or failure modes Riot is paying today
  3. explain why those costs are structural rather than incidental
  4. show how the proposed change removes or reduces them

In other words, Motivation should be problem-first, not architecture-first.

Good motivation sections usually argue from operational pain:

  • what is hard today
  • what has to be reimplemented or worked around today
  • what kinds of output, APIs, or workflows Riot cannot get from the current approach
  • what kinds of maintenance or extension costs the current system imposes

Each point should ideally have the shape:

  • today, Riot pays cost X
  • this proposal changes the system so Riot gets Y instead

Avoid turning Motivation into:

  • an early reference section
  • an architecture preview about data structures or internal layering
  • a description of what Riot happens to have available technically, unless that fact is itself part of the problem statement

It should also contain several specific use cases where this change can help, and explain how it helps. This can then be used to guide the design of the feature.

This section is one of the most important sections of any RFD, and can be lengthy.

For snapshot RFDs, the only difference is that you don’t need to specify the proposed changes, just stating what costs we are paying today.

Explain the proposal as if it was already included in Riot and you were teaching it to another Riot contributor.

The best guide-level sections usually start from a realistic Riot workflow and show how it feels before they start naming internal concepts.

For example:

  • “suppose we have this package with these files and we want to build it”
  • “today Riot has to do this awkward sequence of steps”
  • “with this proposal, the flow becomes this instead”

The spirit of this section is:

  • make the pain from Motivation visible in one or two realistic workflows
  • show the caller-facing or contributor-facing flow before explaining internals
  • teach the proposal through consequences first, architecture second

This does not need to be exact or exhaustive. It is a guide, not a reference. Rough flows, illustrative pseudo-code, and simplified examples are all fine if they teach the right mental model.

That means this section should usually do four things, roughly in this order:

  1. walk through a concrete example or workflow
  2. show the current friction or cost in that workflow
  3. show how the proposed design changes the experience for the caller or contributor
  4. only then introduce the named concepts and internal mental model that make the example work

For infrastructure and implementation RFDs, a very strong pattern is:

  1. “today, to do X, Riot must do A, B, C”
  2. “with this proposal, Riot instead does D, E, F”
  3. “here is the resulting API / command / workflow shape”
  4. “here are the key consequences”

This section should make it obvious that the proposal changes the shape of the work, not just the internal implementation.

That generally means:

  • Introducing new named concepts.
  • Explaining the feature largely in terms of examples.
  • Explaining how Riot contributors should think about the feature, and how it should impact the way they build, run, and maintain Riot systems.
  • If applicable, provide sample error messages, deprecation warnings, API examples, CLI examples, or migration guidance.
  • If applicable, describe the differences between teaching this to existing Riot contributors and new contributors.
  • Discuss how this impacts the ability to read, understand, and maintain Riot code. Code is read and modified far more often than written; will the proposed feature make code easier to maintain?

Avoid starting Guide-level explanation with:

  • a layering diagram
  • a list of internal data structures
  • a tour of implementation modules
  • an architectural rule that has not yet been motivated by an example
  • a walkthrough of semantic layers before the reader understands what practical problem those layers solve

For implementation-oriented RFDs (for runtime internals, build execution, syntax tooling, packaging, and similar areas), this section should focus on how Riot contributors should think about the change, and give examples of its concrete impact. For policy RFDs, this section should provide an example-driven introduction to the policy and explain its impact in concrete terms.

If the proposal has more than one important consumer, prefer showing at least two examples from different angles. For example:

  • a build or batch workflow
  • an editor, runtime, or library-consumer workflow

That is often the fastest way to show that the proposal is one shared system rather than a narrow special-case integration.

For snapshot RFDs, explain the current system as if you were onboarding a contributor to it today.

flowchart TD
A[Trigger or Input] --> B[Runtime Decision Point]
B --> C[Primary Action]
C --> D[Stored/Audited Outcome]
D --> E[User/Operator Visible Effect]

This is the technical portion of the RFD. Explain the design in sufficient detail that:

  • Its interaction with other Riot subsystems is clear.
  • It is reasonably clear how the feature would be implemented.
  • Corner cases are dissected by example.

The section should return to the examples given in the previous section, and explain more fully how the detailed proposal makes those examples work.

Why should we not do this?

  • Why is this design the best in the space of possible designs?
  • What other designs have been considered and what is the rationale for not choosing them?
  • What is the impact of not doing this?
  • Could this be done in a simpler Riot module, library helper, or tool-level integration instead?

Discuss prior art, both the good and the bad, in relation to this proposal. A few examples of what this can include are:

  • Similar features in other OCaml tools, build systems, package managers, editors, or runtimes.
  • Prior approaches used inside Riot itself.
  • Practices from adjacent systems.
  • Papers or posts that discuss related approaches.

This section is intended to encourage you as an author to think about lessons from other systems and provide readers of your RFD with fuller context. If there is no prior art, that is fine.

Note that precedent in another system can be motivating, but does not on its own justify an RFD. Riot may intentionally diverge from common patterns when it better fits Riot’s architecture and goals.

  • What parts of the design do you expect to resolve through the RFD process before this gets merged?
  • What parts of the design do you expect to resolve through implementation before rollout?
  • What related issues are out of scope for this RFD that could be addressed in the future independently of this proposal?

Think about what the natural extension and evolution of your proposal would be and how it would affect Riot holistically over time. Use this section to consider future interactions with runtime, build, syntax, packaging, API, and operations.

This is also a good place to dump related ideas if they are out of scope for the RFD you are writing. If you have tried and cannot think of future possibilities, you may simply state that.

Note that having something written in this section is not by itself a reason to accept the current or a future RFD.