<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Concepts on Orchard</title><link>https://orchard.pthm.dev/docs/concepts/</link><description>Recent content in Concepts on Orchard</description><generator>Hugo</generator><language>en-us</language><atom:link href="https://orchard.pthm.dev/docs/concepts/index.xml" rel="self" type="application/rss+xml"/><item><title>Scenarios</title><link>https://orchard.pthm.dev/docs/concepts/scenarios/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://orchard.pthm.dev/docs/concepts/scenarios/</guid><description>&lt;h1 id="scenarios"&gt;Scenarios&lt;a class="anchor" href="#scenarios"&gt;#&lt;/a&gt;&lt;/h1&gt;
&lt;p&gt;A &lt;strong&gt;scenario&lt;/strong&gt; is the top-level entrypoint in Orchard. It is the thing a user runs.
A scenario declares the providers it needs, accepts parameters via variables,
composes components and actions, and exposes outputs.&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" style="background-color:#f7f7f7;-moz-tab-size:2;-o-tab-size:2;tab-size:2;-webkit-text-size-adjust:none;"&gt;&lt;code class="language-hcl" data-lang="hcl"&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;&lt;span style="color:#cf222e"&gt;scenario&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;merchant_with_chargeback&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;required_providers&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; postgres &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; { source &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;builtin/postgres&amp;#34;&lt;/span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;variable&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;dsn&amp;#34;&lt;/span&gt; {}
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;variable&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;merchant_name&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; default &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;Acme Corp&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;provider&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;postgres&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; dsn &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#cf222e"&gt;var&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;dsn&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;component&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;merchant&amp;#34; &amp;#34;base&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; source &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;../components/merchant.hcl&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; inputs &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; { name &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#cf222e"&gt;var&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;merchant_name&lt;/span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;output&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;merchant_id&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; value &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#cf222e"&gt;component&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;merchant&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;base&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;id&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id="what-goes-inside-a-scenario"&gt;What goes inside a scenario&lt;a class="anchor" href="#what-goes-inside-a-scenario"&gt;#&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;A scenario file contains exactly one &lt;code&gt;scenario &amp;quot;&amp;lt;name&amp;gt;&amp;quot; { ... }&lt;/code&gt; block. Inside that
block, you can declare:&lt;/p&gt;</description></item><item><title>Components</title><link>https://orchard.pthm.dev/docs/concepts/components/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://orchard.pthm.dev/docs/concepts/components/</guid><description>&lt;h1 id="components"&gt;Components&lt;a class="anchor" href="#components"&gt;#&lt;/a&gt;&lt;/h1&gt;
&lt;p&gt;A &lt;strong&gt;component&lt;/strong&gt; is a reusable unit of state. It&amp;rsquo;s the Orchard equivalent of a
function: it takes inputs, performs some work, and returns outputs. Scenarios
compose components to describe complex state without repeating themselves.&lt;/p&gt;
&lt;h2 id="defining-a-component"&gt;Defining a component&lt;a class="anchor" href="#defining-a-component"&gt;#&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;A component lives in its own file. The file contains one &lt;code&gt;component &amp;quot;&amp;lt;name&amp;gt;&amp;quot; { ... }&lt;/code&gt;
block:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" style="background-color:#f7f7f7;-moz-tab-size:2;-o-tab-size:2;tab-size:2;-webkit-text-size-adjust:none;"&gt;&lt;code class="language-hcl" data-lang="hcl"&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;&lt;span style="color:#57606a"&gt;# components/merchant.hcl
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;&lt;span style="color:#cf222e"&gt;component&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;merchant&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;variable&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;name&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; default &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;Default Merchant&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;variable&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;region&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; default &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;us&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; &lt;span style="color:#cf222e"&gt;action&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;postgres_query&amp;#34; &amp;#34;create&amp;#34;&lt;/span&gt; {
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; query &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#0a3069"&gt;&amp;#34;INSERT INTO merchants (name, region) VALUES (&amp;#39;${var.name}&amp;#39;, &amp;#39;${var.region}&amp;#39;) RETURNING id, name, region&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; output &amp;#34;id&amp;#34; { value &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#cf222e"&gt;action&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;postgres_query&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;create&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;id&lt;/span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; output &amp;#34;name&amp;#34; { value &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#cf222e"&gt;action&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;postgres_query&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;create&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;name&lt;/span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt; output &amp;#34;region&amp;#34; { value &lt;span style="color:#0550ae"&gt;=&lt;/span&gt; &lt;span style="color:#cf222e"&gt;action&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;postgres_query&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;create&lt;/span&gt;&lt;span style="color:#1f2328"&gt;.&lt;/span&gt;&lt;span style="color:#cf222e"&gt;region&lt;/span&gt; }
&lt;/span&gt;&lt;/span&gt;&lt;span style="display:flex;"&gt;&lt;span&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;A component has the same vocabulary as a scenario — variables, actions, outputs —
but no &lt;code&gt;required_providers&lt;/code&gt; or &lt;code&gt;provider&lt;/code&gt; blocks. Components inherit their providers
from the enclosing scenario.&lt;/p&gt;</description></item><item><title>Providers</title><link>https://orchard.pthm.dev/docs/concepts/providers/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://orchard.pthm.dev/docs/concepts/providers/</guid><description>&lt;h1 id="providers"&gt;Providers&lt;a class="anchor" href="#providers"&gt;#&lt;/a&gt;&lt;/h1&gt;
&lt;p&gt;A &lt;strong&gt;provider&lt;/strong&gt; is the runtime that turns a declarative HCL action into a real side
effect. &lt;code&gt;builtin/postgres&lt;/code&gt; opens a connection and runs SQL. &lt;code&gt;builtin/http&lt;/code&gt; makes
HTTP requests. &lt;code&gt;builtin/exec&lt;/code&gt; spawns child processes. Custom providers can do
anything you can write a binary for.&lt;/p&gt;
&lt;h2 id="the-two-kinds-of-providers"&gt;The two kinds of providers&lt;a class="anchor" href="#the-two-kinds-of-providers"&gt;#&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Built-in providers&lt;/strong&gt; are compiled into the &lt;code&gt;orchard&lt;/code&gt; binary. They&amp;rsquo;re always
available and need no installation. Today that&amp;rsquo;s:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;builtin/postgres&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;builtin/http&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;builtin/exec&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;External providers&lt;/strong&gt; are separate binaries that speak Orchard&amp;rsquo;s
&lt;a href="../../extending/provider-protocol/"&gt;provider protocol&lt;/a&gt; over stdio. They&amp;rsquo;re
referenced by path:&lt;/p&gt;</description></item><item><title>Wiring</title><link>https://orchard.pthm.dev/docs/concepts/wiring/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://orchard.pthm.dev/docs/concepts/wiring/</guid><description>&lt;h1 id="wiring"&gt;Wiring&lt;a class="anchor" href="#wiring"&gt;#&lt;/a&gt;&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;Wiring&lt;/strong&gt; is how outputs from one step flow into the inputs of the next, and how
Orchard decides the order to execute steps in. You never write a graph by hand —
you write references in expressions, and Orchard derives the graph from them.&lt;/p&gt;
&lt;h2 id="references"&gt;References&lt;a class="anchor" href="#references"&gt;#&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;Four reference namespaces are in scope inside expressions:&lt;/p&gt;
&lt;table&gt;
 &lt;thead&gt;
 &lt;tr&gt;
 &lt;th&gt;Form&lt;/th&gt;
 &lt;th&gt;Resolves to&lt;/th&gt;
 &lt;th&gt;Available when&lt;/th&gt;
 &lt;/tr&gt;
 &lt;/thead&gt;
 &lt;tbody&gt;
 &lt;tr&gt;
 &lt;td&gt;&lt;code&gt;var.&amp;lt;name&amp;gt;&lt;/code&gt;&lt;/td&gt;
 &lt;td&gt;A scenario or component variable.&lt;/td&gt;
 &lt;td&gt;Plan time — variables are resolved up front.&lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
 &lt;td&gt;&lt;code&gt;action.&amp;lt;type&amp;gt;.&amp;lt;name&amp;gt;.&amp;lt;output&amp;gt;&lt;/code&gt;&lt;/td&gt;
 &lt;td&gt;An output from another action.&lt;/td&gt;
 &lt;td&gt;After that action completes.&lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
 &lt;td&gt;&lt;code&gt;component.&amp;lt;type&amp;gt;.&amp;lt;name&amp;gt;.&amp;lt;output&amp;gt;&lt;/code&gt;&lt;/td&gt;
 &lt;td&gt;An output from a component instance.&lt;/td&gt;
 &lt;td&gt;After that component resolves.&lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
 &lt;td&gt;&lt;code&gt;var.&amp;lt;name&amp;gt;&lt;/code&gt; (inside a component)&lt;/td&gt;
 &lt;td&gt;The component&amp;rsquo;s own variable.&lt;/td&gt;
 &lt;td&gt;As soon as the component runs.&lt;/td&gt;
 &lt;/tr&gt;
 &lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;References can appear inside any attribute expression — in action bodies, provider
