> ## Documentation Index
> Fetch the complete documentation index at: https://docs.allocait.app/llms.txt
> Use this file to discover all available pages before exploring further.

# Rules text format

> The keys, defaults and class names rules text accepts.

This page is the format reference for [rules text](https://docs.allocait.app/concepts/rules-text.md). The [full spec](https://allocait.app/rules/spec.md) is the text agents read.

## Format rules

* The file starts with a `---` line, YAML, then another `---` line. Nothing goes before the first `---`.
* Indent with spaces, never tabs. A tab is read as an error, not silently fixed.
* Each class needs a `min`, a `max`, or both, its allocation band (see [Defaults](#defaults)). A class may instead have only a `position_size` or `short_position_size`: it then has no band, its total isn't checked, and each holding is. A class with only a `target` isn't valid, and a `target` needs a `min` or `max`.
* `target`, when given, must sit between `min` and `max`.
* `min` must be less than `max`. The one exception is a `max` of zero, which means none of the class.
* A class you hold nothing in counts as 0%. A `min` above 0 on such a class is out of range until the class reaches it.
* Class names can't repeat, and an unknown key in a rule is an error, so a typo doesn't pass silently.
* `position_size` is optional: the size range one holding in that class is checked against, as a percent of the whole portfolio. `max` is required; leave `min` out for a cap with no floor, for example `{ max: 5 }` means no single holding over 5%.
* `short_position_size` is optional and has the same shape and rules, for a short holding in that class. It's the size range one short is checked against, as a percent of the whole portfolio, counted without the minus sign. A short in a class with no `short_position_size` isn't checked. Leave the key out of a file you import and the class's short size range is cleared, as with `position_size`.
* Percent values can be a plain number or a string like `"53%"`.
* Allocait ignores everything below the second `---` line, so use it for notes, goals, or a review date. A top-level key other than `version`, `name` and `classes` is ignored with a warning. Inputs, monitors and playbooks belong in a [setup file](https://docs.allocait.app/concepts/setup-file.md).

## Defaults

An omitted edge takes these values. They apply to rules text only: the app, `save_class_rule` and `position_rules_apply` refuse a size range with one edge missing.

| You leave out | Allocait uses |
| - | - |
| A class's `min` (with `max` given) | 0 |
| A class's `max` (with `min` given) | 100 |
| `position_size.min` | 0, a cap with no floor |
| `short_position_size.min` | 0, a cap with no floor |
| `position_size` or `short_position_size` entirely | None. The class's holdings (or shorts) are not size-judged, and an import clears any range the class had. |
| `target` | None. A rebalance aims at the midpoint of the band. |
| `name` | None. The file still imports. |

Nothing else defaults to a number. Allocait never picks a range for you.

## Keys

| Key | Required | Meaning |
| - | - | - |
| `version` | No | Always `1`. Missing is read as `1`; any other value is an error. |
| `name` | No | A label for the scenario. Doesn't rename anything on import. |
| `classes` | Yes | At least one entry. Each key is an asset class name; each value is a rule. |

Each rule under `classes` can hold `min`, `max`, `target`, `position_size`, and `short_position_size`, as described above.

## Class names

Use these names when they fit: Cash, Equities, Fixed Income, Currencies, Crypto, Commodities, Options. Anything else becomes a new custom class.

A class name resolves in this order:

1. Your own class with that name.
2. The system class with that name.
3. An alias: Stocks, Equity, ETFs or Funds resolve to Equities, Bonds to Fixed Income, and Forex or FX to Currencies. ETFs and Funds are not asset classes in Allocait, which files each fund under what it holds.

A name that matches none of these becomes its own new custom class.

## For developers

Allocait's agent-facing surface for rules text:

* REST API: `GET`/`POST /scenarios/:id/rules`, `GET /rules/restore-points`, `POST /rules/restore-points/:id/restore`, `GET /rules/spec`.
* MCP: tools `get_rules` (the rules, the rules text and the latest restore points), `preview_rules` (dry run, never writes), `apply_rules` (writes, returns a restore point id), `save_class_rule` (one class, returns a restore point id), `restore_rules`; resources `allocait://rules/spec`, `allocait://scenarios/{scenario_id}/rules`, `allocait://rules/restore-points`; a prompt, `draft_rules`.
* `POST /scenarios/:id/rules` takes a body of `{ rules_text, dry_run? }`. A dry run needs read access and writes nothing; otherwise the call needs write access and returns a `restore_point_id`. The text can be at most 100 KiB and describe at most 500 classes. A parse error returns `400` with the issues.
* `POST /scenarios/:id/position-rules` sets one class and keeps the other rules.

See the [API introduction](https://docs.allocait.app/api/introduction.md) for full request and response shapes.

## Related

* [Rules text](https://docs.allocait.app/concepts/rules-text.md) shows an example and how an import works.
* [Write your rules](https://docs.allocait.app/guides/write-your-rules.md) walks through writing and importing rules text.
* [Allocation bands](https://docs.allocait.app/concepts/allocation-bands.md) and [Size ranges](https://docs.allocait.app/concepts/position-sizes.md) explain how each rule is checked.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.