{
  "openapi": "3.0.3",
  "info": {
    "title": "Jaybird Digital website start",
    "version": "1.0.0",
    "description": "Start a website for a person with no account, save its pages, and give them the address to view it and the link to keep it. The same operations are available as an MCP server at https://jaybirddigital.com/api/start/mcp."
  },
  "servers": [{ "url": "https://jaybirddigital.com" }],
  "paths": {
    "/api/start/websites": {
      "post": {
        "operationId": "startWebsite",
        "summary": "Start a website",
        "requestBody": {
          "required": true,
          "content": { "application/json": { "schema": {
            "type": "object", "additionalProperties": false, "required": ["businessName"],
            "properties": {
              "businessName": { "type": "string", "minLength": 1, "maxLength": 100 },
              "about": { "type": "string", "maxLength": 400 }
            }
          } } }
        },
        "responses": { "201": { "description": "Started. Returns websiteId, editKey, viewUrl, keepUrl, the rules pages follow, and limits." }, "429": { "description": "Too many websites started." } }
      }
    },
    "/api/start/domains": {
      "get": {
        "operationId": "searchDomains",
        "summary": "Look up which domain names are available",
        "parameters": [{ "name": "query", "in": "query", "required": true, "schema": { "type": "string", "minLength": 2, "maxLength": 100 } }],
        "responses": { "200": { "description": "The names found, whether each is available, and what it costs." }, "429": { "description": "Too many requests." }, "503": { "description": "Search is not available right now." } }
      }
    },
    "/api/start/websites/{websiteId}": {
      "parameters": [{ "$ref": "#/components/parameters/websiteId" }],
      "get": {
        "operationId": "getWebsite",
        "summary": "Read a website's state",
        "responses": { "200": { "description": "Its name, state, address, pages and any rule problems." }, "404": { "description": "No such website." } }
      },
      "delete": {
        "operationId": "deleteWebsite",
        "summary": "Permanently remove a website",
        "security": [{ "editKey": [] }],
        "responses": { "200": { "description": "It is gone." }, "404": { "description": "No website has that id and key." }, "409": { "description": "It has a plan, so it is removed from its owner's dashboard." } }
      }
    },
    "/api/start/websites/{websiteId}/files": {
      "parameters": [{ "$ref": "#/components/parameters/websiteId" }],
      "put": {
        "operationId": "saveWebsiteFiles",
        "summary": "Save or replace files, and check them against the rules",
        "security": [{ "editKey": [] }],
        "requestBody": {
          "required": true,
          "content": { "application/json": { "schema": {
            "type": "object", "additionalProperties": false, "required": ["files"],
            "properties": { "files": { "type": "array", "minItems": 1, "maxItems": 40, "items": {
              "type": "object", "additionalProperties": false, "required": ["path", "content"],
              "properties": {
                "path": { "type": "string", "maxLength": 200 },
                "content": { "type": "string" },
                "encoding": { "type": "string", "enum": ["utf8", "base64"] }
              }
            } } }
          } } }
        },
        "responses": { "200": { "description": "Saved. Returns the address, pages and any rule problems." }, "404": { "description": "No website has that id and key." }, "413": { "description": "Over a limit." } }
      }
    },
    "/api/start/websites/{websiteId}/file": {
      "parameters": [
        { "$ref": "#/components/parameters/websiteId" },
        { "name": "path", "in": "query", "required": true, "schema": { "type": "string", "minLength": 1, "maxLength": 200, "pattern": "^[a-z0-9][a-z0-9._/-]*$" } }
      ],
      "get": {
        "operationId": "readWebsiteFile",
        "summary": "Read one saved file",
        "security": [{ "editKey": [] }],
        "responses": { "200": { "description": "The file." }, "404": { "description": "No such file." } }
      },
      "delete": {
        "operationId": "deleteWebsiteFile",
        "summary": "Remove one saved file",
        "security": [{ "editKey": [] }],
        "responses": { "200": { "description": "Removed." }, "404": { "description": "No such file." } }
      }
    },
    "/api/start/mcp": {
      "post": {
        "operationId": "mcp",
        "summary": "The same operations as an MCP server",
        "description": "Signing in is optional. An access token from this site's OAuth sign-in (see /.well-known/oauth-protected-resource/api/start/mcp) adds the account's own tools to the same server.",
        "requestBody": { "required": true, "content": { "application/json": { "schema": { "type": "object" } } } },
        "responses": { "200": { "description": "A JSON-RPC answer." }, "202": { "description": "A notification was received." } }
      },
      "get": {
        "operationId": "mcpStream",
        "summary": "Not offered without a sign-in: this server does not stream",
        "responses": { "405": { "description": "Use POST." } }
      }
    }
  },
  "components": {
    "parameters": {
      "websiteId": { "name": "websiteId", "in": "path", "required": true, "schema": { "type": "string", "pattern": "^[0-9a-f]{32}$" } }
    },
    "securitySchemes": { "editKey": { "type": "http", "scheme": "bearer", "description": "The editKey returned when the website was started." } }
  }
}
