anyOf — Accept Multiple Schema Alternatives

Use anyOf in JSON Schema to accept values matching one or more schemas. Learn the difference between anyOf, oneOf, and allOf for flexible validation.

Composition

JSON Schema

{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "contact": {
      "anyOf": [
        {
          "type": "object",
          "properties": {
            "email": { "type": "string", "format": "email" }
          },
          "required": ["email"]
        },
        {
          "type": "object",
          "properties": {
            "phone": { "type": "string", "pattern": "^\\+[1-9]\\d{6,14}$" }
          },
          "required": ["phone"]
        }
      ]
    },
    "identifier": {
      "anyOf": [
        { "type": "string", "format": "email" },
        { "type": "string", "pattern": "^[a-zA-Z0-9_]{3,30}$" },
        { "type": "integer", "minimum": 1 }
      ]
    }
  },
  "required": ["contact"]
}

Test Data

{
  "contact": {
    "email": "alice@example.com",
    "phone": "+14155551234"
  },
  "identifier": "alice_dev"
}

Detailed Explanation

anyOf — Accept One or More Matching Schemas

The anyOf keyword validates that a value matches at least one of the provided sub-schemas. If the value satisfies one schema, two schemas, or all of them, it passes. It only fails if the value matches none of the schemas.

Basic Syntax

{
  "anyOf": [
    { "type": "string" },
    { "type": "integer" }
  ]
}

This accepts strings and integers. The value "hello" matches the first schema, 42 matches the second, and both pass validation.

How the Example Schema Works

The schema uses anyOf in two fields:

  1. contact — must match at least one of two object schemas: one requiring email, the other requiring phone. The test data has both fields, which satisfies both sub-schemas. But {"email": "alice@example.com"} alone (without phone) would also pass, because it matches at least one sub-schema.

  2. identifier — accepts an email, a username pattern, or a positive integer. The value "alice_dev" matches the username pattern (alphanumeric with underscores, 3-30 characters). But "alice@example.com" would also pass (matching the email format), and 42 would pass (matching the integer schema).

anyOf vs. oneOf vs. allOf

Keyword Meaning Passes when
anyOf At least one match 1+ schemas match
oneOf Exactly one match Exactly 1 schema matches
allOf All must match Every schema matches

The critical difference between anyOf and oneOf is what happens when multiple schemas match:

  • anyOf — multiple matches are fine (logical OR with short-circuit).
  • oneOf — multiple matches cause failure (exclusive OR).

When to Choose anyOf

Use anyOf when:

  • You want to accept multiple formats and do not care about ambiguity.
  • The schemas are not mutually exclusive (e.g., a contact that has both email and phone).
  • You want the simplest, most permissive composition behavior.

Avoid anyOf when:

  • You need to guarantee exactly one schema matches (use oneOf).
  • You want to combine constraints that all apply simultaneously (use allOf).

Error Messages

One downside of anyOf is that error messages can be confusing. When validation fails, the validator reports errors from every sub-schema (since all of them failed). This produces multiple error messages that can be hard for end users to interpret. Some validators provide a summary like "value did not match any of the 3 alternatives."

Use Case

Use anyOf for flexible contact forms (accept email or phone), polymorphic API fields (accept string ID or integer ID), and content types that have multiple valid representations. It is the most forgiving composition keyword and works well when you want to accept multiple formats without strict mutual exclusivity.

Try It — JSON Schema Validator

Open full tool