Mandala

Loop Block YAML Schema

YAML-Konfigurationsreferenz für Loop-Blöcke

Schema-Definition

type: object
required:
  - type
  - name
  - connections
properties:
  type:
    type: string
    enum: [loop]
    description: Block type identifier
  name:
    type: string
    description: Display name for this loop block
  inputs:
    type: object
    description: Optional. If omitted, defaults will be applied.
    properties:
      loopType:
        type: string
        enum: [for, forEach]
        description: Type of loop to execute
        default: for
      iterations:
        type: number
        description: Number of iterations (for 'for' loops)
        default: 5
        minimum: 1
        maximum: 1000
      collection:
        type: string
        description: Collection to iterate over (for 'forEach' loops)
        default: ""
      maxConcurrency:
        type: number
        description: Maximum concurrent executions
        default: 1
        minimum: 1
        maximum: 10
  connections:
    type: object
    properties:
      # Nested format (recommended)
      loop:
        type: object
        properties:
          start:
            type: string
            description: Target block ID to execute inside the loop
          end:
            type: string
            description: Target block ID for loop completion (optional)
      # Direct handle format (alternative)
      loop-start-source:
        type: string | string[]
        description: Target block ID to execute inside the loop (direct format)
      loop-end-source:
        type: string | string[]
        description: Target block ID for loop completion (direct format, optional)
      error:
        type: string
        description: Target block ID for error handling
    note: Use either the nested 'loop' format OR the direct 'loop-start-source' format, not both

Verbindungskonfiguration

Loop-Blöcke unterstützen zwei Verbindungsformate:

Direktes Handle-Format (Alternative)

connections:
  loop-start-source: <string>           # Target block ID to execute inside the loop
  loop-end-source: <string>             # Target block ID after loop completion (optional)
  error: <string>                       # Target block ID for error handling (optional)

Beide Formate funktionieren identisch. Verwenden Sie das Format, das Ihnen besser gefällt.

Konfiguration von untergeordneten Blöcken

Blöcke innerhalb einer Schleife müssen ihre parentId auf die Loop-Block-ID gesetzt haben. Die Eigenschaft extent wird automatisch auf 'parent' gesetzt und muss nicht angegeben werden:

loop-1:
  type: loop
  name: "Process Items"
  inputs:
    loopType: forEach
    collection: <start.items>
  connections:
    loop:
      start: process-item
      end: final-results

# Child block inside the loop
process-item:
  type: agent
  name: "Process Item"
  parentId: loop-1                      # References the loop block
  inputs:
    systemPrompt: "Process this item"
    userPrompt: <loop.currentItem>
    model: gpt-4o
    apiKey: '{{OPENAI_API_KEY}}'

Beispiele

For-Schleife (feste Anzahl von Iterationen)

countdown-loop:
  type: loop
  name: "Countdown Loop"
  inputs:
    loopType: for
    iterations: 5
  connections:
    loop:
      start: countdown-agent
      end: countdown-complete

countdown-agent:
  type: agent
  name: "Countdown Agent"
  parentId: countdown-loop
  inputs:
    systemPrompt: "Generate a countdown message"
    userPrompt: "Count down from 5. Current number: <loop.index>"
    model: gpt-4o
    apiKey: '{{OPENAI_API_KEY}}'

ForEach-Schleife (Verarbeitung von Sammlungen)

email-processor-loop:
  type: loop
  name: "Email Processor Loop"
  inputs:
    loopType: forEach
    collection: <start.emails>
  connections:
    loop:
      start: process-single-email
      end: all-emails-processed

process-single-email:
  type: agent
  name: "Process Single Email"
  parentId: email-processor-loop
  inputs:
    systemPrompt: "Classify and respond to this email"
    userPrompt: "Email content: <loop.currentItem>"
    model: gpt-4o
    apiKey: '{{OPENAI_API_KEY}}'

Schleife mit mehreren untergeordneten Blöcken

data-analysis-loop:
  type: loop
  name: "Data Analysis Loop"
  inputs:
    loopType: forEach
    collection: <data-fetcher.records>
    maxConcurrency: 3
  connections:
    loop:
      start: validate-record
      end: generate-report
    error: handle-loop-error

