Your First Intent (Action)
Continuing the concert app: intents are commands your app submits. Rules run in three phases:
preflight → core → side_effectsIn the DSL, intents are declared under the actions: key in .actions.causet files.
Project: Follow along in the Concert app from causet init. Open actions/.
Prerequisite: Your First Event — ARTIST_FOLLOWED, SHOW_ANNOUNCED.
Follow an artist
# actions/follow.actions.causet
actions:
FOLLOW_ARTIST:
state: user
entity_id_expr: intent.user_id
input:
user_id: { type: string, required: true }
artist_id: { type: string, required: true }
preflight:
rules:
- name: reject_self_follow
when: { expr: "intent.user_id == intent.artist_id" }
then:
- op: reject
code: CANNOT_FOLLOW_SELF
core:
rules:
- name: increment_following
when: {}
then:
- op: add
path: /following_count
value: 1
side_effects:
rules:
- name: emit_followed
then:
- op: emit
event_type: ARTIST_FOLLOWED
payload:
user_id: intent.user_id
artist_id: intent.artist_id| Phase | This intent |
|---|---|
| Preflight | Reject self-follow |
| Core | Increment following_count on the user |
| Side effects | Emit ARTIST_FOLLOWED |
Announce a show
# actions/show.actions.causet
actions:
ANNOUNCE_SHOW:
state: artist
entity_id_expr: intent.artist_id
input:
artist_id: { type: string, required: true }
show_id: { type: string, required: true }
venue: { type: string, required: true }
date: { type: string, required: true }
title: { type: string, required: true }
core:
rules:
- name: emit_announced
when: {}
then:
- op: emit
event_type: SHOW_ANNOUNCED
payload:
artist_id: intent.artist_id
show_id: intent.show_id
venue: intent.venue
date: intent.date
title: intent.titleSubmit via CLI
Follow Pearl Jam:
causet intent FOLLOW_ARTIST \
--fork main \
--stream user_stream \
--entity user-1 \
--payload '{"user_id":"user-1","artist_id":"artist-pearl-jam"}'Announce a show:
causet intent ANNOUNCE_SHOW \
--fork main \
--stream artist_stream \
--entity artist-pearl-jam \
--payload '{"artist_id":"artist-pearl-jam","show_id":"show-pj-brooklyn-2026","venue":"Barclays Center","date":"2026-09-15","title":"Pearl Jam - Dark Matter Tour"}'A reject in preflight aborts the intent — no state changes, no events.
Rule phases reference
| Phase | Allowed | Forbidden |
|---|---|---|
| Preflight | reject, lookup, read-only checks | mutations, emit, submit |
| Core | set, add, emit, relationship_create | reject, submit, decision |
| Side effects | emit, submit, schedule, decision | direct state writes |
Full reference: Intent Rules.
Concert app so far
concert-app/
app.causet
states/ user.state.causet, artist.state.causet
events/ follow.events.causet, show.events.causet
actions/ follow.actions.causet, show.actions.causetNext steps
- Your First Projection —
user_followingandartist_show_directory - Intents — full operations reference