Search anything...
K
Back to Docs
  • Introduction
  • Quick Start
  • Account Setup
  • AI Studio
  • Chat
  • Agents
  • Voice
  • MCP Servers
  • Workflows
  • Authentication
  • Studio API
  • Chat API
  • Agents API
  • Voice API
  • Workflows API
  • Webhooks
  • Error Codes
  • Creating Custom Agents
  • MCP Integration
  • Building Workflows
  • Prompt Engineering
  • Team Management
  • Billing & Plans
  • Usage Monitoring
  • Single-Tenant Cloud
  • Private VPC Deployment
  • SSO Configuration
  • Security Policies
  • Compliance
  • Troubleshooting
  • API Versioning
DocsGuidesBuilding Workflows

Building Workflows

Create automated AI pipelines to streamline your tasks

This guide teaches you how to build powerful automated workflows that chain AI operations together. Learn to create pipelines for content generation, data processing, and complex multi-step tasks.

Understanding Workflows

What is a Workflow?

A workflow is a sequence of automated steps that process data:

Input → Step 1 → Step 2 → Step 3 → Output

Each step can:

  • Call AI models
  • Generate content
  • Transform data
  • Make API calls
  • Apply conditions

When to Use Workflows

Use CaseExample
Batch ProcessingGenerate descriptions for 100 products
Multi-Step TasksResearch → Outline → Write → Edit
Scheduled JobsDaily report generation
API IntegrationTrigger on webhook, return results
Complex PipelinesMulti-model content creation

Creating Your First Workflow

Step 1: Plan Your Workflow

Before building, map out:

  1. Input: What data starts the workflow?
  2. Steps: What operations are needed?
  3. Dependencies: Which steps depend on others?
  4. Output: What's the final result?

Example Planning:

Goal: Generate blog post from topic

Input: topic (string), tone (string)

Steps:
1. Generate outline from topic
2. Write introduction from outline
3. Write body sections from outline
4. Write conclusion
5. Combine all sections

Output: Complete blog post

Step 2: Create the Workflow

  1. Navigate to Workflows in the sidebar
  2. Click New Workflow
  3. Enter name and description:
    • Name: "Blog Post Generator"
    • Description: "Creates complete blog posts from topics"

Step 3: Define Inputs

Configure workflow inputs:

inputs:
  - name: topic
    type: string
    required: true
    description: "The blog post topic"

  - name: tone
    type: string
    required: false
    default: "professional"
    description: "Writing tone (professional, casual, technical)"

  - name: wordCount
    type: number
    required: false
    default: 1000
    description: "Target word count"

Step 4: Add Steps

Step 1: Generate Outline

step: generate_outline
type: ai_chat
config:
  model: gemini-2.0-flash
  temperature: 0.5
  prompt: |
    Create a detailed outline for a blog post about: {{input.topic}}

    Tone: {{input.tone}}
    Target length: {{input.wordCount}} words

    Include:
    - Compelling title
    - Introduction hook
    - 3-5 main sections with key points
    - Conclusion summary

    Format as structured markdown.

Step 2: Write Introduction

step: write_intro
type: ai_chat
depends_on: generate_outline
config:
  model: gemini-2.0-flash
  temperature: 0.7
  prompt: |
    Based on this outline:
    {{steps.generate_outline.output}}

    Write an engaging introduction (150-200 words) that:
    - Hooks the reader immediately
    - Introduces the topic
    - Previews what they'll learn

    Tone: {{input.tone}}

Step 3: Write Body

step: write_body
type: ai_chat
depends_on: generate_outline
config:
  model: gemini-1.5-pro
  temperature: 0.6
  prompt: |
    Based on this outline:
    {{steps.generate_outline.output}}

    Write the main body sections ({{input.wordCount * 0.7}} words).

    For each section:
    - Use clear subheadings
    - Include practical examples
    - Add relevant details

    Tone: {{input.tone}}

Step 4: Write Conclusion

step: write_conclusion
type: ai_chat
depends_on: [write_intro, write_body]
config:
  model: gemini-2.0-flash
  temperature: 0.6
  prompt: |
    Based on the introduction:
    {{steps.write_intro.output}}

    And body:
    {{steps.write_body.output}}

    Write a strong conclusion (100-150 words) that:
    - Summarizes key points
    - Provides a call to action
    - Leaves a lasting impression

Step 5: Combine

