{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "$id": "https://docs.nylorun.com/schemas/agent-folder/v1/flow.json",
  "title": "Nylorun agent folder: flow.json",
  "description": "A flow's node tree (workflow manifest v3's), naming agents of the flow root's agents/ by id and tools beside the file by name",
  "oneOf": [
    {
      "type": "object",
      "properties": {
        "$schema": {
          "type": "string",
          "description": "This file's JSON Schema, for editors; the compiler leaves it out of the manifest"
        },
        "agent": {
          "type": "string",
          "minLength": 1,
          "description": "An agent of the flow root's agents/, by its id"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "agent"
      ],
      "additionalProperties": false
    },
    {
      "type": "object",
      "properties": {
        "$schema": {
          "type": "string",
          "description": "This file's JSON Schema, for editors; the compiler leaves it out of the manifest"
        },
        "tool": {
          "type": "string",
          "minLength": 1,
          "description": "A tool of tools/ beside this flow.json, by its name (tools/<name>.json)"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "tool"
      ],
      "additionalProperties": false
    },
    {
      "type": "object",
      "properties": {
        "$schema": {
          "type": "string",
          "description": "This file's JSON Schema, for editors; the compiler leaves it out of the manifest"
        },
        "chain": {
          "type": "array",
          "items": {
            "$ref": "#/$defs/Node"
          },
          "minItems": 1,
          "description": "Nodes run in order, each given the one before's output"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "chain"
      ],
      "additionalProperties": false
    },
    {
      "type": "object",
      "properties": {
        "$schema": {
          "type": "string",
          "description": "This file's JSON Schema, for editors; the compiler leaves it out of the manifest"
        },
        "switch": {
          "type": "object",
          "properties": {
            "cases": {
              "type": "object",
              "additionalProperties": {
                "$ref": "#/$defs/Node"
              },
              "description": "The node each route runs, by route"
            },
            "default": {
              "$ref": "#/$defs/Node",
              "description": "The node that runs when no route matches"
            }
          },
          "required": [
            "cases"
          ],
          "additionalProperties": false,
          "description": "Runs the node of the route the input names"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "switch"
      ],
      "additionalProperties": false
    },
    {
      "type": "object",
      "properties": {
        "$schema": {
          "type": "string",
          "description": "This file's JSON Schema, for editors; the compiler leaves it out of the manifest"
        },
        "parallel": {
          "type": "object",
          "additionalProperties": {
            "$ref": "#/$defs/Node"
          },
          "minProperties": 1,
          "description": "Runs each branch's node at once, by branch name"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "parallel"
      ],
      "additionalProperties": false
    },
    {
      "type": "object",
      "properties": {
        "$schema": {
          "type": "string",
          "description": "This file's JSON Schema, for editors; the compiler leaves it out of the manifest"
        },
        "map": {
          "type": "object",
          "properties": {
            "each": {
              "$ref": "#/$defs/Node"
            }
          },
          "required": [
            "each"
          ],
          "additionalProperties": false,
          "description": "Runs the node once per item of its input"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "map"
      ],
      "additionalProperties": false
    },
    {
      "type": "object",
      "properties": {
        "$schema": {
          "type": "string",
          "description": "This file's JSON Schema, for editors; the compiler leaves it out of the manifest"
        },
        "loop": {
          "type": "object",
          "properties": {
            "run": {
              "$ref": "#/$defs/Node",
              "description": "The node each attempt runs"
            },
            "verify": {
              "$ref": "#/$defs/Verifier"
            },
            "max": {
              "type": "integer",
              "minimum": 1,
              "description": "The most attempts the loop makes"
            }
          },
          "required": [
            "run",
            "verify",
            "max"
          ],
          "additionalProperties": false,
          "description": "Runs a node until verify passes it, up to max attempts"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "loop"
      ],
      "additionalProperties": false
    }
  ],
  "$defs": {
    "Node": {
      "oneOf": [
        {
          "$ref": "#/$defs/AgentNode"
        },
        {
          "$ref": "#/$defs/ToolNode"
        },
        {
          "$ref": "#/$defs/ChainNode"
        },
        {
          "$ref": "#/$defs/SwitchNode"
        },
        {
          "$ref": "#/$defs/ParallelNode"
        },
        {
          "$ref": "#/$defs/MapNode"
        },
        {
          "$ref": "#/$defs/LoopNode"
        }
      ],
      "description": "A node: exactly one of agent, tool, chain, switch, parallel, map, loop, and an optional id"
    },
    "AgentNode": {
      "type": "object",
      "properties": {
        "agent": {
          "type": "string",
          "minLength": 1,
          "description": "An agent of the flow root's agents/, by its id"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "agent"
      ],
      "additionalProperties": false
    },
    "ToolNode": {
      "type": "object",
      "properties": {
        "tool": {
          "type": "string",
          "minLength": 1,
          "description": "A tool of tools/ beside this flow.json, by its name (tools/<name>.json)"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "tool"
      ],
      "additionalProperties": false
    },
    "ChainNode": {
      "type": "object",
      "properties": {
        "chain": {
          "type": "array",
          "items": {
            "$ref": "#/$defs/Node"
          },
          "minItems": 1,
          "description": "Nodes run in order, each given the one before's output"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "chain"
      ],
      "additionalProperties": false
    },
    "SwitchNode": {
      "type": "object",
      "properties": {
        "switch": {
          "type": "object",
          "properties": {
            "cases": {
              "type": "object",
              "additionalProperties": {
                "$ref": "#/$defs/Node"
              },
              "description": "The node each route runs, by route"
            },
            "default": {
              "$ref": "#/$defs/Node",
              "description": "The node that runs when no route matches"
            }
          },
          "required": [
            "cases"
          ],
          "additionalProperties": false,
          "description": "Runs the node of the route the input names"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "switch"
      ],
      "additionalProperties": false
    },
    "ParallelNode": {
      "type": "object",
      "properties": {
        "parallel": {
          "type": "object",
          "additionalProperties": {
            "$ref": "#/$defs/Node"
          },
          "minProperties": 1,
          "description": "Runs each branch's node at once, by branch name"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "parallel"
      ],
      "additionalProperties": false
    },
    "MapNode": {
      "type": "object",
      "properties": {
        "map": {
          "type": "object",
          "properties": {
            "each": {
              "$ref": "#/$defs/Node"
            }
          },
          "required": [
            "each"
          ],
          "additionalProperties": false,
          "description": "Runs the node once per item of its input"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "map"
      ],
      "additionalProperties": false
    },
    "LoopNode": {
      "type": "object",
      "properties": {
        "loop": {
          "type": "object",
          "properties": {
            "run": {
              "$ref": "#/$defs/Node",
              "description": "The node each attempt runs"
            },
            "verify": {
              "$ref": "#/$defs/Verifier"
            },
            "max": {
              "type": "integer",
              "minimum": 1,
              "description": "The most attempts the loop makes"
            }
          },
          "required": [
            "run",
            "verify",
            "max"
          ],
          "additionalProperties": false,
          "description": "Runs a node until verify passes it, up to max attempts"
        },
        "id": {
          "type": "string",
          "minLength": 1,
          "description": "The node's id, which names its step in a run"
        }
      },
      "required": [
        "loop"
      ],
      "additionalProperties": false
    },
    "Verifier": {
      "oneOf": [
        {
          "type": "object",
          "properties": {
            "agent": {
              "type": "string",
              "minLength": 1,
              "description": "An agent of the flow root's agents/, by its id, that judges each attempt"
            },
            "id": {
              "type": "string",
              "minLength": 1,
              "description": "The node's id, which names its step in a run"
            }
          },
          "required": [
            "agent"
          ],
          "additionalProperties": false
        },
        {
          "type": "object",
          "properties": {
            "tool": {
              "type": "string",
              "minLength": 1,
              "description": "A tool of tools/ beside this flow.json, by its name, that judges each attempt"
            }
          },
          "required": [
            "tool"
          ],
          "additionalProperties": false
        }
      ],
      "description": "What judges each attempt: an agent, or an HTTP tool"
    }
  }
}