validate-record:
  type: function
  name: "Validate Record"
  parentId: data-analysis-loop
  inputs:
    code: |
      const record = <loop.currentItem>;
      const index = <loop.index>;
      
      // Validate the record
      if (!record.id || !record.data) {
        throw new Error(`Invalid record at index ${index}`);
      }
      
      return {
        valid: true,
        recordId: record.id,
        processedAt: new Date().toISOString()
      };
  connections:
    success: analyze-record
    error: record-error

analyze-record:
  type: agent
  name: "Analyze Record"
  parentId: data-analysis-loop
  inputs:
    systemPrompt: "Analyze this data record and extract insights"
    userPrompt: |
      Record ID: <validaterecord.recordId>
      Data: <loop.currentItem.data>
      Position in collection: <loop.index>
    model: gpt-4o
    apiKey: '{{OPENAI_API_KEY}}'
  connections:
    success: store-analysis

store-analysis:
  type: function
  name: "Store Analysis"
  parentId: data-analysis-loop
  inputs:
    code: |
      const analysis = <analyzerecord.content>;
      const recordId = <validaterecord.recordId>;
      
      // Store analysis result
      return {
        recordId,
        analysis,
        completedAt: new Date().toISOString()
      };

Schleife für parallele Verarbeitung

parallel-processing-loop:
  type: loop
  name: "Parallel Processing Loop"
  inputs:
    loopType: forEach
    collection: <start.tasks>
    maxConcurrency: 5
  connections:
    loop:
      start: process-task
      end: aggregate-results

process-task:
  type: api
  name: "Process Task"
  parentId: parallel-processing-loop
  inputs:
    url: "https://api.example.com/process"
    method: POST
    headers:
      - key: "Authorization"
        value: "Bearer {{API_TOKEN}}"
    body: |
      {
        "taskId": "<loop.currentItem.id>",
        "data": "<loop.currentItem.data>"
      }
  connections:
    success: task-completed

Beispiel für direktes Handle-Format

Dieselbe Schleife kann mit dem direkten Handle-Format geschrieben werden:

my-loop:
  type: loop
  name: "Process Items"
  inputs:
    loopType: forEach
    collection: <start.items>
  connections:
    loop-start-source: process-item      # Direct handle format
    loop-end-source: final-results       # Direct handle format
    error: handle-error

process-item:
  type: agent
  name: "Process Item"
  parentId: my-loop
  inputs:
    systemPrompt: "Process this item"
    userPrompt: <loop.currentItem>
    model: gpt-4o
    apiKey: '{{OPENAI_API_KEY}}'

Minimales Schleifenbeispiel (mit Standardwerten)

Sie können den Abschnitt inputs vollständig weglassen, dann werden Standardwerte angewendet:

simple-loop:
  type: loop
  name: "Simple Loop"
  # No inputs section - defaults to loopType: 'for', iterations: 5
  connections:
    loop-start-source: process-step
    loop-end-source: complete

process-step:
  type: agent
  name: "Process Step"
  parentId: simple-loop
  inputs:
    systemPrompt: "Execute step"
    userPrompt: "Step <loop.index>"
    model: gpt-4o
    apiKey: '{{OPENAI_API_KEY}}'

Diese Schleife führt standardmäßig 5 Iterationen aus.

Schleifenvariablen

Innerhalb von Schleifenunterblöcken sind diese speziellen Variablen verfügbar:

# Available in all child blocks of the loop
<loop.index>                    # Current iteration number (0-based)
<loop.currentItem>              # Current item being processed (forEach loops)
<loop.items>                    # Full collection (forEach loops)

Ausgabereferenzen

Nach Abschluss einer Schleife können Sie auf ihre aggregierten Ergebnisse verweisen:

# In blocks after the loop
final-processor:
  inputs:
    all-results: <loop-name.results>    # Array of all iteration results
    total-count: <loop-name.count>      # Number of iterations completed

Bewährte Praktiken

  • Setzen Sie angemessene Iterationsgrenzen, um lange Ausführungszeiten zu vermeiden
  • Verwenden Sie forEach für die Verarbeitung von Sammlungen, for-Schleifen für feste Iterationen
  • Erwägen Sie die Verwendung von maxConcurrency für I/O-gebundene Operationen
  • Integrieren Sie Fehlerbehandlung für eine robuste Schleifenausführung
  • Verwenden Sie aussagekräftige Namen für Schleifenunterblöcke
  • Testen Sie zuerst mit kleinen Sammlungen
  • Überwachen Sie die Ausführungszeit für große Sammlungen
Loop Block YAML Schema