# OpenMAIC Action Engine Action Categories: Fire-and-Forget vs Synchronous

> Discover OpenMAIC Action Engine's two action categories: Fire-and-Forget for instant execution and Synchronous for sequential completion. Learn how they streamline your AI playback.

- Repository: [MAIC/OpenMAIC](https://github.com/THU-MAIC/OpenMAIC)
- Tags: internals
- Published: 2026-09-03

---

**The OpenMAIC Action Engine supports two distinct action categories: Fire-and-Forget actions (like `spotlight` and `laser`) that execute instantly without blocking the playback pipeline, and Synchronous actions (like `speech`, `play_video`, and whiteboard operations) that must complete before the engine proceeds to the next action.**

The OpenMAIC Action Engine, part of the THU-MAIC/OpenMAIC repository, orchestrates multimedia educational content by categorizing operations into distinct execution models. Understanding these OpenMAIC Action Engine action categories is essential for building responsive presentations that coordinate visual effects, narration, and interactive elements. The engine distinguishes between transient visual effects and time-consuming operations that require strict sequential ordering.

## Core Action Categories

The type definitions in `packages/@openmaic/dsl/src/action.ts` establish the fundamental contract distinguishing how actions interact with the playback timeline.

### Fire-and-Forget Actions

Fire-and-Forget actions are executed instantly without blocking the playback pipeline. These visual effects return control to the engine immediately, allowing subsequent actions to proceed without waiting for completion.

According to the source code in `packages/@openmaic/dsl/src/action.ts`, this category includes:

- **`spotlight`** – Highlights specific slide elements with configurable dimming
- **`laser`** – Pointer visual effects for emphasizing content

These actions are ideal for transient visual feedback that should not delay the presentation flow.

### Synchronous Actions

Synchronous actions must complete (or be acknowledged) before the engine proceeds to the following action. This blocking behavior ensures that time-dependent operations finish before the presentation continues.

The synchronous category encompasses:

- **`speech`** – Text-to-speech narration requiring TTS completion
- **`play_video`** – Embedded video playback
- **`wb_open`**, **`wb_draw_*`**, **`wb_edit_code`** – Whiteboard canvas operations
- **`discussion`** – Interactive discussion segments
- **`widget_*`** – Widget interactions including `widget_highlight`

As implemented in THU-MAIC/OpenMAIC, these actions populate the `SYNC_ACTIONS` constant set defined at lines 66-88 of the action definitions file.

## Runtime Constants and Type Safety

The engine exposes explicit helper constants for runtime categorization and validation:

- **`FIRE_AND_FORGET_ACTIONS`** – A TypeScript set containing `spotlight` and `laser` types (line 60)
- **`SYNC_ACTIONS`** – The comprehensive list of synchronous types (lines 66-88)

Additionally, the engine defines **slide-only actions** that constrain certain fire-and-forget operations to slide canvas contexts. Both `spotlight` and `laser` belong to this subset (line 64), meaning they only execute when a slide presentation surface is active, though they remain non-blocking.

## Working with Action Categories in Code

When constructing scenes, developers instantiate actions using the `Action` type union. The engine processes these objects differently based on their category membership as defined in the DSL.

**Fire-and-Forget instantiation:**

```typescript
import type { Action } from '@openmaic/dsl';

const spotlight: Action = {
  type: 'spotlight',
  id: 'a1',
  elementId: 'elem_42',
  dimOpacity: 0.6,
};

```

**Synchronous instantiation:**

```typescript
// Blocks until TTS engine finishes speaking
const speech: Action = {
  type: 'speech',
  id: 'a2',
  text: 'Welcome to the lesson!',
  voice: 'en-US',
  speed: 1.0,
};

// Blocks until drawing animation completes
const drawText: Action = {
  type: 'wb_draw_text',
  id: 'a3',
  content: 'Key concept',
  x: 100,
  y: 150,
  width: 400,
  height: 100,
};

// Blocks until user acknowledges widget interaction
const widgetHighlight: Action = {
  type: 'widget_highlight',
  id: 'a4',
  target: '#simulation-button',
  content: 'Click this to start the demo.',
};

```

## Implementation Across the Codebase

The categorization system extends beyond type definitions into runtime generation and validation logic.

In [`lib/server/agent-runtime/generation-tools.ts`](https://github.com/THU-MAIC/OpenMAIC/blob/main/lib/server/agent-runtime/generation-tools.ts), the `generateSceneActions` function consumes these categories when constructing presentation sequences. The runtime checks action types against `FIRE_AND_FORGET_ACTIONS` and `SYNC_ACTIONS` to determine whether to await completion or proceed immediately.

Testing infrastructure validates these semantics rigorously:

- [`tests/workbench/tts-stage-sync.test.ts`](https://github.com/THU-MAIC/OpenMAIC/blob/main/tests/workbench/tts-stage-sync.test.ts) verifies that speech actions properly block the stage until text-to-speech completion
- [`tests/video-export/normalize.test.ts`](https://github.com/THU-MAIC/OpenMAIC/blob/main/tests/video-export/normalize.test.ts) ensures unknown action types are filtered during export, demonstrating the critical role of categorization for pipeline integrity

## Summary

- The OpenMAIC Action Engine organizes all operations into **Fire-and-Forget** and **Synchronous** categories based on blocking requirements.
- **Fire-and-Forget** actions (`spotlight`, `laser`) execute instantly in `packages/@openmaic/dsl/src/action.ts` without blocking the playback pipeline.
- **Synchronous** actions (`speech`, `play_video`, `wb_draw_*`, `discussion`, `widget_*`) enforce completion before the engine proceeds.
- **Slide-only actions** represent a contextual subset of fire-and-forget operations restricted to slide canvas presence.
- Runtime constants enable type-safe validation and filter logic across the generation tools and export pipelines.

## Frequently Asked Questions

### What distinguishes Fire-and-Forget from Synchronous actions in the OpenMAIC Action Engine?

Fire-and-Forget actions execute instantly and immediately return control to the engine, allowing the pipeline to advance without waiting. Synchronous actions block execution until they complete or receive explicit acknowledgment, ensuring operations like video playback or narration finish before subsequent actions begin.

### Which whiteboard operations are classified as Synchronous actions?

All whiteboard-related actions are synchronous, including `wb_open` for canvas initialization, `wb_draw_text` and other `wb_draw_*` variants for drawing operations, and `wb_edit_code` for code editing within the whiteboard interface. These actions block the pipeline until the user or system completes the editing or drawing operation.

### Are spotlight and laser effects available on all canvas types?

No, `spotlight` and `laser` are classified as **slide-only actions** within the fire-and-forget category. According to lines 64 and surrounding context in `packages/@openmaic/dsl/src/action.ts`, these actions only apply when a slide canvas is present, though they maintain non-blocking execution semantics typical of fire-and-forget operations.

### How does the engine validate action categories during scene generation?

The engine references the `FIRE_AND_FORGET_ACTIONS` and `SYNC_ACTIONS` sets defined in `packages/@openmaic/dsl/src/action.ts` to perform compile-time and runtime membership checks. Validation logic in [`lib/server/agent-runtime/generation-tools.ts`](https://github.com/THU-MAIC/OpenMAIC/blob/main/lib/server/agent-runtime/generation-tools.ts) and test suites like [`tests/video-export/normalize.test.ts`](https://github.com/THU-MAIC/OpenMAIC/blob/main/tests/video-export/normalize.test.ts) enforce category constraints, filtering unknown types and applying appropriate await semantics based on category membership.