acc-create-saga-pattern

Generates Saga pattern components for PHP 8.5. Creates Saga interfaces, steps, orchestrator, state management, and compensation logic with unit tests.

16 stars

Best use case

acc-create-saga-pattern is best used when you need a repeatable AI agent workflow instead of a one-off prompt.

Generates Saga pattern components for PHP 8.5. Creates Saga interfaces, steps, orchestrator, state management, and compensation logic with unit tests.

Teams using acc-create-saga-pattern should expect a more consistent output, faster repeated execution, less prompt rewriting.

When to use this skill

  • You want a reusable workflow that can be run more than once with consistent structure.

When not to use this skill

  • You only need a quick one-off answer and do not need a reusable workflow.
  • You cannot install or maintain the underlying files, dependencies, or repository context.

Installation

Claude Code / Cursor / Codex

$curl -o ~/.claude/skills/acc-create-saga-pattern/SKILL.md --create-dirs "https://raw.githubusercontent.com/diegosouzapw/awesome-omni-skill/main/skills/development/acc-create-saga-pattern/SKILL.md"

Manual Installation

  1. Download SKILL.md from GitHub
  2. Place it in .claude/skills/acc-create-saga-pattern/SKILL.md inside your project
  3. Restart your AI agent — it will auto-discover the skill

How acc-create-saga-pattern Compares

Feature / Agentacc-create-saga-patternStandard Approach
Platform SupportNot specifiedLimited / Varies
Context Awareness High Baseline
Installation ComplexityUnknownN/A

Frequently Asked Questions

What does this skill do?

Generates Saga pattern components for PHP 8.5. Creates Saga interfaces, steps, orchestrator, state management, and compensation logic with unit tests.

Where can I find the source code?

You can find the source code on GitHub using the link provided at the top of the page.

SKILL.md Source

# Saga Pattern Generator

Creates Saga pattern infrastructure for distributed transaction coordination.

## When to Use

- Distributed transactions across multiple services
- Long-running business processes
- Operations requiring compensation on failure
- Multi-step workflows with rollback capability

## Component Characteristics

### SagaState Enum
- Domain layer enum
- Defines saga lifecycle states: Pending, Running, Compensating, Completed, Failed, CompensationFailed
- Includes state transition validation
- Terminal states detection

### SagaStep Interface
- Domain layer interface
- Execute and compensate methods
- Idempotency declaration
- Timeout configuration

### SagaContext
- Carries saga execution data
- Serializable for persistence
- Supports data accumulation across steps

### SagaOrchestrator
- Application layer coordinator
- Manages step execution
- Handles compensation flow (reverse order)
- Persists state after each step

### SagaPersistence
- Stores saga state for recovery
- Supports finding incomplete sagas
- Dead letter handling

---

## Generation Process

### Step 1: Analyze Request

Determine:
- Context name (Order, Payment, Shipping)
- Required saga steps
- Compensation logic for each step

### Step 2: Generate Core Components

Create in this order:

1. **Domain Layer** (`src/Domain/Shared/Saga/`)
   - `SagaState.php` — State enum with transitions
   - `StepResult.php` — Step result value object
   - `SagaStepInterface.php` — Step contract
   - `SagaContext.php` — Execution context
   - `SagaResult.php` — Saga result
   - Exception classes

2. **Application Layer** (`src/Application/Shared/Saga/`)
   - `SagaPersistenceInterface.php` — Persistence port
   - `SagaRecord.php` — Persisted record
   - `AbstractSagaStep.php` — Base step class
   - `SagaOrchestrator.php` — Orchestrator

3. **Infrastructure Layer**
   - `DoctrineSagaPersistence.php` — Doctrine implementation
   - Database migration

4. **Tests**
   - `SagaStateTest.php`
   - `SagaOrchestratorTest.php`

### Step 3: Generate Context-Specific Steps

For each saga step (e.g., Order saga):

