Skip to main content
Glama

DigitalOcean MCP Server

Official
by digitalocean
api.ts3.24 kB
import { createApiClient } from "./specs/digitalocean-openapi.yaml.zod"; import { ApiClient } from "./specs/digitalocean-openapi.yaml.zod"; import logger from "./logger"; import { LIB_VERSION } from "./version"; const BASE_URL = "https://api.digitalocean.com"; function getToken() { const token = process.env.DIGITALOCEAN_API_TOKEN; if (!token) { throw new Error("DIGITALOCEAN_API_TOKEN is not set"); } return token; } function parsePath(path: string, pathParams: Record<string, string> = {}) { // extract the path params from the path. Each params will be in the form {param_name} const pathParts = path.split("/"); const newParts = pathParts.map((part) => { if (part.startsWith("{") && part.endsWith("}")) { const key = part.slice(1, -1); return pathParams[key] || part; } return part; }); return newParts.join("/"); } export function createClient(params: { sessionId?: string } = {}): { client: ApiClient; } { const token = getToken(); const sharedHeaders: Record<string, string> = { "User-Agent": `digitalocean-mcp/${LIB_VERSION}`, Authorization: `Bearer ${token}`, "Content-Type": "application/json", Accept: "application/json", }; const client = createApiClient(async (method, url, params) => { const queryString = new URLSearchParams( params?.query as Record<string, string> ).toString(); const _headers = { ...sharedHeaders, ...params?.header, }; const _url = parsePath(url, params?.path as Record<string, string>); const urlWithQuery = queryString ? `${_url}?${queryString}` : _url; const body = params?.body && !["GET", "HEAD"].includes(method) ? JSON.stringify(params?.body) : undefined; const res = await fetch(urlWithQuery, { method, headers: _headers as HeadersInit, body, }); if (res.status !== 200) { const errorObj = (await res.json()) as IDigitalOceanApiError; if (errorObj.id) { const error = DigitalOceanApiError.fromResponse(errorObj); logger.error( `API Error: ${method.toUpperCase()} ${urlWithQuery} ${error.message}` ); throw error; } throw new Error(`${res.status} ${res.statusText}`); } const responseContentType = res.headers.get("content-type"); if (responseContentType?.includes("application/json")) { return res.json(); } else if (responseContentType?.includes("text/")) { return res.text(); } else if (responseContentType?.includes("application/octet-stream")) { return res.blob(); } else { return res.text(); } }, BASE_URL); return { client }; } interface IDigitalOceanApiError { id: string; message: string; } export class DigitalOceanApiError extends Error { id: string; message: string; static fromResponse(response: IDigitalOceanApiError): DigitalOceanApiError { return new DigitalOceanApiError(response.id, response.message); } static isDigitalOceanApiError(error: unknown): error is DigitalOceanApiError { return error instanceof DigitalOceanApiError; } constructor(id: string, message: string) { super(message); this.id = id; this.message = message; } }

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/digitalocean/digitalocean-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server