Skip to main content

Overview

The ValidateContent block validates text content against various rules like required substrings, forbidden words, length constraints, and regex patterns.
{
  "block": "ValidateContent",
  "input": {
    "from": "response.message",
    "as": "text"
  },
  "config": {
    "contains": ["hello", "world"]
  },
  "output": "validation"
}

Input Parameters

Required

ParameterTypeDescription
textstringThe text content to validate
Note: Use the from/as input format to map your data to the text parameter.

Configuration

All config parameters are optional. Use the ones relevant to your validation:
ParameterTypeDescription
containsstring/arrayRequired substring(s) - case insensitive
notContainsstring/arrayForbidden substring(s) - case insensitive
minLengthnumberMinimum text length
maxLengthnumberMaximum text length
matchesstringRegex pattern the text must match
matchFlagsstringRegex flags (default: 'i' for case-insensitive)

Output Fields

FieldTypeDescription
passedbooleanWhether all validations passed
failuresarrayList of validation failures
scorenumberValidation score (0.0 - 1.0)
checksobjectIndividual check results

Examples

Validate Required Keywords

{
  "block": "ValidateContent",
  "input": {
    "from": "aiResponse.message",
    "as": "text"
  },
  "config": {
    "contains": ["appointment", "time"]
  },
  "output": "validation"
}
Success:
{
  passed: true,
  failures: [],
  score: 1.0,
  checks: {
    contains_appointment: true,
    contains_time: true
  }
}
Failure:
{
  passed: false,
  failures: ["Missing expected content: time"],
  score: 0.5,
  checks: {
    contains_appointment: true,
    contains_time: false
  }
}

Forbid Inappropriate Content

{
  "block": "ValidateContent",
  "input": {
    "from": "userInput.comment",
    "as": "text"
  },
  "config": {
    "notContains": ["spam", "offensive", "inappropriate"]
  },
  "output": "validation"
}

Validate Text Length

{
  "block": "ValidateContent",
  "input": {
    "from": "user.bio",
    "as": "text"
  },
  "config": {
    "minLength": 10,
    "maxLength": 500
  },
  "output": "validation"
}

Regex Pattern Matching

{
  "block": "ValidateContent",
  "input": {
    "from": "user.email",
    "as": "text"
  },
  "config": {
    "matches": "^[\\w.-]+@[\\w.-]+\\.\\w+$"
  },
  "output": "emailValidation"
}

Combined Validations

{
  "block": "ValidateContent",
  "input": {
    "from": "aiResponse.message",
    "as": "text"
  },
  "config": {
    "contains": ["meeting", "time"],
    "notContains": ["error", "failed"],
    "minLength": 20,
    "maxLength": 500,
    "matches": "\\d{1,2}:\\d{2}"
  },
  "output": "validation"
}

Common Patterns

Validate AI Response Quality

{
  "pipeline": [
    {
      "block": "HttpRequest",
      "input": {
        "url": "${AI_API_URL}/chat",
        "method": "POST",
        "body": {
          "message": "What time is the meeting?"
        }
      },
      "output": "response"
    },
    {
      "block": "JsonParser",
      "input": "${response.body}",
      "output": { "parsed": "aiResponse" }
    },
    {
      "block": "ValidateContent",
      "input": {
        "from": "aiResponse.message",
        "as": "text"
      },
      "config": {
        "contains": ["meeting", "time"],
        "minLength": 10
      },
      "output": "validation"
    }
  ],
  "assertions": {
    "validation.passed": true
  }
}

Multi-Field Validation

{
  "pipeline": [
    {
      "block": "MockData",
      "config": {
        "data": {
          "name": "John Doe",
          "email": "john@example.com",
          "bio": "Software engineer"
        }
      },
      "output": "user"
    },
    {
      "id": "validate-name",
      "block": "ValidateContent",
      "input": {
        "from": "user.name",
        "as": "text"
      },
      "config": {
        "minLength": 2,
        "maxLength": 100
      },
      "output": "nameValidation"
    },
    {
      "id": "validate-email",
      "block": "ValidateContent",
      "input": {
        "from": "user.email",
        "as": "text"
      },
      "config": {
        "matches": ".*@.*\\..*"
      },
      "output": "emailValidation"
    },
    {
      "id": "validate-bio",
      "block": "ValidateContent",
      "input": {
        "from": "user.bio",
        "as": "text"
      },
      "config": {
        "minLength": 10
      },
      "output": "bioValidation"
    }
  ],
  "assertions": {
    "nameValidation.passed": true,
    "emailValidation.passed": true,
    "bioValidation.passed": true
  }
}

