Skip to content
Docs / dflux Runner
ContactGet started

Flow schema

Authoritative schema for kind: flow YAML. Every field, every action type, every check op.

This page is the field-by-field reference. For prose on the authoring model, see Writing flows and suites and Flows. The cited template files live in the d3x-templates repository.

Synopsis

YAML

Top-level fields

NameTypeRequiredDefaultDescription
kindstringnoflow. Optional but required by the templates loader so it can dispatch to the correct parser.
namestringyesUnique flow name. Looked up by run-flow -flow <name>.
descriptionstringnoOne-line summary; shown in the catalog and control-plane UI.
detailstringnoLong-form description; markdown allowed.
categoryenumnofunctional, negative, robustness, stability, lifecycle, load, stress. Filters in catalog views.
typeenumyesclient or server. Client flows fire Start; server flows wait for first RX.
protocolenumyesngap, sbi, diameter, rest, pfcp. Routes inbound demux + the default send protocol.
nfenumyesgnb, amf, smf, ausf, udm, pcf, nrf, upf, mme, pgw, pcrf, af, external. Validated against the environment.
initial_statestringyesName of the state the FSM starts in.
final_states[]stringyesTerminal state names; reaching one ends the flow.
unsupported_states[]UnsupportedStatenoTerminals that mean “this core does not implement the scenario”. Produces verdict unsupported and run-flow exit 3 when every completed UE lands there. Each entry needs state (must be in final_states) and a reason. The state must be reachable by an inbound message, not via on_timeout or Error.
final_checks[]ChecknoAggregate-metric assertions evaluated once after every UE finishes. A failed final check does not abort the FSM (it has already ended) but makes the verdict fail.
fuzzobjectnoWire-level mutation of encoded frames. Present = this flow is a fuzz driver. Drive campaigns with d3x-run fuzz; see d3x-run schema for the field set.
statesmapyesMap of state name → State.
any_state_transitions[]TransitionnoFallback transitions matched when no state-specific transition does.

State shape

NameTypeRequiredDefaultDescription
transitions[]TransitionnoEvent-keyed transitions out of this state.
on_timeoutTimeoutConfignoFallback transition fired when no event matches before duration elapses.

TimeoutConfig:

NameTypeDescription
durationdurationHow long to wait before firing
targetstringTarget state
actions[]ActionRun on the timeout transition before target is applied, with the same execution semantics as transitions[].actions. Lets a flow express "wait N then send X" for token-expiry or post-idle re-probe tests.

For the conceptual model behind states and transitions, see States and transitions.

Transition shape

NameTypeRequiredDescription
eventEventDefyesTrigger; see Event shape
targetstringyesTarget state name (or _self in any_state_transitions)
actions[]ActionnoOperations to execute when this transition fires

Event shape

event: accepts three forms.

YAML

Authors may prefix any event name with the protocol (ngap.X, diameter.X, sbi.X) for visual disambiguation in multi-protocol flows. The matcher strips a known protocol prefix on either side before comparing; an unknown prefix such as weird.X is left intact and will not match a bare event.

Synthetic events:

EventSourceNotes
StartengineFired once per UE for client flows out of initial_state
ErrorprotocolFired on decode error, enricher error, or unrecoverable failure
StateTimeoutengineFired when an on_timeout block elapses
UplaneCompleteengineFired after a uplane_start action finishes its run

Action types

Action types: send, parallel_send, check, extract, uplane_start, ngap_realloc, ngap_handover_swap, cmd. All actions execute in YAML order within a transition, with the constraint that check and extract must not appear after a send / parallel_send. For when to reach for each, see Actions and checks.

send

Emit a message on the wire. Required when the transition needs to TX.

FieldTypeRequiredDescription
typesendyes
messagestringyesRegistered enricher name; see Enricher catalog
message_bodyJSON stringnoPre-populated fields on the typed message struct, merged before the enricher fills the rest
paramsmapnoRuntime params overlay
protocolenumnoOverride the default protocol (per-action; used in multi-protocol flows)
peerstringnoOverride the target peer name within the protocol
YAML

check

Assert a field on the most recent inbound message (or ue.<path> against UE context). Must precede any send in the same transition.

FieldTypeRequiredDescription
typecheckyes
fieldstringyesField path; ue.X reads UE context, otherwise reads the most recent RX message
openumyesSee Check ops
expectedanydependsRequired for ops that compare against a value

extract

Read a field off the most recent inbound message and store it in ue.Params[<store>] for later template lookup. Must precede any send.

YAML
FieldTypeRequiredDescription
typeextractyes
fieldstringone ofShorthand: field path to read from the inbound message. Pair with store.
valuestringone ofShorthand: a template-derived value, used instead of field. Set field or value, never both.
storestringyes (shorthand)Shorthand: target key in ue.Params
extractslistone ofList form: multiple {field|value, store} entries

uplane_start

Arm the user-plane traffic generator after the NGAP send that surfaced the UPF tunnel parameters. Reads parameters from the gNB's uplane: config block. Allowed between sends.

YAML

ngap_realloc

NGAP-only. Reallocate RAN-UE-NGAP-ID on the same gNB before the next send. Used in stress flows.

ngap_handover_swap

NGAP-only. Move the UE from the source gNB to the target gNB after HandoverCommand. Used by templates/gnb/handover_source.yaml.

parallel_send

Fire N copies of one send concurrently. Must be the only send-type action in the transition.

