Skip to content

Workflow Functions in Martini

Overview

Martini's workflow functions provide a programmatic way to invoke workflows and deliver events to paused workflow instances.

There are two core workflow functions:

  • invokeWorkflow — triggers a workflow by namespace and optionally passes input data, returning the workflow's output. Intended for use in services (and Groovy code), since workflows already have the dedicated Invoke Workflow Node for this purpose.
  • sendEvent — delivers a named event (with optional payload) to one or all workflow instances currently paused at a Wait For Event Node.

What You Will Learn

  • The two overloads of invokeWorkflow and sendEvent and when to use each
  • How to pass inputs and read outputs for both functions
  • How to troubleshoot common issues

When To Use This

  • Use invokeWorkflow to trigger a workflow from a service or Groovy code.
  • Use sendEvent to resume workflow instances paused at a Wait For Event Node.

Prerequisites

Invoking a Workflow Programmatically

invokeWorkflow lets you start any workflow in the same Martini package from a service or Groovy code. It resolves the workflow by namespace, maps your inputs to the workflow's declared input properties, executes the workflow, and returns the workflow's output properties wrapped in a data model named output.

Getting Started with invokeWorkflow

There are two overloads:

1
2
invokeWorkflow(workflowName)
invokeWorkflow(workflowName, input)

invokeWorkflow(workflowName)

Use this function when the target workflow requires no inputs.

  • workflowName — the workflow namespace (for example, "acme_billing.GenerateInvoice").
  • To copy the namespace:
    • Right-click the workflow in the Navigator view
    • Select Copy Namespace or press

invokeWorkflow(workflowName, input)

Use this function when the target workflow requires inputs.

  • workflowName — the workflow namespace.
  • input — a data model or Map containing the workflow inputs.
  • Input property names must exactly match the workflow's declared input property names (case-sensitive).

Example

Suppose acme_billing.GenerateInvoice declares:

  • Inputs: customerId, orderId
  • Output: invoiceNumber

Populate customerId and orderId in input and invoke the workflow. The function returns the workflow output, including output.invoiceNumber (for example, "INV-2026-00391").

How invokeWorkflow Works

When you call invokeWorkflow, Martini performs the following steps in order:

  1. Resolves the workflow using the namespace you provide.
  2. Maps inputs from the input argument to the target workflow's declared input properties. Mapping is case-sensitive — customerid will not match a property named customerId.
  3. Executes the workflow synchronously, blocking until the workflow completes.
  4. Returns the output as a data model named output, containing the workflow's declared output properties and their values.

Same-package restriction

invokeWorkflow can only call workflows within the same Martini package. If you need to invoke a workflow from another package, that package must be declared as a dependency of the calling package.

Troubleshooting invokeWorkflow Issues

Problem Detection Cause Fix
Workflow not found Runtime exception referencing the namespace Incorrect or mistyped namespace Right-click the workflow in the Navigator view and use Copy Namespace to get the exact value
Inputs not mapped Output properties are null or empty Property name casing mismatch (e.g., customerid vs customerId) Match input Map or data model property names exactly to the workflow's declared input property names
Cross-package invocation fails Runtime error at execution Target workflow is in a different package not listed as a dependency Add the target package as a dependency, or move the workflow into the same package
output is empty All output properties return null Workflow has no declared output properties Open the workflow in the Workflow Designer and verify output properties are configured under Inputs & Outputs

Sending Events to Paused Workflow Instances

sendEvent delivers a named event — with an optional data payload — to workflow instances that are currently paused at a Wait For Event Node. You can broadcast the event to all matching instances or target a single instance by its context ID.

This function is the programmatic counterpart to manually triggering event-based workflow resumption, and is particularly useful when an external system (such as a payment gateway, an approval microservice, or a monitoring agent) needs to unblock a waiting workflow.

Getting Started with sendEvent

There are two overloads:

1
2
sendEvent(event)
sendEvent(event, contextId)

sendEvent(event)

Use this when you want to broadcast an event to all workflow instances currently paused and waiting for it.

  • Map a data model to event — it must have a name property matching the event name configured in the Wait For Event node (case-sensitive) and a data property containing the payload.
  • The function returns postEvents, a data model array where each element contains the contextId and updated status of a resumed instance.

sendEvent(event, contextId)

Use this when you want to deliver an event to one specific workflow instance.

  • Provide the same event model and set contextId to the target instance's context ID.
  • The function returns postEvent, a single data model with the contextId and updated status of the resumed instance.

Example

Suppose multiple instances of acme_hr.OnboardEmployee are paused waiting for BackgroundCheckComplete. Map an event model with name set to "BackgroundCheckComplete" and data containing the payload properties (e.g., employeeId and status).

  • Use sendEvent(event) to resume all waiting instances.
  • Use sendEvent(event, contextId) to resume only the instance matching contextId.

How sendEvent Works

When you call sendEvent, Martini performs the following steps:

  1. Queries the database for all workflow instances currently paused at a Wait For Event node.
  2. Filters by event name — only instances waiting for the exact event name you provide are considered.
  3. Applies context ID filter (if provided) — limits delivery to the single workflow instance with the matching context ID.
  4. Maps the event's data payload into the input properties of the Wait For Event node. Property name matching is case-sensitive.
  5. Resumes each targeted instance immediately from the node following the Wait For Event node.
  6. Returns results:
    • If no contextId was provided: returns postEvents, a data model array where each element contains the contextId and updated status of a resumed instance.
    • If a contextId was provided: returns postEvent, a single data model containing the contextId and updated status of the resumed instance.

Troubleshooting sendEvent Issues

Problem Detection Cause Fix
No workflow instances resumed postEvents is an empty list No instances are currently paused waiting for the specified event name Verify the event name matches exactly (case-sensitive) what is configured in the Wait For Event node
Event payload not mapped Wait For Event node properties remain null after resumption Property name casing mismatch in the event's data object Match each property name in data exactly to the property names configured in the Wait For Event node
Wrong instance resumed Unexpected workflow instance received the event contextId not supplied when multiple instances were waiting Obtain the correct contextId and pass it to sendEvent
postEvent returns null No result returned when targeting by contextId The supplied contextId does not match any paused instance Confirm the instance is still paused (it may have already been resumed or timed out)

Helpful Resources