Content Safety Check

{
  "block": "ValidateContent",
  "input": {
    "from": "userComment.text",
    "as": "text"
  },
  "config": {
    "notContains": [
      "spam",
      "offensive",
      "inappropriate",
      "abuse"
    ],
    "minLength": 5,
    "maxLength": 10000
  },
  "output": "safetyCheck"
}

Validation Score

The score field represents how well the content passed validation:
  • 1.0 - All validations passed
  • 0.5 - Some validations failed
  • < 0.5 - Multiple validations failed
The score is calculated based on:
  • Missing required content
  • Forbidden content found
  • Length violations
  • Pattern mismatches
Use the score for assertions:
{
  "assertions": {
    "validation.score": { "gt": 0.8 }
  }
}

Error Messages

Common failure messages:
MessageCause
Missing expected content: wordRequired substring not found
Found forbidden content: wordForbidden substring found
Text too short: 5 < 10Below minLength
Text too long: 600 > 500Above maxLength
Text doesn't match pattern: regexRegex pattern didn’t match

Full Example

{
  "name": "Content Validation Test",
  "context": {
    "AI_API_URL": "${env.AI_API_URL}"
  },
  "tests": [{
    "id": "validate-ai-response",
    "pipeline": [
      {
        "id": "call-ai",
        "block": "HttpRequest",
        "input": {
          "url": "${AI_API_URL}/chat",
          "method": "POST",
          "headers": {
            "Authorization": "Bearer ${env.API_KEY}"
          },
          "body": {
            "messages": [{
              "role": "user",
              "content": "Schedule a meeting for tomorrow at 2pm"
            }]
          }
        },
        "output": "response"
      },
      {
        "id": "parse",
        "block": "JsonParser",
        "input": "${response.body}",
        "output": {
          "parsed": "aiResponse"
        }
      },
      {
        "id": "validate-response",
        "block": "ValidateContent",
        "input": {
          "from": "aiResponse.message",
          "as": "text"
        },
        "config": {
          "contains": ["meeting", "tomorrow", "2pm"],
          "notContains": ["error", "sorry", "cannot"],
          "minLength": 20,
          "maxLength": 500
        },
        "output": "validation"
      }
    ],
    "assertions": {
      "response.status": 200,
      "validation.passed": true,
      "validation.score": { "gt": 0.9 }
    }
  }]
}

Tips

ValidateContent expects a text parameter. Use the from/as format:
{
  "input": {
    "from": "response.message",
    "as": "text"
  }
}
The contains and notContains checks are case-insensitive:
{
  "config": {
    "contains": "hello"
  }
}
// Matches: "Hello", "HELLO", "hello"
Use ValidateContent for structural checks, LLMJudge for semantic validation:
{
  "pipeline": [
    {
      "block": "ValidateContent",
      "input": { "from": "response.text", "as": "text" },
      "config": { "minLength": 10, "contains": "meeting" },
      "output": "structureCheck"
    },
    {
      "block": "LLMJudge",
      "input": {
        "text": "${response.text}",
        "expected": { "expectedBehavior": "Professional tone" }
      },
      "output": "semanticCheck"
    }
  ]
}
Regex patterns are powerful for complex validation:
{
  "config": {
    "matches": "^Meeting at \\d{1,2}(am|pm)$"
  }
}

When to Use

Use ValidateContent when:
  • Checking for required keywords
  • Filtering inappropriate content
  • Validating text length
  • Pattern matching (emails, URLs, etc.)
  • Structural content validation
Use LLMJudge instead when:
  • Checking semantic meaning
  • Evaluating tone or style
  • Comparing similarity to expected content
  • Complex reasoning about content

Next Steps

I