Portal Community

Protocol Overview

Octopus communicates with an external MCP server over HTTPS using two endpoints. The server must respond with Content-Type: application/json on all routes. HTTP 200 indicates success; 4xx/5xx responses cause the agent to receive a structured error result.

EndpointCalled WhenPurpose
GET /toolsAgent startup / config refreshDiscover all available tools and their schemas
POST /tool/{name}/callAgent decides to use a toolExecute the named tool with the supplied arguments
GET /healthStartup probe / monitoringConfirm the server is running (recommended)

GET /tools — Tool Discovery

Octopus calls GET /tools once when the agent is initialized and again on each configuration refresh. The response is a JSON array of tool descriptor objects.

Request

GET /tools HTTP/1.1
Host: my-mcp-server.internal
Authorization: Bearer eyJhbGci...
Accept: application/json

Response — 200 OK

[
  {
    "name":        "zendesk_create_ticket",
    "description": "Create a new Zendesk support ticket. Returns the ticket ID and URL.",
    "inputSchema": {
      "type": "object",
      "properties": {
        "subject": {
          "type":        "string",
          "description": "The ticket subject line"
        },
        "description": {
          "type":        "string",
          "description": "Full description of the issue"
        },
        "priority": {
          "type":        "string",
          "enum":        ["low", "normal", "high", "urgent"],
          "description": "Ticket priority level"
        }
      },
      "required": ["subject", "description"]
    },
    "outputSchema": {
      "type": "object",
      "properties": {
        "ticket_id":  { "type": "integer" },
        "ticket_url": { "type": "string", "format": "uri" },
        "status":     { "type": "string" }
      }
    }
  },
  {
    "name":        "zendesk_search_tickets",
    "description": "Search Zendesk tickets using full-text or field-based query.",
    "inputSchema": {
      "type": "object",
      "properties": {
        "query":  { "type": "string",
                    "description": "Zendesk search query string" },
        "status": { "type": "string",
                    "enum": ["open","pending","solved","closed"],
                    "description": "Optional status filter" }
      },
      "required": ["query"]
    }
  }
]
FieldTypeRequiredDescription
namestringYesSnake-case tool identifier, unique within the server
descriptionstringYesLLM-readable description of what the tool does and returns
inputSchemaJSON Schema objectYesJSON Schema (draft-07) describing the tool's input parameters
outputSchemaJSON Schema objectNoOptional JSON Schema describing the tool's output shape

POST /tool/{name}/call — Tool Execution

When the LLM decides to call a tool, Octopus sends a POST to /tool/{name}/call with the argument object the LLM produced. The argument object must conform to the tool's inputSchema.

Request

POST /tool/zendesk_create_ticket/call HTTP/1.1
Host: my-mcp-server.internal
Authorization: Bearer eyJhbGci...
Content-Type: application/json
X-Octopus-Tenant-Id: tenant-abc123
X-Octopus-Correlation-Id: episode-xyz789

{
  "subject":     "Cannot access the billing portal",
  "description": "Since the last update, users report a 403 error on /billing.",
  "priority":    "high"
}

Request Headers

HeaderDescription
Authorization: Bearer {token}Token resolved via ICredentialResolver at agent startup
X-Octopus-Tenant-IdThe calling tenant's ID — use for per-tenant scoping in your server
X-Octopus-Correlation-IdEpisode ID for end-to-end tracing across logs
Content-Type: application/jsonAlways JSON; your server must accept this

Success Response — 200 OK

{
  "ticket_id":  12345,
  "ticket_url": "https://mycompany.zendesk.com/tickets/12345",
  "status":     "open"
}

Error Response — 4xx / 5xx

Return a structured error body. Octopus relays the message field to the agent as the tool result so the LLM can explain the failure to the user.

// HTTP 422
{
  "error":   "validation_error",
  "message": "The 'priority' field must be one of: low, normal, high, urgent.",
  "field":   "priority"
}

// HTTP 503
{
  "error":   "upstream_unavailable",
  "message": "Zendesk API is temporarily unavailable. Retry in 30 seconds.",
  "retry_after": 30
}

GET /health — Health Check

Implement a GET /health endpoint for Kubernetes liveness probes and Octopus startup health checks. Return HTTP 200 with a simple body.

GET /health HTTP/1.1
Host: my-mcp-server.internal

HTTP/1.1 200 OK
Content-Type: application/json

{ "status": "ok", "version": "1.2.0" }

Protocol Constraints

ConstraintValueNotes
TransportHTTPS only (TLS 1.2+)HTTP is rejected in production mode
Response Content-Typeapplication/jsonRequired on all routes
Tool call timeout30 seconds (default)Configurable per server registration
Max response body4 MBLarger responses are truncated by Octopus
Max tools per server100Register multiple servers if you need more
Tool name charactersLowercase a-z, digits, underscoresNo hyphens, spaces, or dots
Idempotency. Octopus may retry a tool call if it receives a network timeout. Design write operations (create ticket, send email) to be idempotent, or document in the tool description that the LLM should confirm before calling them more than once.