FieldTypeRequiredDescription
typeparallel_sendyes
messagestringyesRegistered enricher name
countintyesTotal number of requests to fire (≥ 1)
concurrencyintnoMax in flight at once. 0 = unbounded, capped at count

cmd

Run a local program synchronously. There is no shell — argv is a list, with no word-splitting or globbing. Off unless the process was started with -allow-cmd-actions.

FieldTypeRequiredDescription
typecmdyes
argv[]stringyesProgram + arguments as a list. Every element is template-expanded.
cwdstringnoWorking directory. Relative paths resolve against the flow YAML's own directory (also the default).
envmapnoEnvironment overlay on the runner's own env (values are template-expanded).
timeoutdurationnoKill the process on expiry (default 10s).
ignore_errorboolnoA non-zero exit or timeout is logged instead of failing the UE.
store_stdout / store_stderrstringnoPublish captured output into ue.Params under this key.

Check ops

OpRequired expectedPasses when
equalsyesField equals the expected value
not_equalsyesField's string form differs from expected
not_emptynoField resolves and is non-zero
greater_thanyesField > expected
less_thanyesField < expected
greater_or_equalyesField ≥ expected
less_or_equalyesField ≤ expected
containsyesField's string form contains the expected substring
not_containsyesField's string form does not contain the expected substring
existsnoField resolves (regardless of value)
regexyesField's string form matches the RE2 pattern in expected
in / oneofyesField's string form is a member of the expected set
lengthyesLength of the resolved value equals expected
ie_presentnoField resolves and is non-nil/non-empty (stricter than exists)

Template expressions

message_body JSON, params values, and expected values may contain {{...}} expressions. Two forms.

YAML

Whole-value templates ("{{x}}") preserve the resolved value's native type. String interpolation ("prefix-{{x}}-suffix") returns a string. Compilation happens at flow-load time; unknown function names and arity errors fail fast.

Resolution scopes:

  • ue.X — UE context fields (PascalCase)
  • params.X — per-flow params (params: on a suite step, or the send action's own params)
  • bare names — fields on the most recent inbound message

Enricher catalog

Each enricher binds one message label to a built-in encoder. The FSM author references the label by name in send.message. The tables below are a representative subset. Dump the live catalog — every enricher name, plus accepted params, check ops, and metric keys — with d3x-run vocab.

NGAP

MessagePrototype
NGSetupRequestNGAPNgSetupRequest
InitialUEMessageNGAPInitialUEMessage
AuthResponseNGAPNASUplinkNASTransport
SecurityModeCompleteNGAPNASUplinkNASTransport
InitialContextSetupResponseNGAPInitialContextSetupResponse
RegistrationCompleteNGAPNASUplinkNASTransport
ConfigurationUpdateCompleteNGAPNASUplinkNASTransport
PDUSessionEstablishmentRequestNGAPNASUplinkNASTransport
PDUSessionResourceSetupResponseNGAPPduSessionResourceSetupResponse
DeregistrationRequestNGAPNASUplinkNASTransport
UEContextReleaseCommandNGAPUEContextReleaseCommand
UEContextReleaseCompleteNGAPUEContextReleaseComplete
PDUSessionReleaseRequestNGAPNASUplinkNASTransport
PDUSessionResourceReleaseResponseNGAPPduSessionResourceReleaseResponse
NGResetNGAPNGReset
ServiceRequestNGAPInitialUEMessage
UEContextReleaseRequestNGAPUEContextReleaseRequest
UEContextSuspendRequestNGAPUEContextSuspendRequest
RANConfigurationUpdateNGAPRANConfigurationUpdate
MalformedInitialUEMessageNGAPInitialUEMessage
HandoverRequiredNGAPHandoverRequired
HandoverNotifyNGAPHandoverNotify

Diameter

S6a: ULR, ULA, ULAUserUnknown, ULALoopDetected, AIR, AIA, PUR, PUA, IDR, IDA, CLR, CLA, NOR, NOA. All on DiameterMessageProto.

Gx: CCRInit, CCRTerminate, CCA.

Rx: AAR, AAA.

SBI

UDM: Nudm_SDM_GetSubscriptionData, Nudm_SDM_GetSubscriptionData_Answer, Nudm_UEAuthentication_GetAuthData, Nudm_UEAuthentication_GetAuthData_Answer.

AUSF: Nausf_UEAuthentication_Authenticate, Nausf_UEAuthentication_Authenticate_Answer.

AMF: Namf_Communication_N1N2MessageTransfer, Namf_Communication_N1N2MessageTransfer_Answer.

PFCP

PFCPHeartbeatRequest, PFCPHeartbeatResponse, PFCPAssociationSetupRequest, PFCPAssociationSetupResponse, PFCPSessionEstablishmentRequest, PFCPSessionEstablishmentResponse, PFCPSessionModificationRequest, PFCPSessionModificationResponse, PFCPSessionDeletionRequest, PFCPSessionDeletionResponse.

REST

Generic — flow authors declare the message label inline. The loader registers the label at flow-load time. The shipped catch-all sentinels are RESTGeneric and RESTGeneric_Answer.

Examples

Minimal client flow

YAML

Server flow

YAML

Notes

  • A check action that fails aborts the transition; the FSM stays in the current state.
  • Send actions cannot precede checks within the same transition. The validator rejects this at flow-load.
  • Server flows must NOT have a Start-event transition at initial_state — they're reactive.
  • Client flows MUST have a Start-event transition at initial_state.
  • _self is allowed only as the target of an any_state_transition and means "stay in the current state".

Where to go next