step: combine
type: transform
depends_on: [write_intro, write_body, write_conclusion]
config:
  template: |
    {{steps.write_intro.output}}

    {{steps.write_body.output}}

    {{steps.write_conclusion.output}}

Step 5: Test and Save

  1. Click Test Workflow
  2. Enter sample inputs:
    {
      "topic": "Remote Work Best Practices",
      "tone": "professional",
      "wordCount": 1000
    }
    
  3. Review the output
  4. Click Save

Workflow Patterns

Linear Pipeline

Steps execute in sequence:

[Input] → [Step 1] → [Step 2] → [Step 3] → [Output]

Use for: Simple transformations, content generation

Parallel Processing

Independent steps run simultaneously:

         ┌→ [Step 2a] ─┐
[Step 1] ├→ [Step 2b] ─┼→ [Step 3]
         └→ [Step 2c] ─┘

Use for: Multi-format output, independent generations

Conditional Branching

Different paths based on conditions:

           ┌→ [Path A] ─┐
[Step 1] ─┤             ├→ [Output]
           └→ [Path B] ─┘

Use for: Different handling based on input/results

Loop Processing

Iterate over items:

[Input List] → [Loop] → [Process Item] → [Collect Results]

Use for: Batch processing, list transformations


Step Types

AI Chat Step

Send a message to an AI model:

type: ai_chat
config:
  model: gemini-2.0-flash  # or gemini-1.5-pro
  temperature: 0.7
  systemPrompt: "You are a helpful assistant"
  prompt: "User message here"

Image Generation Step

Generate an image:

type: image_generation
config:
  model: flux-pro-1.1
  prompt: "Image description"
  aspectRatio: "16:9"
  quality: "high"

Transform Step

Modify data:

type: transform
config:
  template: "Combined: {{step1.output}} + {{step2.output}}"
  # Or use JavaScript expression
  expression: "steps.data.items.map(i => i.name).join(', ')"

HTTP Request Step

Call external APIs:

type: http_request
config:
  method: POST
  url: "https://api.example.com/webhook"
  headers:
    Authorization: "Bearer {{secrets.API_KEY}}"
    Content-Type: "application/json"
  body:
    data: "{{previousStep.output}}"

Condition Step

Branch based on logic:

type: condition
config:
  expression: "input.priority === 'high'"
  trueBranch: high_priority_step
  falseBranch: normal_step

Loop Step

Process arrays:

type: loop
config:
  items: "{{input.products}}"
  itemVariable: "product"
  step:
    type: ai_chat
    prompt: "Describe {{product.name}}"

Variables and Data Flow

Accessing Variables

SyntaxDescriptionExample
{{input.name}}Workflow input{{input.topic}}
{{steps.stepName.output}}Step output{{steps.outline.output}}
{{secrets.KEY}}Secret value{{secrets.API_KEY}}
{{loop.item}}Current loop item{{loop.item.name}}
{{loop.index}}Current loop index{{loop.index}}

Transform Expressions

Use JavaScript expressions for complex transformations:

# String manipulation
expression: "input.name.toUpperCase()"

# Array operations
expression: "steps.data.output.items.filter(i => i.active)"

# Conditional
expression: "input.premium ? 'VIP' : 'Standard'"

# JSON parsing
expression: "JSON.parse(steps.api.output).results"

Data Passing Best Practices

  1. Keep data minimal - Only pass what's needed
  2. Use clear names - Descriptive variable names
  3. Handle null - Check for missing data
  4. Format consistently - Standardize data formats

Workflow Examples

Product Description Generator

name: Product Description Generator
description: Generates product descriptions for e-commerce

inputs:
  - name: products
    type: array
    required: true
    description: Array of product objects

steps:
  - id: generate_descriptions
    type: loop
    config:
      items: "{{input.products}}"
      itemVariable: product
      step:
        type: ai_chat
        config:
          model: gemini-2.0-flash
          temperature: 0.7
          prompt: |
            Write a compelling product description for:

            Name: {{product.name}}
            Category: {{product.category}}
            Features: {{product.features}}
            Price: ${{product.price}}

            Include:
            - Attention-grabbing headline
            - Key benefits (not just features)
            - Call to action

  - id: format_output
    type: transform
    depends_on: generate_descriptions
    config:
      expression: |
        steps.generate_descriptions.output.map((desc, i) => ({
          productId: input.products[i].id,
          description: desc
        }))

Social Media Content Pipeline

