@cloudinary/asset-management-mcpv0.9.1

MCP Server

Documentation All MCP Servers Package Repository

Endpoints

EndpointMethodDescription
/mcp POST Streamable HTTP transportRecommended
/sse GET SSE transportDeprecated

Server URL

http://staging-asset-management.mcp.cloudinary.com/mcp

Configuration

Add this to your MCP client configuration. OAuth is used by default when no headers are provided.

Minimal (OAuth)
{ "mcpServers": { "@cloudinary/asset-management-mcp": { "url": "http://staging-asset-management.mcp.cloudinary.com/mcp" } } }
With API Key
{ "mcpServers": { "@cloudinary/asset-management-mcp": { "url": "http://staging-asset-management.mcp.cloudinary.com/mcp", "headers": { "cloudinary-url": "cloudinary://api_key:api_secret@cloud_name" } } } }

Authentication

MethodDescription
OAuth 2.0 Default. The OAuth flow is initiated automatically when the client connects with no auth headers.
API Key Pass cloudinary-url header, or individual cloudinary-cloud-name, cloudinary-api-key, cloudinary-api-secret headers.

Configuration Headers

Optional headers to customize server behavior. Applied at session creation time.

HeaderDescription
cloudinary-region API region: api, api-eu, or api-ap
cloudinary-tools Comma-separated list of tools to enable (e.g. search-assets,list-images)

Response Headers

API response headers are collected into _meta.headers on each tool result. The debug preset is active by default.

HeaderDescription
cloudinary-collect-headers Control which response headers are returned. Accepts:
debug — rate-limit + request ID (default)
ratelimit — rate-limit headers only
all — every response header
Or a comma-separated list of exact names, prefix:<value>, regex:<pattern>, and preset names
cloudinary-embed-headers Set to true to also include collected headers in the response body as _headers, for clients that don't surface _meta
Tool result structure
{ "_meta": { "headers": { "x-featureratelimit-limit": "5000", "x-featureratelimit-remaining": "4998", "x-featureratelimit-reset": "Thu, 13 Feb 2026 00:00:00 GMT", "x-request-id": "bfeaccc60050594832508590a358a1a4" } }, "content": [{ "type": "text", "text": "{...}" }] }

Available Tools (23)

upload-asset asset-rename generate-archive download-asset-backup delete-asset list-images list-videos list-files get-asset-details asset-update list-tags delete-derived-assets get-usage-details create-asset-relations delete-asset-relations move-folder create-folder delete-folder search-folders `, and `metadata.` match on tokens split by whitespace and punctuation — `tags:analysis` matches the tag `full-analysis`. `public_id`, `folder`, `asset_folder`, and `format` match the whole value — `public_id:dog` will not match `dog_pldcwy`; use `public_id="dog_pldcwy"` (exact) or `public_id:dog*` (prefix). These exact-match fields still accept a trailing `*` for prefix match (except `folder` / `asset_folder`, where wildcards are ignored). - **Dates**: ISO-8601 in quotes (`uploaded_at>"2024-01-15"`) or relative shorthand `Nh`, `Nd`, `Nw`, `Nm`, `Ny` (`uploaded_at>1d`, `created_at:[4w TO 1w]`). Send raw `<`/`>`, never HTML-escaped. - **Quoting**: wrap any value containing a space, colon, or other reserved character (`! ( ) { } [ ] ^ ~ ? \ = & < > |`) in double quotes, or escape each character with `\`. Examples: `tags:"service:mantels"`, `aspect_ratio:"16:9"`, `folder:"My Folder"`. ## Common mistakes - Use `folder:` or `asset_folder:` (singular); `folders:`, `asset_folder_id:`, and other invented variants are not valid fields. Pass the exact folder name — wildcards do not apply here. - There is no "has any value" / presence probe. `folder:*`, `metadata.alt:*`, `context.key:*`, `tags:*`, and `-tags:*` are all parse errors. See *"Which assets have any value for `metadata.`?"* under **Common tasks** for workarounds. - `NOT foo AND bar` is a parse error. Write it as `bar AND NOT foo` or `-foo AND bar`, and keep every `NOT` between two clauses (`a AND NOT b AND NOT c` is fine; `NOT b AND NOT c …` is not). - `public_id:dog` will not match `dog_pldcwy`. Use `public_id="dog_pldcwy"` (exact) or `public_id:dog*` (prefix). - `tags=service:mantels` fails because the unquoted colon is parsed as a field separator. Use `tags="service:mantels"` or `tags=service\:mantels`. - Do not HTML-escape operators. Send `uploaded_at<1h`, not `uploaded_at<1h`. - Do not leave an operand empty (e.g. `tags: AND -tags:foo`). Omit the empty clause entirely. ## Tips - Set `max_results: 0` to return only `total_count` and `aggregations` without any resource payload — useful for counts and aggregation-only queries. - `total_count` is always present in the response; prefer it over running an aggregation just to get a count. - `aggregate` (both simple and range variants) and the `metadata`, `image_metadata`, `image_analysis` values of `with_field` require a Tier 2 search plan. - Range aggregations require each range to include a `key` label (1–20 chars, `[a-zA-Z0-9_-]+`) and at least one of `from` / `to`. ## Common tasks - **Count matching assets** — put the filter in `expression` with `max_results: 0` and read `total_count` from the response. Works on every tier; no `aggregate` needed. - **Preview one matching asset** — set `max_results: 1`; add `with_field: ["tags", "context"]` (or `metadata`, Tier 2) to inspect values. Prefer this over fetching and scanning a full page. - **Distribution of values for a field** — Tier 2: `aggregate: [format|resource_type|type]` for enum counts, or range aggregations on `bytes`, `image_pixels`, `video_pixels`, or `duration`. Tier 1 fallback: run N small queries with `max_results: 0`, one per candidate value, and read `total_count` from each. - **"Which assets have any value for `metadata.`?"** — not expressible directly (`metadata.X:*` is a parse error; there is no presence probe). Workarounds: (a) if the field has a known value set, enumerate — `metadata.region:(apac OR emea OR amer)`; (b) query broadly with `with_field: ["metadata"]` (Tier 2) and filter client-side for entries where the field is set; (c) at ingest time, attach a sentinel tag whenever the field is set, then search by that tag. - **Newest / largest N** — keep the filter in `expression` and sort explicitly: `sort_by: [{uploaded_at: "desc"}]` with `max_results: 10`. - **Filter by folder** — both `asset_folder:"parent/child"` and `folder:"parent/child"` match an exact folder path; there is no wildcard or "contains". To query across multiple folders, enumerate: `asset_folder:("campaigns/2024" OR "campaigns/2025")`. - **Filter by metadata when you only know the label** — first call `list-metadata-fields` to resolve the label to an `external_id`, then query `metadata.:value`. - **Multiple independent filters in one turn** — prefer one `expression` with `OR` / parentheses over firing many parallel calls: `metadata.region:apac OR metadata.region:emea` in a single request is faster and more reliable than two parallel requests. ## Examples - `tags:shirt AND uploaded_at>1d` - `resource_type:image AND bytes>1000000 AND (format:png OR format:jpg)` - `folder:products AND context.category:electronics` - `tags:"service:mantels" AND -tags:discontinued` ">search-assets visual-search-assets get-tx-reference transform-asset