Skip to content

Actor Lifecycle Hooks

Actor lifecycle hooks are rule events that fire at specific points in an actor's lifecycle. They allow you to validate operations, enforce business logic, and trigger automations tied to actor state changes.

Hook Timing

Hooks are organized by when they execute relative to the operation.

Before Hooks

Execute before the operation completes — can prevent it with a validation error:

Use for: Validation, preventing invalid state

After Hooks

Execute after the operation completes — changes are persisted:

Use for: Automation, notifications, integrations

Command Hooks

Execute when commands are applied to an actor:

Use for: Cascading logic, deriving additional changes

Calculate Hooks

Execute after the command hooks and their emitted commands have been applied, before the validate hooks:

  • OnOrderCalculate — Derived calculations on the enriched order (e.g. tax after price enrichment)

Use for: Calculations that consume the output of OnOrderCommands rules

Validate Hooks

Execute after the command and calculate hooks have settled — can reject the operation or auto-fix state:

  • OnOrderValidate — Enforce order invariants once all reactions have settled

Use for: Invariants on the post-reaction state, auto-fixing derived state

Journal Hooks

Execute when journal entries are created:

Use for: Audit trail reactions, logging

Hooks by Actor Type

Order (9 hooks)

Payment (7 hooks)

Ticket (8 hooks)

SKU (5 hooks)

Asset (5 hooks)

Execution Order

For a single actor operation, hooks execute in this sequence:

  1. Before hooks — can prevent the operation with a validation error
  2. Operation executes — entity created, commands applied
  3. Commands hooks — can add further commands
  4. Calculate hooks (order actor) — derived calculations on the enriched state
  5. Validate hooks (order actor) — enforce invariants or auto-fix once reactions settled
  6. Created/Deleted hooks — automation and notifications
  7. State-change hooks — for specific transitions, e.g. OnOrderInvoiceCreated when invoices appeared on the order, OnPaymentCapture when a payment was captured
  8. Journal hooks — if a journal entry was created

Example for creating an order:

  1. OnOrderBeforeCreated — Validate the order
  2. Order created in database
  3. OnOrderCreated — Send confirmation email
  4. OnOrderInvoiceCreated — If invoices were created in the same message, react to them (e.g. capture payments)
  5. OnOrderJournal — Log journal entry (if created)

Choosing the Right Hook

Use Before hooks when:

  • Validating input before operations complete
  • Preventing invalid state changes
  • Checking business rule constraints

Use After hooks when:

  • Sending notifications
  • Triggering external integrations
  • Creating related entities
  • Scheduling follow-up work

Use Command hooks when:

  • Deriving additional changes from commands
  • Applying cascading updates
  • Enforcing command combinations

Examples

Validation with a Before Hook

filtrera
param input: OnOrderBeforeCreated

let hasValidDelivery = input.order.deliveries count > 0

from hasValidDelivery match
  false |> {
    effect = 'validationError'
    code = 'NO_DELIVERY'
    message = 'Order must have at least one delivery'
  }

Automation with an After Hook

filtrera
param input: OnTicketComplete

from {
  effect = 'messageActor'
  actorType = 'order'
  actorId = input.ticket.orderId
  messages = [{
    type = 'applyCommands'
    body = {
      commands = [{
        type = 'addTag'
        value = 'support-resolved'
      }]
    }
  }]
}

Cascading with a Command Hook

filtrera
param input: OnOrderCommands

let hasCancellation = input.order.commands
  any c => c.type = 'cancel'

from hasCancellation match
  true |> {
    effect = 'orderCommand'
    type = 'addTag'
    value = 'cancelled'
  }

See Also

© 2026 Hantera AB. All rights reserved.