Defining a stylesheet
Stylesheets are set in themodel_stylesheet graph attribute:
example.fabro
- spec gets Haiku (matches
*) - implement and test get Sonnet with high reasoning (match
.coding) - review gets Gemini Pro (matches
#review)
Selectors
Each rule starts with a selector that determines which nodes it applies to:| Selector | Syntax | Matches | Specificity |
|---|---|---|---|
| Universal | * | All nodes | 0 |
| Shape | box, tab, hexagon, etc. | Nodes with that Graphviz shape | 1 |
| Class | .classname | Nodes with class="classname" | 2 |
| ID | #nodeid | The node with that specific ID | 3 |
Assigning classes
Set theclass attribute on a node to target it with class selectors. Multiple classes are space-separated:
.coding and .critical rules.
Properties
Stylesheets support four properties:| Property | Description | Example |
|---|---|---|
model | Model ID or alias | claude-sonnet-4-5, opus, gemini-pro |
provider | Provider name (optional — auto-inferred from the model catalog when omitted) | anthropic, openai, gemini |
reasoning_effort | Reasoning effort level | low, medium, high |
backend | Agent execution backend — api (default) runs Fabro’s own tool loop, cli delegates to an external CLI tool. See Backends. | cli, api |
Specificity and cascading
When multiple rules match the same node, the rule with the highest specificity wins. This follows the same principle as CSS:id="review" and class="coding" gets gpt-5.2 because #id (specificity 3) beats .class (specificity 2).
If two rules have the same specificity, the last one in the stylesheet wins.
Explicit attributes override stylesheets
A model set directly on a node attribute always takes precedence over stylesheets, regardless of specificity:.coding sets model: claude-sonnet-4-5, this node uses Opus because the explicit attribute wins.
Syntax reference
The stylesheet syntax is a simplified subset of CSS:- Selectors:
*,shape,.class,#id - Properties and values are separated by
: - Declarations are separated by
; - Whitespace is flexible — newlines and indentation are ignored
- CSS comments (
/* ... */) are not supported
Full example
- Defaults everything to Haiku with low reasoning
- Overrides all agent nodes (
boxshape) to high reasoning - Keeps prompt nodes (
tabshape) at low reasoning - Routes
.codingnodes to Sonnet - Routes
.reviewnodes to Gemini for independent critique - Routes the
final_checknode to Opus for maximum quality