name: Social Media Pipeline
description: Creates multi-platform content from a single brief

inputs:
  - name: brief
    type: string
    required: true
  - name: brand_voice
    type: string
    default: "friendly and professional"

steps:
  - id: core_message
    type: ai_chat
    config:
      prompt: |
        Extract the core marketing message from this brief:
        {{input.brief}}

        Brand voice: {{input.brand_voice}}

        Return a 1-2 sentence core message.

  - id: twitter_post
    type: ai_chat
    depends_on: core_message
    config:
      prompt: |
        Create a Twitter post (max 280 chars) for:
        {{steps.core_message.output}}

        Include relevant hashtags.

  - id: linkedin_post
    type: ai_chat
    depends_on: core_message
    config:
      prompt: |
        Create a LinkedIn post (300-500 words) for:
        {{steps.core_message.output}}

        Professional tone, include call to action.

  - id: instagram_caption
    type: ai_chat
    depends_on: core_message
    config:
      prompt: |
        Create an Instagram caption for:
        {{steps.core_message.output}}

        Engaging, include emojis, relevant hashtags.

  - id: compile_output
    type: transform
    depends_on: [twitter_post, linkedin_post, instagram_caption]
    config:
      template: |
        {
          "twitter": "{{steps.twitter_post.output}}",
          "linkedin": "{{steps.linkedin_post.output}}",
          "instagram": "{{steps.instagram_caption.output}}"
        }

Customer Support Auto-Response

name: Support Ticket Auto-Response
description: Automatically categorizes and responds to support tickets

inputs:
  - name: ticket
    type: object
    required: true
    # { subject, body, customerId }

steps:
  - id: categorize
    type: ai_chat
    config:
      temperature: 0.2
      prompt: |
        Categorize this support ticket:

        Subject: {{input.ticket.subject}}
        Body: {{input.ticket.body}}

        Categories: billing, technical, feature_request, general

        Return only the category name.

  - id: check_category
    type: condition
    depends_on: categorize
    config:
      expression: "steps.categorize.output.trim() === 'billing'"
      trueBranch: billing_response
      falseBranch: general_response

  - id: billing_response
    type: ai_chat
    config:
      systemPrompt: "You are a billing support specialist"
      prompt: |
        Write a helpful response to this billing inquiry:
        {{input.ticket.body}}

        Be empathetic and solution-focused.

  - id: general_response
    type: ai_chat
    config:
      systemPrompt: "You are a friendly support agent"
      prompt: |
        Write a helpful response to:
        {{input.ticket.body}}

        Category: {{steps.categorize.output}}

Execution and Monitoring

Triggering Workflows

Via API:

curl -X POST https://www.girardai.com/api/v1/workflows/{id}/execute \
  -H "Authorization: Bearer sk_live_xxx" \
  -d '{"inputs": {"topic": "AI"}}'

Via Webhook:

POST https://www.girardai.com/api/v1/webhooks/{workflowId}

Via Dashboard:

  1. Open workflow
  2. Click "Run"
  3. Enter inputs
  4. Execute

Monitoring Runs

Check execution status:

  1. Go to workflow Runs tab
  2. See all executions
  3. Click run for details:
    • Step-by-step progress
    • Inputs/outputs
    • Errors and logs
    • Duration

Handling Errors

Build in error handling:

steps:
  - id: risky_step
    type: http_request
    config:
      url: "{{input.apiUrl}}"
    onError:
      retry:
        attempts: 3
        delay: 1000
      fallback: error_handler_step

  - id: error_handler_step
    type: transform
    config:
      template: |
        {
          "success": false,
          "error": "API call failed",
          "fallbackData": "Default response"
        }

Best Practices

Performance

  1. Parallelize independent steps - Run together when possible
  2. Use appropriate models - Flash for speed, Pro for quality
  3. Limit data passing - Only pass necessary data
  4. Cache when possible - Avoid redundant operations

Reliability

  1. Add error handling - Retry and fallback logic
  2. Validate inputs - Check data before processing
  3. Log important steps - Debugging and auditing
  4. Test thoroughly - Cover edge cases

Maintainability

  1. Use clear names - Descriptive step IDs
  2. Add comments - Document complex logic
  3. Modularize - Break into smaller workflows
  4. Version control - Track changes

Previous: MCP Integration | Next: Prompt Engineering

Previous
MCP Integration
Next
Prompt Engineering