# SerenAI - Full API Reference > Pay-per-query data marketplace for AI agents. Complete endpoint documentation. For a condensed overview, see [/llms.txt](/llms.txt). ## Base URL & Authentication ``` Base URL: https://api.serendb.com Authorization: Bearer seren_live_xxxxx ``` --- ## Agent Marketplace (Primary API) Query data publishers with pay-per-query pricing. This is the main API for AI agents. ### `POST /auth/agent` POST /auth/agent Register a new AI agent account. This endpoint allows AI agents to self-register and receive an API key immediately. Unlike the standard signup flow, agent registration: - Does NOT require email verification - Automatically creates a personal organization - Returns an API key named "agent" for immediate use **Important:** Save the `api_key` immediately - it is only shown once! **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `PATCH /auth/agent` Update an agent's profile (e.g. set a real email address). When the email is changed, `email_verified` is set to `false` and a verification email with a clickable link is sent. The user verifies by clicking the link — no separate API call is needed. A verified email is required before making Stripe deposits. **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ## Agent Wallet & Payments Manage prepaid balance and payment methods. ### `GET /wallet/balance` Get wallet balance (funded + promotional) **Response:** 200 --- ### `POST /wallet/bonus/payment-method` Claim payment method bonus (if not already claimed) **Response:** 200 --- ### `POST /wallet/bonus/signup` Claim signup bonus (if not already claimed) **Response:** 200 --- ### `POST /wallet/daily/claim` Claim daily free credits **Response:** 200 --- ### `GET /wallet/daily/eligibility` Check if user can claim daily credits **Response:** 200 --- ### `POST /wallet/deposit` Deposit funds via Stripe **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `POST /wallet/deposit/crypto` Deposit configured asset via on-chain payment flow Allows agents to deposit the configured asset directly on-chain to their prepaid balance. Follows the 402 payment protocol: 1. First request (no payment header) returns 402 with payment requirements 2. Second request (with payment header) settles on-chain and credits balance **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `POST /wallet/recover` POST /wallet/recover Recover an agent account using a recovery code. This endpoint allows agents who have lost their API key to recover their account using the recovery code they saved when setting up wallet recovery. **What this does:** - Verifies the recovery code - Revokes all existing API keys (for security) - Issues a new API key - Rotates the recovery code (old code is invalidated) **Important:** Save both the new API key AND the new recovery code - they're only shown once! **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `POST /wallet/recovery` Set up account recovery (recovery code and/or email). - If you don't have a `recovery_code` yet, this endpoint generates one and returns it **once**. - If you already have a `recovery_code`, it will not be shown again. - You can optionally set/update a recovery `email` for human account recovery. Use the recovery code with `POST /wallet/recover` to rotate access after losing your API key. **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /wallet/referral` Get user's referral info and code **Response:** 200 --- ### `POST /wallet/referral/apply` Apply a referral code to the current user **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /wallet/transactions` Get transaction history including credits and debits **Parameters:** - `limit` (integer): Maximum number of transactions to return (default 50, max 100) - `offset` (integer): Offset for pagination - `include_usage` (boolean): Include raw usage/micropayment debits (default false). When false, usage debits are aggregated by day and publisher. - `start_date` (string,null): Filter: only transactions on or after this date (YYYY-MM-DD, interpreted as UTC midnight) - `end_date` (string,null): Filter: only transactions strictly before this date (YYYY-MM-DD, interpreted as UTC midnight). To include a full day, set end_date to the day *after* the last day you want. **Response:** 200 --- ### `GET /wallet/transactions/export` Export transactions as a CSV file for a date range **Parameters:** - `start_date` (string,null): Start date (YYYY-MM-DD, inclusive, UTC midnight) - `end_date` (string,null): End date (YYYY-MM-DD, exclusive, UTC midnight) **Response:** 200 --- ### `GET /wallet/transactions/summary` Get summary statistics for transactions in a date range **Parameters:** - `start_date` (string,null): Start date (YYYY-MM-DD, inclusive, UTC midnight) - `end_date` (string,null): End date (YYYY-MM-DD, exclusive, UTC midnight) **Response:** 200 --- ## Agent Templates Discover and invoke pre-built agent templates. ### `GET /organizations/{organization_id}/templates/analytics/{publisher_id}` GET /organizations/{organization_id}/templates/analytics/{publisher_id} Get template analytics for a specific publisher **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Response:** 200 --- ### `GET /templates` GET /templates List available templates in the catalog **Parameters:** - `verified_only` (boolean): Filter to verified templates only - `language` (string): Filter by language (python, typescript, javascript) - `min_price` (integer): Minimum price in atomic units - `max_price` (integer): Maximum price in atomic units - `search` (string): Search in name and description - `sort_by` (string): Sort order (popularity, price_asc, price_desc, newest, oldest) - `limit` (integer): Maximum number of templates to return (default: 50) - `offset` (integer): Offset for pagination (default: 0) **Response:** 200 --- ### `POST /templates/publish` POST /templates/publish Publish a new agent template **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `GET /templates/{slug}` GET /templates/{slug} Get template details by slug **Parameters:** - `slug` (string *(required)*): Template slug **Response:** 200 --- ### `POST /templates/{slug}/invoke` POST /templates/{slug}/invoke Invoke an agent template. Supports two modes: - **Bearer auth present**: uses the authenticated user's SerenBucks balance. - **No bearer auth**: uses x402 (requires `X-AGENT-WALLET` + payment headers). **Parameters:** - `slug` (string *(required)*): Template slug **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ## Databases ### `GET /databases` List all databases across all projects for the authenticated user Returns all databases the user has access to, with project and branch context included. This provides a single view of all databases without needing to query each project/branch separately. **Response:** 200 --- ## Agent Analytics ### `GET /organizations/{organization_id}/publishers/{publisher_id}/analytics/revenue` GET /organizations/:org_id/publishers/:publisher_id/analytics/revenue Get revenue metrics with period-over-period comparison. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID - `days` (integer): Number of days to analyze (default: 30) **Response:** 200 --- ### `GET /organizations/{organization_id}/publishers/{publisher_id}/analytics/revenue-by-day` GET /organizations/:org_id/publishers/:publisher_id/analytics/revenue-by-day Get daily revenue breakdown. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID - `days` (integer): Number of days to analyze (default: 30) **Response:** 200 --- ### `GET /organizations/{organization_id}/publishers/{publisher_id}/analytics/top-agents` GET /organizations/:org_id/publishers/:publisher_id/analytics/top-agents Get top agents by spending. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID - `limit` (integer): Number of agents to return (default: 10) **Response:** 200 --- ## Agent Tasks ### `GET /organizations/{organization_id}/agents/tasks` GET /organizations/{organization_id}/agents/tasks **Parameters:** - `organization_id` (string *(required)*): Organization ID - `limit` (integer): - `offset` (integer): **Response:** 200 --- ### `GET /organizations/{organization_id}/agents/tasks/{task_id}` GET /organizations/{organization_id}/agents/tasks/{task_id} **Parameters:** - `organization_id` (string *(required)*): Organization ID - `task_id` (string *(required)*): Task ID **Response:** 200 --- ### `POST /organizations/{organization_id}/agents/tasks/{task_id}/cancel` POST /organizations/{organization_id}/agents/tasks/{task_id}/cancel **Parameters:** - `organization_id` (string *(required)*): Organization ID - `task_id` (string *(required)*): Task ID **Response:** 200 --- ### `GET /organizations/{organization_id}/agents/tasks/{task_id}/events` GET /organizations/{organization_id}/agents/tasks/{task_id}/events **Parameters:** - `organization_id` (string *(required)*): Organization ID - `task_id` (string *(required)*): Task ID **Response:** 200 --- ### `GET /organizations/{organization_id}/agents/tasks/{task_id}/stream` GET /organizations/{organization_id}/agents/tasks/{task_id}/stream **Parameters:** - `organization_id` (string *(required)*): Organization ID - `task_id` (string *(required)*): Task ID **Response:** 200 --- ## Audit Logs ### `GET /organizations/{organization_id}/audit-logs` List audit logs for an organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `actor_id` (string,null): Filter by actor ID - `action` (string,null): Filter by action (e.g., "project.create") - `resource_type` (string,null): Filter by resource type (e.g., "project", "branch") - `resource_id` (string,null): Filter by resource ID - `status` (string,null): Filter by status - `action_category` (string,null): Filter by action category - `start_date` (string,null): Filter by start date (ISO 8601) - `end_date` (string,null): Filter by end date (ISO 8601) - `limit` (integer): Maximum number of results (default 50, max 100) - `offset` (integer): Offset for pagination **Response:** 200 --- ### `GET /organizations/{organization_id}/audit-logs/{log_id}` Get a specific audit log entry **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `log_id` (string *(required)*): Audit log ID **Response:** 200 --- ## Auth ### `POST /auth/forgot-password` POST /auth/forgot-password Request a password reset email **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /auth/me` GET /auth/me Get current authenticated user information with default organization **Response:** 200 --- ### `POST /auth/resend-verification` POST /auth/resend-verification Resend email verification link **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `POST /auth/reset-password` POST /auth/reset-password Reset password using a valid token **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `POST /auth/verify-email` POST /auth/verify-email Verify email address using a token from the verification email link. Called by the console frontend when the user clicks the link — agents do not need to call this directly. On success, automatically logs the user in and returns tokens **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /organizations/default/api-keys` List API keys for the user's default organization **Response:** 200 --- ### `POST /organizations/default/api-keys` Create a new API key for the user's default organization This is a convenience endpoint that resolves "default" to the user's first organization, avoiding an extra round-trip to /auth/me. **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `DELETE /organizations/default/api-keys/{key_id}` Revoke an API key from the user's default organization **Parameters:** - `key_id` (string *(required)*): API key ID **Response:** 200 --- ### `GET /organizations/{organization_id}/api-keys` List API keys for a specific organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `POST /organizations/{organization_id}/api-keys` Create a new API key for a specific organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `DELETE /organizations/{organization_id}/api-keys/{key_id}` Revoke an organization API key **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `key_id` (string *(required)*): API key ID **Response:** 200 --- ## billing ### `GET /billing/health` GET /billing/health High-level billing and metering health summary for Seren Core **Response:** 200 --- ### `POST /billing/invoices/generate` POST /billing/invoices/generate Generate monthly invoices for all organizations **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /billing/invoices/{id}` GET /billing/invoices/:id Get invoice details with line items **Parameters:** - `id` (string *(required)*): Invoice ID **Response:** 200 --- ### `POST /billing/invoices/{id}/issue` POST /billing/invoices/:id/issue Issue a draft invoice **Parameters:** - `id` (string *(required)*): Invoice ID **Response:** 200 --- ### `GET /billing/usage/{organization_id}` GET /billing/usage/:organization_id Get usage summary for an organization **Parameters:** - `organization_id` (string *(required)*): Organization ID - `start_date` (string,null): - `end_date` (string,null): **Response:** 200 --- ### `GET /organizations/{organization_id}/billing/endpoints/{endpoint_id}/events` GET /organizations/{organization_id}/billing/endpoints/{endpoint_id}/events Debug endpoint: show recent usage_events and compute_usage_events for an endpoint **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `endpoint_id` (string *(required)*): Endpoint ID **Response:** 200 --- ### `GET /organizations/{organization_id}/consumption` GET /organizations/{organization_id}/consumption Aggregated organization-level consumption over a billing window. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `start_date` (string,null): Optional ISO-8601 start date (YYYY-MM-DD), defaults to first day of current month. - `end_date` (string,null): Optional ISO-8601 end date (YYYY-MM-DD), defaults to today (UTC). **Response:** 200 --- ## Eval ### `GET /eval/matrix` Get the global eval routing matrix. **Response:** 200 --- ### `POST /eval/signals` Ingest eval signals from Seren Desktop clients. **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ## federation ### `GET /federation` GET /federation List federated resources with optional filtering. Used for cross-publisher resource discovery. **Parameters:** - `publisher_slug` (string,null): Filter by publisher slug - `resource_type` (string,null): Filter by resource type (e.g., "bounty", "dataset") - `status` (string,null): Filter by status (default: "active") - `limit` (integer): Maximum number of results (default: 50, max: 100) - `offset` (integer): Offset for pagination **Response:** 200 --- ### `POST /federation` POST /federation Upsert a federated resource for a publisher. Publishers use this to register/update their resources for cross-publisher discovery. **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /federation/history` GET /federation/history List append-only federation history events. **Parameters:** - `publisher_slug` (string,null): Filter by publisher slug - `resource_type` (string,null): Filter by resource type - `external_id` (string,null): Filter by external resource ID - `operation` (string,null): Filter by history operation: insert, update, delete - `limit` (integer): Maximum number of results (default: 50, max: 100) - `offset` (integer): Offset for pagination **Response:** 200 --- ### `GET /federation/history/stats` GET /federation/history/stats Get aggregate statistics over federation history. **Parameters:** - `publisher_slug` (string,null): Filter by publisher slug (optional) - `resource_type` (string,null): Filter by resource type (optional) **Response:** 200 --- ### `GET /federation/stats` GET /federation/stats Get federation statistics, optionally filtered by publisher. **Parameters:** - `publisher_slug` (string,null): Filter by publisher slug (optional - if omitted, returns stats across all publishers) **Response:** 200 --- ### `GET /federation/{id}` GET /federation/{id} Get a specific federated resource by ID. **Parameters:** - `id` (string *(required)*): Federated resource ID **Response:** 200 --- ### `DELETE /federation/{resource_type}/{external_id}` DELETE /federation/{resource_type}/{external_id} Delete a federated resource by type and external ID. Only the owning publisher can delete their resources. **Parameters:** - `resource_type` (string *(required)*): Resource type - `external_id` (string *(required)*): External resource ID **Response:** 204 --- ## OAuth ### `GET /oauth/connections` List user's OAuth connections Returns all OAuth providers the user has connected to. **Response:** 200 --- ### `DELETE /oauth/connections/providers/{provider_id}` Revoke an OAuth connection by provider ID (supports org-scoped providers) **Parameters:** - `provider_id` (string *(required)*): OAuth provider UUID to disconnect **Response:** 200 --- ### `DELETE /oauth/connections/{provider}` Revoke an OAuth connection Disconnects the user's account from the OAuth provider and deletes stored tokens. **Parameters:** - `provider` (string *(required)*): OAuth provider slug to disconnect **Response:** 200 --- ### `GET /oauth/providers` List available OAuth providers Returns all active OAuth providers that users can connect to, including global providers and providers from organizations the user belongs to. **Response:** 200 --- ### `GET /oauth/providers/{provider_id}/authorize` Initiate OAuth authorization flow by provider ID (supports org-scoped providers) **Parameters:** - `provider_id` (string *(required)*): OAuth provider UUID - `redirect_uri` (string): Where to redirect after OAuth completes --- ### `GET /oauth/providers/{provider_id}/callback` Handle OAuth callback by provider ID (supports org-scoped providers) **Parameters:** - `provider_id` (string *(required)*): OAuth provider UUID - `code` (string *(required)*): Authorization code from provider - `state` (string *(required)*): State parameter for CSRF verification --- ### `GET /oauth/{provider}/authorize` Initiate OAuth authorization flow Redirects the user to the OAuth provider's consent screen. After authorization, the provider will redirect back to the callback URL. **Parameters:** - `provider` (string *(required)*): OAuth provider slug (e.g., 'neon') - `redirect_uri` (string): Where to redirect after OAuth completes --- ### `GET /oauth/{provider}/callback` Handle OAuth callback Called by the OAuth provider after the user authorizes. Exchanges the authorization code for tokens and stores them. **Parameters:** - `provider` (string *(required)*): OAuth provider slug - `code` (string *(required)*): Authorization code from provider - `state` (string *(required)*): State parameter for CSRF verification --- ## oauth-providers ### `GET /organizations/{organization_id}/oauth/providers` GET /organizations/{organization_id}/oauth/providers List all OAuth providers for an organization. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `POST /organizations/{organization_id}/oauth/providers` POST /organizations/{organization_id}/oauth/providers Create a new OAuth provider for an organization. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `GET /organizations/{organization_id}/oauth/providers/{provider_id}` GET /organizations/{organization_id}/oauth/providers/{provider_id} Get a specific OAuth provider for an organization. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `provider_id` (string *(required)*): OAuth provider ID **Response:** 200 --- ### `DELETE /organizations/{organization_id}/oauth/providers/{provider_id}` DELETE /organizations/{organization_id}/oauth/providers/{provider_id} Delete an OAuth provider for an organization. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `provider_id` (string *(required)*): OAuth provider ID **Response:** 204 --- ### `PATCH /organizations/{organization_id}/oauth/providers/{provider_id}` PATCH /organizations/{organization_id}/oauth/providers/{provider_id} Update an OAuth provider for an organization. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `provider_id` (string *(required)*): OAuth provider ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ## Organizations ### `GET /organizations` GET /organizations List all organizations for the authenticated user **Response:** 200 --- ### `GET /organizations/{organization_id}/invites` GET /organizations/{organization_id}/invites List pending and historical organization invites. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `POST /organizations/{organization_id}/invites` POST /organizations/{organization_id}/invites Create a new organization invite and send an email via the configured mailer. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `GET /organizations/{organization_id}/members` GET /organizations/{organization_id}/members List organization members with basic user details. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `GET /organizations/{organization_id}/publishers` GET /organizations/:org_id/publishers List publishers owned by an organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `POST /organizations/{organization_id}/publishers` POST /organizations/:org_id/publishers Create a new publisher **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `GET /organizations/{organization_id}/publishers/{publisher_id}` GET /organizations/:org_id/publishers/:publisher_id Get publisher details **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Response:** 200 --- ### `PUT /organizations/{organization_id}/publishers/{publisher_id}` PUT /organizations/:org_id/publishers/:publisher_id Update a publisher **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `DELETE /organizations/{organization_id}/publishers/{publisher_id}` DELETE /organizations/:org_id/publishers/:publisher_id Soft delete a publisher **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Response:** 200 --- ### `GET /organizations/{organization_id}/publishers/{publisher_id}/earnings` GET /organizations/:org_id/publishers/:publisher_id/earnings List earnings for a publisher (per asset). **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Response:** 200 --- ### `POST /organizations/{organization_id}/publishers/{publisher_id}/logo` POST /organizations/{organization_id}/publishers/{publisher_id}/logo Upload a logo for a publisher **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /organizations/{organization_id}/publishers/{publisher_id}/payouts` GET /organizations/:org_id/publishers/:publisher_id/payouts List payout requests for a publisher. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID - `limit` (integer,null): Maximum number of results (default: 50) - `offset` (integer,null): Offset for pagination **Response:** 200 --- ### `POST /organizations/{organization_id}/publishers/{publisher_id}/payouts` POST /organizations/:org_id/publishers/:publisher_id/payouts Request a payout for a publisher's earnings. **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `PUT /organizations/{organization_id}/publishers/{publisher_id}/pricing` PUT /organizations/:org_id/publishers/:publisher_id/pricing Update publisher pricing config for a specific asset **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `publisher_id` (string *(required)*): Publisher ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ## payments ### `POST /billing/invoices/{id}/pay` POST /billing/invoices/:id/pay Create a payment intent for an invoice **Parameters:** - `id` (string *(required)*): Invoice ID **Response:** 200 --- ### `GET /billing/invoices/{id}/payments` GET /billing/invoices/:id/payments Get payment history for an invoice **Parameters:** - `id` (string *(required)*): Invoice ID **Response:** 200 --- ### `GET /billing/payment-methods` GET /billing/payment-methods List payment methods for the organization **Response:** 200 --- ### `POST /billing/payment-methods` POST /billing/payment-methods Add a payment method for the organization **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `DELETE /billing/payment-methods/{id}` DELETE /billing/payment-methods/{id} Remove a payment method from the organization **Parameters:** - `id` (string *(required)*): Payment method ID **Response:** 204 --- ### `GET /payments/supported` GET /payments/supported Returns supported x402 payment kinds for facilitator discovery. **Response:** 200 --- ## Plans ### `GET /organizations/{organization_id}/plan` GET /organizations/:org_id/plan Get the current plan for an organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `POST /organizations/{organization_id}/plan` POST /organizations/:org_id/plan Upgrade or downgrade an organization's plan **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /organizations/{organization_id}/quota` GET /organizations/:org_id/quota Get current quota usage for an organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `GET /plans` GET /plans List all available subscription plans **Response:** 200 --- ### `GET /plans/{plan_id}` GET /plans/:plan_id Get details of a specific plan **Parameters:** - `plan_id` (string *(required)*): Plan ID **Response:** 200 --- ## publisher-payments ### `POST /billing/publishers/{slug}/charges` POST /billing/publishers/{slug}/charges **Parameters:** - `slug` (string *(required)*): Publisher slug **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /billing/publishers/{slug}/charges/{charge_id}` GET /billing/publishers/{slug}/charges/{charge_id} **Parameters:** - `slug` (string *(required)*): Publisher slug - `charge_id` (string *(required)*): Charge ID **Response:** 200 --- ### `POST /billing/publishers/{slug}/charges/{charge_id}/refund` POST /billing/publishers/{slug}/charges/{charge_id}/refund **Parameters:** - `slug` (string *(required)*): Publisher slug - `charge_id` (string *(required)*): Charge ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `POST /billing/publishers/{slug}/charges/{charge_id}/slash` POST /billing/publishers/{slug}/charges/{charge_id}/slash **Parameters:** - `slug` (string *(required)*): Publisher slug - `charge_id` (string *(required)*): Original charge ID **Request Body:** See OpenAPI spec for schema **Response:** 204 --- ### `POST /billing/publishers/{slug}/payouts` POST /billing/publishers/{slug}/payouts **Parameters:** - `slug` (string *(required)*): Publisher slug **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /billing/publishers/{slug}/payouts/{payout_id}` GET /billing/publishers/{slug}/payouts/{payout_id} **Parameters:** - `slug` (string *(required)*): Publisher slug - `payout_id` (string *(required)*): Payout ID **Response:** 200 --- ### `GET /wallet/lookup/{agent_wallet}` GET /wallet/lookup/{agent_wallet} Look up an agent's available balance (for publisher pre-checks) **Parameters:** - `agent_wallet` (string *(required)*): Agent wallet address **Response:** 200 --- ## publishers ### `GET /publishers` GET /publishers List publishers with full details and pricing (store view) **Parameters:** - `is_verified` (boolean,null): Filter by verification status - `category` (string): Filter by publisher category - `search` (string,null): Search by name or slug - `limit` (integer): Maximum number of results (default: 50, max: 100) - `offset` (integer): Offset for pagination **Response:** 200 --- ### `GET /publishers/suggest` GET /publishers/suggest Suggest publishers based on a task or query **Parameters:** - `query` (string *(required)*): The task or query to match against publisher capabilities. Examples: "scrape website", "AI research", "PDF extraction" - `type` (string): Type of suggestions: "publisher", "agent", or "both" (default: "both") Note: Agent suggestions are planned but not yet implemented. - `limit` (integer): Maximum number of results (default: 5, max: 20) **Response:** 200 --- ### `GET /publishers/{slug}` GET /publishers/{slug} Get publisher by slug (store view with full details) **Parameters:** - `slug` (string *(required)*): Publisher slug **Response:** 200 --- ### `POST /publishers/{slug}` Handle requests to the publisher root. For database publishers, this executes a query from the request body. For API publishers, this proxies to the root endpoint. For agent publishers (compute_type=agent), this creates a task and returns 202 Accepted. For MCP publishers, this returns an error (use specific tool/resource endpoints). **Parameters:** - `slug` (string *(required)*): Publisher slug identifier **Request Body:** See OpenAPI spec for schema **Response:** 200, 202 --- ### `POST /publishers/{slug}/estimate` Estimate query cost without payment **Parameters:** - `slug` (string *(required)*): Publisher slug **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /publishers/{slug}/logo` GET /publishers/{slug}/logo Fetch publisher logo (inline data or redirect to URL) Accepts either publisher slug or UUID for backwards compatibility **Parameters:** - `slug` (string *(required)*): Publisher slug or UUID **Response:** 200 --- ### `GET /publishers/{slug}/{path}` **Parameters:** - `slug` (string *(required)*): Publisher slug identifier - `path` (string *(required)*): Path to proxy to the publisher **Response:** 200 --- ### `POST /publishers/{slug}/{path}` **Parameters:** - `slug` (string *(required)*): Publisher slug identifier - `path` (string *(required)*): Path to proxy to the publisher **Response:** 200 --- ## RBAC ### `PUT /organizations/{organization_id}/members/{member_id}/role` Assign a role to an organization member **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `member_id` (string *(required)*): Member user ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /organizations/{organization_id}/permissions/check/{permission}` Check if the current user has a specific permission **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `permission` (string *(required)*): Permission name to check **Response:** 200 --- ### `GET /organizations/{organization_id}/permissions/mine` Get current user's permissions in an organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `GET /organizations/{organization_id}/roles` List roles for an organization (includes built-in roles) **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `POST /organizations/{organization_id}/roles` Create a custom role **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `GET /organizations/{organization_id}/roles/{role_id}` Get a specific role **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `role_id` (string *(required)*): Role ID **Response:** 200 --- ### `DELETE /organizations/{organization_id}/roles/{role_id}` Delete a custom role **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `role_id` (string *(required)*): Role ID **Response:** 204 --- ### `PATCH /organizations/{organization_id}/roles/{role_id}` Update a custom role **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `role_id` (string *(required)*): Role ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /permissions` List all permissions **Response:** 200 --- ## Sessions ### `GET /sessions` List all active sessions for the current user **Response:** 200 --- ### `POST /sessions/revoke-all` Revoke all sessions (logout everywhere) **Response:** 200 --- ### `DELETE /sessions/{session_id}` Revoke a specific session **Parameters:** - `session_id` (string *(required)*): Session ID to revoke **Response:** 200 --- ### `POST /sessions/{session_id}/revoke-others` Revoke all sessions except a specified one **Parameters:** - `session_id` (string *(required)*): Session ID to keep (current session) **Response:** 200 --- ## webhooks ### `POST /webhooks/stripe` POST /webhooks/stripe Handle Stripe webhook events **Response:** 200 --- ## Webhooks ### `GET /organizations/{organization_id}/webhooks` List webhooks for an organization **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Response:** 200 --- ### `POST /organizations/{organization_id}/webhooks` Create a webhook **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization **Request Body:** See OpenAPI spec for schema **Response:** 201 --- ### `GET /organizations/{organization_id}/webhooks/{webhook_id}` Get a specific webhook **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `webhook_id` (string *(required)*): Webhook ID **Response:** 200 --- ### `DELETE /organizations/{organization_id}/webhooks/{webhook_id}` Delete a webhook **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `webhook_id` (string *(required)*): Webhook ID **Response:** 204 --- ### `PATCH /organizations/{organization_id}/webhooks/{webhook_id}` Update a webhook **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `webhook_id` (string *(required)*): Webhook ID **Request Body:** See OpenAPI spec for schema **Response:** 200 --- ### `GET /organizations/{organization_id}/webhooks/{webhook_id}/deliveries` List recent deliveries for a webhook **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `webhook_id` (string *(required)*): Webhook ID **Response:** 200 --- ### `POST /organizations/{organization_id}/webhooks/{webhook_id}/rotate-secret` Regenerate webhook secret **Parameters:** - `organization_id` (string *(required)*): Organization ID or 'default' for authenticated user's default organization - `webhook_id` (string *(required)*): Webhook ID **Response:** 200 --- ### `GET /webhooks/event-types` List available event types **Response:** 200 --- ## VPC (Infrastructure) - `GET /organizations/{organization_id}/vpc-endpoints` - - `POST /organizations/{organization_id}/vpc-endpoints` - - `GET /organizations/{organization_id}/vpc-endpoints/{endpoint_id}` - - `DELETE /organizations/{organization_id}/vpc-endpoints/{endpoint_id}` - - `GET /organizations/{organization_id}/vpc/region/{region_id}/vpc_endpoints` - List VPC endpoints for an organization filtered by region (alias path) - `GET /organizations/{organization_id}/vpc/region/{region_id}/vpc_endpoints/{endpoint_id}` - Get VPC endpoint details with region in path (alias) - `DELETE /organizations/{organization_id}/vpc/region/{region_id}/vpc_endpoints/{endpoint_id}` - Delete VPC endpoint with region in path (alias) - `GET /organizations/{organization_id}/vpc/vpc_endpoints` - List VPC endpoints for an organization (alias path with underscores) --- ## Key Schemas ### CreatePublisherRequest Complete schema for creating a publisher. All fields except required ones are optional. **Required fields:** `name`, `slug`, `wallet_address`, `wallet_network_id` ```json { "name": "string (required) - Display name", "slug": "string (required) - URL-friendly unique identifier", "wallet_address": "string (required) - 0x... Ethereum address for payments", "wallet_network_id": "string (required) - CAIP-2 format, e.g., 'eip155:8453' for Base", "description": "string - Publisher description", "logo_url": "string - URL to publisher logo", "categories": ["string"] - e.g., ["blockchain", "finance"], "capabilities": ["string"] - e.g., ["sql_query", "web_scraping"], "use_cases": ["string"] - Human-readable use case descriptions, "source_type": "string - 'serendb' | 'neon' | 'supabase' | 'api'", "billing_model": "string - 'x402_per_request' | 'prepaid_credits' | 'x402_passthrough'", "api_url": "string - External API URL (required for api source_type)", "api_key_header": "string - Header name for API key injection (e.g., 'Authorization')", "api_key_query_param": "string - Query param for API key injection", "upstream_api_key": "string - API key for upstream service (encrypted)", "project_id": "uuid - SerenDB project ID (for serendb source_type)", "branch_id": "uuid - SerenDB branch ID (for serendb source_type)", "database_name": "string - Database name (default: 'serendb')", "base_price_per_1000_rows": "decimal string - e.g., '0.001'", "price_per_call": "decimal string - e.g., '0.01'", "price_per_get": "decimal string", "price_per_post": "decimal string", "price_per_put": "decimal string", "price_per_patch": "decimal string", "price_per_delete": "decimal string", "resource_name": "string - Display name for the resource", "resource_description": "string - Description of what the resource provides" } ``` **Example - Create an API publisher:** ```bash curl -X POST "https://api.serendb.com/agent/publishers" \ -H "Authorization: Bearer $SEREN_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "name": "My Weather API", "slug": "my-weather-api", "description": "Real-time weather data", "wallet_address": "0x83334ef0C6f6396413C508A7762741e9FD8B20E9", "wallet_network_id": "eip155:8453", "source_type": "api", "api_url": "https://api.weather-service.com", "api_key_header": "X-API-Key", "upstream_api_key": "your-api-key", "billing_model": "x402_per_request", "price_per_call": "0.001" }' ``` ### Publisher A data publisher in the agent marketplace. ```json { "id": "uuid", "slug": "string (unique identifier for API calls)", "name": "string", "description": "string", "is_verified": "boolean", "pricing": { "asset": "USDC", "price_per_query": "decimal" }, "categories": ["string"], "capabilities": ["database", "api", "streaming"] } ``` ### Query Response Response from `/agent/database` or `/agent/api`. ```json { "data": { "rows": [...], "columns": [...] }, "cost": { "amount": "0.01", "asset": "USDC" }, "publisher": { "slug": "publisher-slug", "name": "Publisher Name" } } ``` ### Wallet Balance Response from `/agent/wallet/balance`. ```json { "funded_balance": "10.50", "promotional_balance": "5.00", "total_balance": "15.50", "asset": "USDC" } ``` ### UpdatePublisherPricingRequest Configure pricing for a publisher. ```json { "price_per_call": "decimal string - Default price per API call", "price_per_get": "decimal string - Price for GET requests", "price_per_post": "decimal string - Price for POST requests", "price_per_put": "decimal string - Price for PUT requests", "price_per_patch": "decimal string - Price for PATCH requests", "price_per_delete": "decimal string - Price for DELETE requests", "base_price_per_1000_rows": "decimal string - Price per 1000 rows (database)", "min_charge": "decimal string - Minimum charge per request", "max_charge": "decimal string - Maximum charge per request", "prepaid_enabled": "boolean - Accept SerenBucks payments", "onchain_enabled": "boolean - Accept on-chain x402 payments" } ``` **Example - Configure pricing:** ```bash curl -X PUT "https://api.serendb.com/agent/publishers/my-api/pricing" \ -H "Authorization: Bearer $SEREN_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "price_per_call": "0.01", "min_charge": "0.001", "prepaid_enabled": true, "onchain_enabled": true }' ``` ### Project A database project for self-hosted data. ```json { "id": "uuid", "name": "string", "region": "us-east-1 | eu-west-1 | ...", "created_at": "timestamp", "default_branch_id": "uuid" } ``` --- For the complete OpenAPI specification: https://api.serendb.com/openapi.json