{
  "openapi": "3.1.0",
  "info": {
    "title": "ProbeGate Website Security API for Agents",
    "version": "0.2.0",
    "description": "Ownership-verified website security assessments, capture flags, evidence and signed webhook alerts. 100 free runs per month, 15 minutes and 60 requests per free run. MCP endpoint /mcp; complete instructions /llms-full.txt."
  },
  "servers": [
    {
      "url": "https://probegate.peachjam.dev/v1"
    }
  ],
  "security": [
    {
      "apiKey": []
    }
  ],
  "components": {
    "securitySchemes": {
      "apiKey": {
        "type": "http",
        "scheme": "bearer",
        "bearerFormat": "fh_live_..."
      }
    },
    "schemas": {
      "Error": {
        "type": "object",
        "properties": {
          "error": {
            "type": "object",
            "properties": {
              "code": {
                "type": "string"
              },
              "message": {
                "type": "string"
              }
            }
          }
        }
      }
    }
  },
  "paths": {
    "/health": {
      "get": {
        "summary": "Service and pinned model identity",
        "operationId": "get_health",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "security": []
      }
    },
    "/config": {
      "get": {
        "summary": "Public billing configuration",
        "operationId": "get_config",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "security": []
      }
    },
    "/auth/register": {
      "post": {
        "summary": "Create a workspace",
        "operationId": "post_auth_register",
        "responses": {
          "201": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "security": [],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "email": {
                    "type": "string",
                    "format": "email"
                  },
                  "password": {
                    "type": "string",
                    "minLength": 12,
                    "maxLength": 128
                  }
                },
                "required": [
                  "email",
                  "password"
                ]
              }
            }
          }
        }
      }
    },
    "/auth/login": {
      "post": {
        "summary": "Start a console session",
        "operationId": "post_auth_login",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "security": [],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "email": {
                    "type": "string",
                    "format": "email"
                  },
                  "password": {
                    "type": "string"
                  }
                },
                "required": [
                  "email",
                  "password"
                ]
              }
            }
          }
        }
      }
    },
    "/auth/logout": {
      "post": {
        "summary": "End a console session",
        "operationId": "post_auth_logout",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "security": [],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {}
              }
            }
          }
        }
      }
    },
    "/me": {
      "get": {
        "summary": "Plan, usage and limits",
        "operationId": "get_me",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        }
      }
    },
    "/targets": {
      "get": {
        "summary": "List your targets",
        "operationId": "get_targets",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        }
      },
      "post": {
        "summary": "Register a target and receive an ownership challenge",
        "operationId": "post_targets",
        "responses": {
          "201": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "url": {
                    "type": "string",
                    "format": "uri",
                    "example": "https://app.example.com"
                  }
                },
                "required": [
                  "url"
                ]
              }
            }
          }
        }
      }
    },
    "/targets/{id}/verify": {
      "post": {
        "summary": "Verify exact-host ownership",
        "operationId": "post_targets_id_verify",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "method": {
                    "type": "string",
                    "enum": [
                      "dns",
                      "file"
                    ]
                  }
                },
                "required": [
                  "method"
                ]
              }
            }
          }
        }
      }
    },
    "/targets/{id}/verification": {
      "delete": {
        "summary": "Revoke ownership and cancel active runs",
        "operationId": "delete_targets_id_verification",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ]
      }
    },
    "/runs": {
      "get": {
        "summary": "List the latest 100 assessments",
        "operationId": "get_runs",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        }
      },
      "post": {
        "summary": "Start a bounded assessment",
        "operationId": "post_runs",
        "responses": {
          "202": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "Idempotency-Key",
            "in": "header",
            "schema": {
              "type": "string",
              "minLength": 8,
              "maxLength": 128
            }
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "target_id": {
                    "type": "string"
                  },
                  "duration_seconds": {
                    "type": "integer",
                    "minimum": 60,
                    "maximum": 3600,
                    "default": 300
                  },
                  "max_requests": {
                    "type": "integer",
                    "minimum": 2,
                    "maximum": 120,
                    "default": 15
                  },
                  "flag": {
                    "type": "string",
                    "minLength": 12,
                    "maxLength": 256,
                    "writeOnly": true
                  },
                  "webhook_id": {
                    "type": "string"
                  }
                },
                "required": [
                  "target_id"
                ]
              }
            }
          }
        }
      }
    },
    "/runs/{id}": {
      "get": {
        "summary": "Result, findings, model provenance and evidence",
        "operationId": "get_runs_id",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ]
      }
    },
    "/runs/{id}/cancel": {
      "post": {
        "summary": "Cancel an assessment",
        "operationId": "post_runs_id_cancel",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {}
              }
            }
          }
        }
      }
    },
    "/keys": {
      "get": {
        "summary": "List key metadata",
        "operationId": "get_keys",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        }
      },
      "post": {
        "summary": "Create an API key (shown once)",
        "operationId": "post_keys",
        "responses": {
          "201": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string",
                    "maxLength": 80
                  }
                },
                "required": [
                  "name"
                ]
              }
            }
          }
        }
      }
    },
    "/keys/{id}": {
      "delete": {
        "summary": "Revoke an API key",
        "operationId": "delete_keys_id",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ]
      }
    },
    "/webhooks": {
      "get": {
        "summary": "List alert receivers",
        "operationId": "get_webhooks",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        }
      },
      "post": {
        "summary": "Register a signed alert receiver",
        "operationId": "post_webhooks",
        "responses": {
          "201": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "url": {
                    "type": "string",
                    "format": "uri"
                  }
                },
                "required": [
                  "url"
                ]
              }
            }
          }
        }
      }
    },
    "/webhooks/{id}": {
      "delete": {
        "summary": "Disable an alert receiver",
        "operationId": "delete_webhooks_id",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ]
      }
    },
    "/events": {
      "get": {
        "summary": "Poll the latest 100 events",
        "operationId": "get_events",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        }
      }
    },
    "/deliveries": {
      "get": {
        "summary": "Inspect latest 100 webhook deliveries",
        "operationId": "get_deliveries",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        }
      }
    },
    "/deliveries/{id}/retry": {
      "post": {
        "summary": "Retry a delivery",
        "operationId": "post_deliveries_id_retry",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ],
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {}
              }
            }
          }
        }
      }
    },
    "/billing/checkout": {
      "post": {
        "summary": "Create a one-time prepaid credit checkout",
        "operationId": "post_billing_checkout",
        "responses": {
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          },
          "201": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          }
        },
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "provider": {
                    "type": "string",
                    "enum": [
                      "paddle",
                      "flitt"
                    ],
                    "default": "paddle"
                  }
                }
              }
            }
          }
        }
      }
    },
    "/billing/portal": {
      "post": {
        "summary": "Create a customer portal session",
        "operationId": "post_billing_portal",
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request"
          },
          "401": {
            "description": "Unauthorized"
          },
          "403": {
            "description": "Ownership or origin not authorized"
          },
          "409": {
            "description": "Conflict, concurrency limit or quota exceeded"
          },
          "429": {
            "description": "API rate limit exceeded"
          }
        },
        "requestBody": {
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {}
              }
            }
          }
        }
      }
    },
    "/billing/purchases": {
      "get": {
        "summary": "List payment receipts and verified status",
        "operationId": "list_payment_receipts_and_verified_status",
        "responses": {
          "200": {
            "description": "Verified result"
          },
          "401": {
            "description": "Authentication required"
          }
        }
      }
    },
    "/billing/purchases/{id}/sync": {
      "post": {
        "summary": "Reconcile a purchase with its payment provider",
        "operationId": "reconcile_a_purchase_with_its_payment_provider",
        "responses": {
          "200": {
            "description": "Verified result"
          },
          "401": {
            "description": "Authentication required"
          }
        },
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            }
          }
        ]
      }
    }
  }
}