```
src/Application/{Context}/Saga/Step/
├── ReserveInventoryStep.php
├── ChargePaymentStep.php
└── CreateShipmentStep.php

src/Application/{Context}/Saga/
└── {Context}SagaFactory.php
```

---

## File Placement

| Layer | Path |
|-------|------|
| Domain Types | `src/Domain/Shared/Saga/` |
| Application Saga | `src/Application/Shared/Saga/` |
| Context Steps | `src/Application/{Context}/Saga/Step/` |
| Saga Factory | `src/Application/{Context}/Saga/` |
| Infrastructure | `src/Infrastructure/Persistence/Doctrine/Repository/` |
| Unit Tests | `tests/Unit/{Layer}/{Path}/` |

---

## Key Principles

### Compensation Rules
1. Compensate in **reverse order** of execution
2. Compensations must be **idempotent**
3. Handle "already compensated" gracefully
4. Log all compensation attempts

### Idempotency
1. Use idempotency keys for each step
2. Check for existing results before executing
3. Return existing result if found

### State Transitions
```
Pending → Running → Completed
              ↓
         Compensating → Failed
              ↓
         CompensationFailed
```

---

## Naming Conventions

| Component | Pattern | Example |
|-----------|---------|---------|
| State Enum | `SagaState` | `SagaState` |
| Step Interface | `SagaStepInterface` | `SagaStepInterface` |
| Abstract Step | `AbstractSagaStep` | `AbstractSagaStep` |
| Concrete Step | `{Action}Step` | `ReserveInventoryStep` |
| Orchestrator | `SagaOrchestrator` | `SagaOrchestrator` |
| Factory | `{Name}SagaFactory` | `OrderSagaFactory` |
| Test | `{ClassName}Test` | `SagaOrchestratorTest` |

---

## Quick Template Reference

### SagaStepInterface

```php
interface SagaStepInterface
{
    public function name(): string;
    public function execute(SagaContext $context): StepResult;
    public function compensate(SagaContext $context): StepResult;
    public function isIdempotent(): bool;
    public function timeout(): int;
}
```

### StepResult

```php
final readonly class StepResult
{
    public static function success(array $data = []): self;
    public static function failure(string $error): self;
    public function isSuccess(): bool;
    public function isFailure(): bool;
}
```

### Concrete Step Pattern

```php
final readonly class {Action}Step extends AbstractSagaStep
{
    public function name(): string
    {
        return '{action_name}';
    }

    public function execute(SagaContext $context): StepResult
    {
        $idempotencyKey = $this->idempotencyKey($context);

        // Check for existing result (idempotency)
        // Execute action
        // Return StepResult::success([...data...]) or failure
    }

    public function compensate(SagaContext $context): StepResult
    {
        // Get data from context
        // Undo action
        // Handle "already undone" gracefully
        return StepResult::success();
    }
}
```

---

## Usage Example

```php
// Create saga
$saga = $orderSagaFactory->create($command);

// Execute
$result = $saga->execute();

if ($result->isCompleted()) {
    // Success
} elseif ($result->isFailed()) {
    // Failed but compensated
    $error = $result->error;
} elseif ($result->isCompensationFailed()) {
    // Needs manual intervention
    $originalError = $result->error;
    $compensationError = $result->compensationError;
}
```

---

## DI Configuration

```yaml
# Symfony services.yaml
Domain\Shared\Saga\SagaStepInterface:
    tags: ['saga.step']

Application\Shared\Saga\SagaPersistenceInterface:
    alias: Infrastructure\Persistence\Doctrine\Repository\DoctrineSagaPersistence

Application\Order\Saga\OrderSagaFactory:
    arguments:
        $reserveStep: '@Application\Order\Saga\Step\ReserveInventoryStep'
        $chargeStep: '@Application\Order\Saga\Step\ChargePaymentStep'
        $shipStep: '@Application\Order\Saga\Step\CreateShipmentStep'
```

