Workflow Studio

Triggers Reference

Complete configuration reference for every workflow trigger type — schedule, webhook, record events, ITSM events, event bus, and manual.

Overview

A trigger is what starts a workflow run. Every workflow has exactly one trigger. The trigger defines what event to listen for and can include filters so the workflow only runs when conditions are met. Trigger payloads are available to nodes as {{trigger.*}}.

Schedule Trigger

Runs the workflow on a POSIX cron schedule. The trigger payload contains the scheduled fire time and workspace metadata.

FieldTypeRequiredDefaultDescription
typeliteralrequiredMust be "schedule"
cronstringrequiredPOSIX cron expression: "min hour day month weekday". Seconds not supported.
timezonestringoptionalUTCIANA timezone identifier. e.g. "America/New_York". Cron is evaluated in this timezone.
startAttimestampoptionalISO 8601. Schedule is inactive before this datetime.
endAttimestampoptionalISO 8601. Schedule is automatically deactivated after this datetime.
maxConcurrentRunsintegeroptional1Max simultaneous runs. If a run is still active when the schedule fires, behaviour depends on skipIfRunning.
skipIfRunningbooleanoptionaltrueIf true and a run is still active, skip this fire instead of queuing.
json
{
  "trigger": {
    "type": "schedule",
    "cron": "0 8 * * MON-FRI",
    "timezone": "America/New_York",
    "skipIfRunning": true
  }
}
// Trigger payload available to nodes:
// trigger.scheduledAt  — ISO timestamp of the scheduled fire time
// trigger.actualFiredAt — ISO timestamp of actual execution start
// trigger.workspace.slug

Common cron expressions

ExpressionSchedule
0 * * * *Every hour at :00
0 9 * * *Every day at 9:00 AM
0 9 * * MON-FRIWeekdays at 9:00 AM
*/15 * * * *Every 15 minutes
0 0 1 * *1st of every month at midnight
0 8,17 * * MON-FRIWeekdays at 8 AM and 5 PM
0 0 * * SUNEvery Sunday midnight

Webhook (Inbound) Trigger

FlowOS generates a unique inbound URL for each workflow with a webhook trigger. External systems POST to this URL to start a run.

FieldTypeRequiredDefaultDescription
typeliteralrequiredMust be "webhook"
methodenumoptionalPOSTPOST · GET · PUT · PATCH. The HTTP method the webhook URL accepts.
authenticationenumoptionalnonenone · hmac_sha256 · bearer · basic. How incoming requests are validated.
secretstringoptionalRequired for hmac_sha256 and bearer auth. Stored encrypted.
allowedIpsstring[]optionalCIDR ranges allowed to call this webhook. Empty = allow all.
responseModeenumoptionalasyncasync (200 immediately, run async) · sync (wait up to 30s, return run output).
responseBodystringoptionalStatic JSON body to return immediately (async mode). Template expressions supported.
conditionsobject[]optionalRun only if body/header conditions match. See condition schema.
json
{
  "trigger": {
    "type": "webhook",
    "method": "POST",
    "authentication": "hmac_sha256",
    "secret": "{{secrets.GITHUB_WEBHOOK_SECRET}}",
    "conditions": [
      { "field": "body.action", "operator": "in", "value": ["opened", "reopened"] },
      { "field": "body.pull_request.base.ref", "operator": "equals", "value": "main" }
    ]
  }
}
// Generated URL: https://acme.flowos.io/webhooks/wf_01HZ.../inbound
// trigger.body.*     — parsed request body
// trigger.headers.*  — request headers
// trigger.method     — HTTP method
// trigger.ip         — sender IP address

Record Event Trigger

Fires when a record in a DB Studio table is created, updated, or deleted. Supports field-level conditions.

