{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "$id": "https://artifacts.apis.io/atako-ai/json-schema/atako-ai-create-agent-body-schema.json",
  "title": "CreateAgentBody",
  "x-generated": "2026-11-01",
  "x-method": "derived",
  "x-generator": "derive-json-schema.py",
  "x-source": "openapi/_original/atako-ai-api-openapi.json#/components/schemas/CreateAgentBody",
  "type": "object",
  "required": [
    "name",
    "image"
  ],
  "properties": {
    "name": {
      "type": "string",
      "minLength": 1
    },
    "image": {
      "type": "string",
      "description": "PNG filename under apps/web/public/aiygents/."
    },
    "finish": {
      "type": [
        "string",
        "null"
      ],
      "enum": [
        "carbone",
        "chrome-studio",
        "titane",
        "candy",
        "nacre-ormeau",
        "velours",
        "ceramique",
        "marbre",
        "terrazzo",
        "cuir",
        "jade",
        "maille",
        "mercure",
        "lave",
        "eau",
        "glace",
        "malachite",
        "labradorite",
        "calacatta",
        "noyer",
        "soie",
        "ecailles"
      ],
      "description": "The 3D body finish (the user-facing « skin »). Absent or null = carbone; unknown → 400 FINISH_INVALID."
    },
    "mission": {
      "type": [
        "string",
        "null"
      ],
      "maxLength": 20000,
      "description": "The agent's mission in 1–3 sentences, trimmed."
    },
    "systemPrompt": {
      "type": [
        "string",
        "null"
      ],
      "maxLength": 20000,
      "description": "Free-text agent instructions, trimmed. Stored and sent to the orchestrator as-is (no business context appended)."
    },
    "clientContext": {
      "type": [
        "string",
        "null"
      ],
      "maxLength": 20000,
      "description": "Free-text per-agent business context, trimmed. Kept in its own column."
    },
    "modelId": {
      "type": "string",
      "description": "Either an `ai_models` UUID (from GET /models or `aiModelId` in GET /models/catalog) or a raw OpenRouter slug (`slug` in GET /models/catalog, e.g. \"mistralai/mistral-small\"). A slug unknown to the catalog is rejected with 400. Omitted → admin-declared default model. With a direct-provider BYOK key (openai/anthropic), this is instead the provider's own model id."
    },
    "harnessId": {
      "type": "string",
      "format": "uuid",
      "description": "From GET /harnesses."
    },
    "teamId": {
      "type": [
        "string",
        "null"
      ],
      "format": "uuid",
      "description": "Assigns the agent to a shared team instead of keeping it personal."
    },
    "modelConfig": {
      "type": "object",
      "description": "Per-task-type model overrides, forwarded to the orchestrator webhook.",
      "properties": {
        "vision": {
          "type": [
            "string",
            "null"
          ]
        },
        "low_effort": {
          "type": [
            "string",
            "null"
          ]
        },
        "medium_effort": {
          "type": [
            "string",
            "null"
          ]
        },
        "high_effort": {
          "type": [
            "string",
            "null"
          ]
        }
      }
    },
    "engine": {
      "type": "string",
      "enum": [
        "openclaw",
        "hermes",
        "opencode"
      ],
      "description": "Defaults to the platform default engine (hermes). `opencode` additionally requires `allowedRepos`."
    },
    "allowedRepos": {
      "type": "array",
      "items": {
        "type": "string"
      },
      "description": "Repositories (`owner/repo`) the agent may work on. REQUIRED (≥1) for `engine: opencode`, which also requires an active company GitHub connection; ignored by the other engines."
    },
    "llmKeyId": {
      "type": "string",
      "format": "uuid",
      "description": "BYOK: id of a company LLM provider key (see docs — BYOK key management is not part of this customer API cut)."
    }
  }
}