---

## Database Schema

```sql
CREATE TABLE sagas (
    id VARCHAR(255) PRIMARY KEY,
    type VARCHAR(255) NOT NULL,
    state VARCHAR(50) NOT NULL,
    completed_steps JSONB NOT NULL DEFAULT '[]',
    context JSONB NOT NULL,
    error TEXT,
    created_at TIMESTAMP(6) NOT NULL,
    updated_at TIMESTAMP(6) NOT NULL,
    completed_at TIMESTAMP(6)
);

CREATE INDEX idx_sagas_state ON sagas (state);
CREATE INDEX idx_sagas_type_state ON sagas (type, state);
```

---

## References

For complete PHP templates and test examples, see:
- `references/templates.md` — All component templates
- `references/examples.md` — Order saga example and unit tests

Related Skills

advanced-typescript-patterns

16
from diegosouzapw/awesome-omni-skill

Advanced TypeScript patterns for TMNL. Covers conditional types, mapped types, branded types, generic constraints, type inference, and utility type composition. Pure TypeScript patterns beyond Effect Schema.

Advanced GetX Patterns

16
from diegosouzapw/awesome-omni-skill

Advanced GetX features including Workers, GetxService, SmartManagement, GetConnect, GetSocket, bindings composition, and testing patterns

ActiveRecord Query Patterns

16
from diegosouzapw/awesome-omni-skill

Complete guide to ActiveRecord query optimization, associations, scopes, and PostgreSQL-specific patterns. Use this skill when writing database queries, designing model associations, creating migrations, optimizing query performance, or debugging N+1 queries and grouping errors.

actions-pattern

16
from diegosouzapw/awesome-omni-skill

Garante que novas Actions sigam o padrão de classes actions reutilizáveis do Easy Budget.

Action Pattern Conventions

16
from diegosouzapw/awesome-omni-skill

This skill should be used when the user asks about "Laravel action pattern", "action class naming", "how to structure actions", "React component patterns", "Node.js service structure", "framework-specific conventions", or discusses creating reusable, focused classes following action pattern conventions in Laravel, Symfony, React, Vue, or Node.js projects.

Action Cable & WebSocket Patterns

16
from diegosouzapw/awesome-omni-skill

Real-time WebSocket features with Action Cable in Rails. Use when: (1) Building real-time chat, (2) Live notifications/presence, (3) Broadcasting model updates, (4) WebSocket authorization. Trigger keywords: Action Cable, WebSocket, real-time, channels, broadcasting, stream, subscriptions, presence, cable

accessibility-patterns

16
from diegosouzapw/awesome-omni-skill

Build inclusive web experiences following WCAG guidelines. Covers semantic HTML, ARIA, keyboard navigation, color contrast, and testing strategies. Triggers on accessibility, a11y, WCAG, screen readers, or inclusive design requests.

acc-create-use-case

16
from diegosouzapw/awesome-omni-skill

Generates Application Use Cases for PHP 8.5. Creates orchestration services that coordinate domain objects, handle transactions, and dispatch events. Includes unit tests.

acc-create-state

16
from diegosouzapw/awesome-omni-skill

Generates State pattern for PHP 8.5. Creates state machines with context, state interface, and concrete states for behavior changes. Includes unit tests.

acc-create-retry-pattern

16
from diegosouzapw/awesome-omni-skill

Generates Retry pattern for PHP 8.5. Creates resilience component with exponential backoff, jitter, and configurable retry strategies. Includes unit tests.

acc-create-responder

16
from diegosouzapw/awesome-omni-skill

Generates ADR Responder classes for PHP 8.5. Creates HTTP response builders with PSR-7/PSR-17 support. Includes unit tests.

acc-create-repository

16
from diegosouzapw/awesome-omni-skill

Generates DDD Repository interfaces and implementation stubs for PHP 8.5. Creates domain interfaces in Domain layer, implementation in Infrastructure.