openapi: 3.2.0 info: contact: url: https://github.com/stacklok/toolhive description: 'API for accessing MCP server registry data and deployed server information This API provides endpoints to query the MCP (Model Context Protocol) server registry, get information about available servers, and check the status of deployed servers. Authentication is required by default. Use Bearer token authentication with a valid OAuth/OIDC access token. The /.well-known/oauth-protected-resource endpoint provides OAuth discovery metadata (RFC 9728).' license: name: Apache 2.0 url: http://www.apache.org/licenses/LICENSE-2.0.html title: ToolHive Registry clients V1 Entries API version: '0.1' tags: - name: Entries paths: /v1/entries: post: description: Publish a new server or skill entry. Exactly one of 'server' or 'skill' must be provided. requestBody: content: application/json: schema: oneOf: - type: object - $ref: '#/components/schemas/internal_api_v1.publishEntryRequest' description: Entry to publish (server or skill) summary: request description: Entry to publish (server or skill) required: true responses: '201': content: application/json: schema: type: object description: Published entry (server or skill) '400': content: application/json: schema: additionalProperties: type: string type: object description: Bad request '409': content: application/json: schema: additionalProperties: type: string type: object description: Conflict '500': content: application/json: schema: additionalProperties: type: string type: object description: Internal server error summary: Publish entry tags: - Entries operationId: postV1Entries x-operation-id-source: derived /v1/entries/{type}/{name}/claims: get: description: 'Get the claims for an API-published entry name within the managed source. Claims are stored at the entry-name level and are shared by every version of that name. Synced-source entries (git/api/file/kubernetes) are out of scope: their claims come from upstream (the source manifest or the `toolhive.stacklok.dev/authz-claims` annotation) and are surfaced through the `/v1/sources/{name}/entries` and `/v1/registries/{name}/entries` lists.' parameters: - description: Entry Type (server or skill) in: path name: type required: true schema: type: string - description: Entry Name in: path name: name required: true schema: type: string responses: '200': content: application/json: schema: $ref: '#/components/schemas/internal_api_v1.entryClaimsResponse' description: Entry claims '400': content: application/json: schema: additionalProperties: type: string type: object description: Bad request '403': content: application/json: schema: additionalProperties: type: string type: object description: Forbidden '404': content: application/json: schema: additionalProperties: type: string type: object description: Not found '500': content: application/json: schema: additionalProperties: type: string type: object description: Internal server error '503': content: application/json: schema: additionalProperties: type: string type: object description: No managed source available summary: Get entry claims tags: - Entries operationId: getV1EntriesByTypeByNameClaims x-operation-id-source: derived put: description: Update claims for a published entry name parameters: - description: Entry Type (server or skill) in: path name: type required: true schema: type: string - description: Entry Name in: path name: name required: true schema: type: string requestBody: content: application/json: schema: oneOf: - type: object - $ref: '#/components/schemas/internal_api_v1.updateEntryClaimsRequest' description: Claims to set summary: request description: Claims to set required: true responses: '204': description: No Content '400': content: application/json: schema: additionalProperties: type: string type: object description: Bad request '403': content: application/json: schema: additionalProperties: type: string type: object description: Forbidden '404': content: application/json: schema: additionalProperties: type: string type: object description: Not found '500': content: application/json: schema: additionalProperties: type: string type: object description: Internal server error '503': content: application/json: schema: additionalProperties: type: string type: object description: No managed source available summary: Update entry claims tags: - Entries operationId: putV1EntriesByTypeByNameClaims x-operation-id-source: derived /v1/entries/{type}/{name}/versions/{version}: delete: description: Delete a published entry version parameters: - description: Entry Type (server or skill) in: path name: type required: true schema: type: string - description: Entry Name in: path name: name required: true schema: type: string - description: Version in: path name: version required: true schema: type: string responses: '204': description: No Content '400': content: application/json: schema: additionalProperties: type: string type: object description: Bad request '404': content: application/json: schema: additionalProperties: type: string type: object description: Not found '500': content: application/json: schema: additionalProperties: type: string type: object description: Internal server error summary: Delete published entry tags: - Entries operationId: deleteV1EntriesByTypeByNameVersionsByVersion x-operation-id-source: derived components: schemas: model.Input: properties: choices: items: type: string type: array uniqueItems: false default: type: string description: type: string format: $ref: '#/components/schemas/model.Format' isRequired: type: boolean isSecret: type: boolean placeholder: type: string value: type: string type: object internal_api_v1.entryClaimsResponse: properties: claims: additionalProperties: {} type: object type: object internal_api_v1.updateEntryClaimsRequest: properties: claims: additionalProperties: {} type: object type: object model.Format: enum: - string - number - boolean - filepath type: string x-enum-varnames: - FormatString - FormatNumber - FormatBoolean - FormatFilePath model.Icon: properties: mimeType: example: image/png type: string sizes: items: type: string type: array uniqueItems: false src: example: https://example.com/icon.png format: uri maxLength: 255 type: string theme: type: string type: object model.Argument: properties: choices: items: type: string type: array uniqueItems: false default: type: string description: type: string format: $ref: '#/components/schemas/model.Format' isRepeated: type: boolean isRequired: type: boolean isSecret: type: boolean name: example: --port type: string placeholder: type: string type: $ref: '#/components/schemas/model.ArgumentType' value: type: string valueHint: example: file_path type: string variables: additionalProperties: $ref: '#/components/schemas/model.Input' type: object type: object model.Repository: properties: id: example: b94b5f7e-c7c6-d760-2c78-a5e9b8a5b8c9 type: string source: example: github type: string subfolder: example: src/everything type: string url: example: https://github.com/modelcontextprotocol/servers format: uri type: string type: object v0.ServerJSON: properties: $schema: example: https://static.modelcontextprotocol.io/schemas/2025-12-11/server.schema.json format: uri minLength: 1 type: string _meta: $ref: '#/components/schemas/v0.ServerMeta' description: example: MCP server providing weather data and forecasts via OpenWeatherMap API maxLength: 100 minLength: 1 type: string icons: items: $ref: '#/components/schemas/model.Icon' type: array uniqueItems: false name: example: io.github.user/weather maxLength: 200 minLength: 3 pattern: ^[a-zA-Z0-9.-]+/[a-zA-Z0-9._-]+$ type: string packages: items: $ref: '#/components/schemas/model.Package' type: array uniqueItems: false remotes: items: $ref: '#/components/schemas/model.Transport' type: array uniqueItems: false repository: $ref: '#/components/schemas/model.Repository' title: example: Weather API maxLength: 100 minLength: 1 type: string version: example: 1.0.2 maxLength: 255 minLength: 1 type: string websiteUrl: example: https://modelcontextprotocol.io/examples format: uri type: string type: object model.ArgumentType: enum: - positional - named example: positional type: string x-enum-varnames: - ArgumentTypePositional - ArgumentTypeNamed model.Package: properties: environmentVariables: description: EnvironmentVariables are set when running the package items: $ref: '#/components/schemas/model.KeyValueInput' type: array uniqueItems: false fileSha256: description: FileSHA256 is the SHA-256 hash for integrity verification (required for mcpb, optional for others) example: fe333e598595000ae021bd27117db32ec69af6987f507ba7a63c90638ff633ce pattern: ^[a-f0-9]{64}$ type: string identifier: description: "Identifier is the package identifier:\n - For NPM/PyPI/NuGet: package name or ID\n - For OCI: full image reference (e.g., \"ghcr.io/owner/repo:v1.0.0\")\n - For MCPB: direct download URL" example: '@modelcontextprotocol/server-brave-search' minLength: 1 type: string packageArguments: description: PackageArguments are passed to the package's binary items: $ref: '#/components/schemas/model.Argument' type: array uniqueItems: false registryBaseUrl: description: RegistryBaseURL is the base URL of the package registry (used by npm, pypi, nuget, cargo; not used by oci, mcpb) example: https://registry.npmjs.org format: uri type: string registryType: description: RegistryType indicates how to download packages (e.g., "npm", "pypi", "cargo", "oci", "nuget", "mcpb") example: npm minLength: 1 type: string runtimeArguments: description: RuntimeArguments are passed to the package's runtime command (e.g., docker, npx) items: $ref: '#/components/schemas/model.Argument' type: array uniqueItems: false runtimeHint: description: RunTimeHint suggests the appropriate runtime for the package example: npx type: string transport: $ref: '#/components/schemas/model.Transport' version: description: Version is the package version (required for npm, pypi, nuget; optional for mcpb; not used by oci where version is in the identifier) example: 1.0.2 maxLength: 255 minLength: 1 type: string type: object model.Transport: description: Transport is required and specifies the transport protocol configuration properties: headers: items: $ref: '#/components/schemas/model.KeyValueInput' type: array uniqueItems: false type: example: stdio type: string url: example: https://api.example.com/mcp type: string variables: additionalProperties: $ref: '#/components/schemas/model.Input' type: object type: object model.KeyValueInput: properties: choices: items: type: string type: array uniqueItems: false default: type: string description: type: string format: $ref: '#/components/schemas/model.Format' isRequired: type: boolean isSecret: type: boolean name: example: SOME_VARIABLE type: string placeholder: type: string value: type: string variables: additionalProperties: $ref: '#/components/schemas/model.Input' type: object type: object v0.ServerMeta: properties: io.modelcontextprotocol.registry/publisher-provided: additionalProperties: {} type: object type: object github_com_stacklok_toolhive-registry-server_internal_service.SkillIcon: properties: label: type: string size: type: string src: type: string type: type: string type: object github_com_stacklok_toolhive-registry-server_internal_service.SkillPackage: properties: commit: type: string digest: type: string identifier: type: string mediaType: type: string ref: type: string registryType: type: string subfolder: type: string url: type: string type: object internal_api_v1.publishEntryRequest: properties: claims: additionalProperties: {} type: object server: $ref: '#/components/schemas/v0.ServerJSON' skill: $ref: '#/components/schemas/github_com_stacklok_toolhive-registry-server_internal_service.Skill' type: object github_com_stacklok_toolhive-registry-server_internal_service.SkillRepository: properties: type: type: string url: type: string type: object github_com_stacklok_toolhive-registry-server_internal_service.Skill: properties: _meta: additionalProperties: {} type: object allowedTools: items: type: string type: array uniqueItems: false compatibility: type: string createdAt: type: string description: type: string icons: items: $ref: '#/components/schemas/github_com_stacklok_toolhive-registry-server_internal_service.SkillIcon' type: array uniqueItems: false id: type: string isLatest: type: boolean license: type: string metadata: additionalProperties: {} type: object name: type: string namespace: type: string packages: items: $ref: '#/components/schemas/github_com_stacklok_toolhive-registry-server_internal_service.SkillPackage' type: array uniqueItems: false repository: $ref: '#/components/schemas/github_com_stacklok_toolhive-registry-server_internal_service.SkillRepository' status: type: string title: type: string updatedAt: type: string version: type: string type: object securitySchemes: BearerAuth: description: 'OAuth 2.0 Bearer token authentication. Format: "Bearer {token}"' in: header name: Authorization type: apiKey externalDocs: description: '' url: ''