FieldTypeRequiredDefaultDescription
typeenumrequiredrecord_created · record_updated · record_deleted · record_any
tableSlugstringrequiredSlug of the table to watch.
conditionsobject[]optionalFilter conditions on the record fields. All must pass for the trigger to fire.
changedFieldsstring[]optionalFor record_updated: only fire if one of these fields changed. Empty = any change.
json
{
  "trigger": {
    "type": "record_updated",
    "tableSlug": "incidents",
    "changedFields": ["status"],
    "conditions": [
      { "field": "status",   "operator": "equals", "value": "resolved" },
      { "field": "severity", "operator": "in",     "value": ["P1","P2"] }
    ]
  }
}
// trigger.record.*   — full record after the change
// trigger.before.*   — field values before the change (record_updated only)
// trigger.changes    — array of { field, from, to } for changed fields

ITSM Event Trigger

Fires on specific ITSM lifecycle events — incident escalations, change approvals, SLA breaches, etc.

FieldTypeRequiredDefaultDescription
typeliteralrequiredMust be "itsm_event"
eventstringrequiredThe event type to watch. See the full event catalog in the Webhooks & Events docs.
conditionsobject[]optionalConditions on the event payload fields.
json
{
  "trigger": {
    "type": "itsm_event",
    "event": "incident.sla_breached",
    "conditions": [
      { "field": "resource.severity", "operator": "in", "value": ["P1","P2"] }
    ]
  }
}
// trigger.event.*      — full event payload (see event catalog)
// trigger.resource.*   — the incident/change/problem record
// trigger.actor.*      — who triggered the event (user or system)

Event Bus Trigger

Fires when a message is published to a named event bus topic.

FieldTypeRequiredDefaultDescription
typeliteralrequiredMust be "event_bus"
topicstringrequiredName of the event bus topic to subscribe to.
eventTypestringoptionalFilter to a specific event type within the topic. Empty = all.
conditionsobject[]optionalConditions on the event payload fields.
batchSizeintegeroptional1Batch up to N messages into a single run. Available as trigger.batch array.
batchWindowMsintegeroptional0Collect messages for this many ms before starting the run (batching window).

Event Trigger

Fires when a named platform event is emitted — e.g. request.created when a service catalog request is submitted. No polling; the workflow is invoked synchronously as the event is dispatched.

FieldTypeRequiredDefaultDescription
typeliteralrequiredMust be "event"
eventNamestringrequiredName of the platform event to listen for. e.g. "request.created"
conditionsobject[]optionalFilter conditions on the event payload fields. All must pass for the workflow to fire.
json
// Trigger any workflow on every catalog request submission:
{
  "trigger": {
    "type": "event",
    "config": {
      "eventName": "request.created"
    }
  }
}

// Trigger payload available to nodes as ctx.payload.*:
// requestId       — MongoDB ObjectId of the new request
// requestNumber   — human-readable number, e.g. "REQ-0030"
// catalogItemId   — ID of the catalog item requested
// requestedBy     — user ID of the submitter
// workspaceId     — workspace the request belongs to
// title           — request title
// variables       — key-value map of form field responses (catalog item variables)
Multiple workflows
Multiple workflows can listen to the same event — all fire. Use a Condition node filtering on ctx.payload.catalogItemId to limit a workflow to a specific catalog item.
Built-in platform events
request.created — service catalog request submitted incident.created — ITSM incident opened incident.resolved — incident moved to resolved change.approved — change request approved sla.breached — SLA timer exceeded

Manual Trigger

Workflow can only be started via API call or the "Run now" button in the studio. No automatic firing.

FieldTypeRequiredDefaultDescription
typeliteralrequiredMust be "manual"
inputSchemaobjectoptionalJSON Schema defining the expected input fields. Validated on trigger calls.
requiredScopesstring[]optionalToken scopes required to trigger this workflow via API. Default: workflows:trigger.

Trigger Condition Schema

All trigger types that accept conditions use this schema for each condition object:

FieldTypeRequiredDefaultDescription
fieldstringrequiredDot-notation path into the trigger payload. e.g. "body.event.severity" or "record.status".
operatorenumrequiredequals · not_equals · in · not_in · contains · starts_with · ends_with · gt · gte · lt · lte · is_null · is_not_null · regex
valueanyoptionalThe value to compare against. For "in"/"not_in", pass an array.