configs (variables only), output values, or component inputs.&lt;/p&gt;</description></item><item><title>Plan vs run</title><link>https://orchard.pthm.dev/docs/concepts/plan-vs-run/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://orchard.pthm.dev/docs/concepts/plan-vs-run/</guid><description>&lt;h1 id="plan-vs-run"&gt;Plan vs run&lt;a class="anchor" href="#plan-vs-run"&gt;#&lt;/a&gt;&lt;/h1&gt;
&lt;p&gt;Orchard has two execution modes. They share parsing, validation, and graph
construction but diverge on how they deal with providers and side effects.&lt;/p&gt;
&lt;h2 id="orchard-plan"&gt;&lt;code&gt;orchard plan&lt;/code&gt;&lt;a class="anchor" href="#orchard-plan"&gt;#&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;&lt;code&gt;orchard plan&lt;/code&gt; is a &lt;strong&gt;read-only&lt;/strong&gt; preview. It:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Parses the scenario file and any component files it references.&lt;/li&gt;
&lt;li&gt;Loads provider schemas.&lt;/li&gt;
&lt;li&gt;Validates the scenario: every reference resolves, every required attribute
is set, every type matches.&lt;/li&gt;
&lt;li&gt;Builds and sorts the dependency graph.&lt;/li&gt;
&lt;li&gt;Prints the plan — what will run, in what order, with what inputs.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;code&gt;plan&lt;/code&gt; &lt;strong&gt;never configures a provider and never executes an action.&lt;/strong&gt; It cannot
open database connections, make HTTP requests, or spawn subprocesses. For
built-in providers, plan skips &lt;code&gt;Configure&lt;/code&gt; entirely. For external providers,
plan uses a short-lived schema probe that runs &lt;code&gt;&amp;lt;binary&amp;gt; schema&lt;/code&gt;, reads the
schema JSON, and exits immediately.&lt;/p&gt;</description></item><item><title>Lifecycle and teardown</title><link>https://orchard.pthm.dev/docs/concepts/lifecycle/</link><pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate><guid>https://orchard.pthm.dev/docs/concepts/lifecycle/</guid><description>&lt;h1 id="lifecycle-and-teardown"&gt;Lifecycle and teardown&lt;a class="anchor" href="#lifecycle-and-teardown"&gt;#&lt;/a&gt;&lt;/h1&gt;
&lt;p&gt;Orchard creates state. Good tools also clean it up. Every &lt;code&gt;orchard run&lt;/code&gt; writes
a &lt;strong&gt;run record&lt;/strong&gt; describing what happened; &lt;code&gt;orchard teardown&lt;/code&gt; uses that record
to reverse it.&lt;/p&gt;
&lt;h2 id="run-records"&gt;Run records&lt;a class="anchor" href="#run-records"&gt;#&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;After every &lt;code&gt;orchard run&lt;/code&gt;, Orchard writes a JSON file named
&lt;code&gt;orchard_&amp;lt;scenario&amp;gt;_run_&amp;lt;id&amp;gt;.json&lt;/code&gt; into the current directory. The filename&amp;rsquo;s
&lt;code&gt;&amp;lt;id&amp;gt;&lt;/code&gt; prefix is sortable — &lt;code&gt;YYYYMMDDTHHMMSSZ_&amp;lt;8hex&amp;gt;&lt;/code&gt; — so listing the
directory in your shell gives you runs in chronological order.&lt;/p&gt;
&lt;pre tabindex="0"&gt;&lt;code&gt;$ orchard run scenarios/dev.hcl
scenario: dev
executing...
 ok action.postgres_query.create_merchant (4ms)
 ok action.postgres_query.create_product (2ms)
...

$ ls orchard_dev_run_*.json
orchard_dev_run_20260415T103045Z_a3f29e5b.json&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The record captures:&lt;/p&gt;</description></item></channel></rss>