Server URL
text
https://www.youthumb.ai/api/mcpAdd YouThumb to your agent
| Agent | How to add the server |
|---|---|
| Claude | Settings → Connectors → Add custom connector, paste the server URL, then Connect. |
| ChatGPT | In the connector settings (developer mode), create a connector with the server URL and OAuth authentication. |
| Claude Code | claude mcp add --transport http youthumb https://www.youthumb.ai/api/mcp, then run /mcp to sign in. |
| Codex | codex mcp add youthumb --url https://www.youthumb.ai/api/mcp, then codex mcp login youthumb. |
Sign in and approve
- Your agent opens a YouThumb page in your browser.
- Sign in with your email and password or with Google. Magic links are not available for this connection.
- YouThumb shows the app that asks for access, where it will send you back, and the rights it requests.
- Choose the Organization used by this app: the app will only work in this organization, with its credits. To change it later, reconnect the app.
- Choose Allow or Deny.
What your agent can do
| Right | Tools |
|---|---|
mcp:read | get_credits, list_persons, get_person, list_assets, list_templates, list_presets, get_generation |
mcp:generate | create_thumbnail_project, start_generation |
mcp:assets | upload_asset, delete_asset, create_person, add_person_images |
Keep control of credits
Creating a project does not use credits; starting the generation does. The agent uses the credits of the organization you chose when you approved it. When credits run out, a plan limit is reached or too many generations run at once, the tool returns a readable error instead of generating. Prefer an API key and theyouthumb-ai skill? See Agents.
Library, favorites and trash
Discover existing projects before creating another thumbnail.GET /api/thumbnails and list_thumbnail_projects accept search, status, favorite and deleted. Lists use page (starting at 1) and limit (1–100, default 20); filters apply before pagination. favorite=false selects non-favorites and deleted=true selects trashed projects.
Favorites are shared by the selected organization. Send {"isFavorite":true} or {"isFavorite":false} explicitly; retries do not toggle the state. Rename with {"projectName":"New title"}. Library management costs no credits. MCP reads require mcp:read and Read access; mutations require mcp:generate and Generation access, plus the account's normal permissions. Trashing an entire project is restricted to administrators.
Normal lists and detail hide deleted jobs and deleted parent projects. list_generations returns completed results across visible thumbnail projects, including every variation image in each job’s results array. Trash listing accepts kind=projects or kind=jobs (individually deleted jobs, including those under deleted parents). There is no permanent deletion. Restore the project first, then any individually deleted jobs. Project restoration sets its status to completed and does not restore its children. Project deletedAt is derived from updatedAt; it is not an immutable historical deletion timestamp. A job has its own stored deletedAt. Repeated trash/restore requests preserve timestamps when already in the requested state.
Active jobs and projects with active jobs cannot be trashed (409). Restoring a job under a deleted parent also returns 409. Invalid payloads return 400, insufficient permissions 403, and unknown or foreign-organization identifiers 404.
GET /api/thumbnails/:projectId, /detailed-status, /status and get_generation share details: project metadata, isFavorite, full-project summary, latest result, job metadata, grouped images and person IDs. jobs[].results and top-level activeJobs remain available. Without query options all visible jobs are returned; page or limit opts into bounded job pages. A comma-separated status alone filters all visible jobs without pagination, preserving existing clients. Summary and latest result always describe the whole visible project.
| REST | MCP | Parameters |
|---|---|---|
GET /api/thumbnails | list_thumbnail_projects | page, limit, search, status, favorite, deleted |
GET /api/thumbnails/:projectId | get_generation | summary?, page?, limit?, status? |
PATCH /api/thumbnails/:projectId | update_thumbnail_project | projectName |
GET /api/thumbnails/results | list_generations | page, limit, favorite, projectId |
PUT /api/thumbnails/:projectId/favorite | set_project_favorite | isFavorite |
PUT /api/thumbnails/jobs/:jobId/favorite | set_generation_favorite | isFavorite |
DELETE /api/thumbnails/:projectId | trash_thumbnail_project | projectId |
POST /api/thumbnails/:projectId/restore | restore_thumbnail_project | projectId |
DELETE /api/thumbnails/jobs/:jobId | trash_generation | jobId |
POST /api/thumbnails/jobs/:jobId/restore | restore_generation | jobId |
GET /api/thumbnails/trash | list_trash | kind=projects / jobs, page, limit |
json
{"favorite":true,"page":1,"limit":20}Attempts, iteration and retry
POST /api/thumbnails/:projectId/start and start_generation keep the same project. Optional overrides: prompt, personId (null clears), presetKey, templateId, styleReferenceUrl, youtubeUrl, sourceResultId, contentImages ([] clears), title ("" clears), and advancedOptions. Omitted fields retain project defaults; options merge. Overrides affect only this attempt, never the saved project. Supply only one source selector (preset, template, URL, YouTube or result). Each content image contains exactly one userImageId or url; explicit image URLs must belong to your configured uploaded storage path. Upload external images first.
Read jobs[].results[].id from project detail; pass that ID as sourceResultId to iterate on that exact completed image. It must belong to a visible completed job in the same project. A reference selects normal generation; a preset selects magic generation. Deleted projects and results cannot be generated from.
json
{"projectId":"<project-id>","sourceResultId":"<result-image-id>","prompt":"Keep this composition and brighten the background","advancedOptions":{"variations":1}}POST /api/thumbnails/jobs/:jobId/retry / retry_generation({jobId}) accepts a failed Default job only. It creates a new billed attempt in the same project, preserving the failed prompt, input images, persons, title, preset and options; it never resets the failed job or uses changed project defaults. The new metadata records retryOfJobId. Every call is non-idempotent and consumes generation credits again. Success includes jobId, projectId, status, creditsConsumed only after launch acknowledgement. A synchronous launch failure refunds credits and fails the orphan job.
Prompt assistance
POST /api/thumbnails/prompts/improve / improve_prompt: prompt plus optional context with axes (composition, hook, readability), language (fr, en, es), personName, title, customInstruction, hasStyleReference, referenceTokens (@image1...), sketchTokens (@sketch1...).
POST /api/thumbnails/prompts/from-reference / prompt_from_reference: exactly one of assetId, published or own-private templateId, projectId + sourceResultId, or imageUrl proven to be an upload owned by the caller; optional language (default en). Arbitrary URLs are refused; upload first. References are authorized in the selected organization before billing.
Both return {prompt, creditsConsumed: 0.5} without creating a project or image. Provider failure refunds once. MCP requires mcp:generate and Generation enabled. Its daily cap counts exact half credits; changing the tool does not evade the limit. Existing integer limits retain their meaning.
Resources: persons, uploads and catalog
All resource operations use the connected identity. Stored assets must belong to the selected organization and be owned by you or shared with it. Imports stay unpublished and are still discoverable. Unknown or inaccessible IDs return 404; permission refusals return 403; invalid inputs return 400. MCP errors useisError: true. Management operations consume no credits.
| REST | MCP | Input / effect |
|---|---|---|
PATCH /api/persons/:id | update_person | name? (1–100), description? (max 500); null clears description; at least one field |
DELETE /api/persons/:id | delete_person | Deletes profile and photo associations; stored images remain |
DELETE /api/persons/:id/images/:imageId | remove_person_image | Detaches only this existing association, without deleting the asset |
PUT /api/persons/:id/default | set_default_person | Idempotent organization default; existing owner permissions apply |
GET /api/assets/:id | get_asset | Authorized stored asset UUID |
GET /api/templates/:id | get_template | Published catalog template or your own private template |
mcp:assets and active Images and persons access. Reads require mcp:read and active Read access. Tool arguments use personId, imageId, assetId or templateId instead of URL path parameters. Person reads/updates return the profile with images and imageCount; delete returns {"deleted":true}. Existing create/add-photo calls also validate every referenced image before writing.
Asset discovery
GET /api/assets / list_assets accepts type (face, template, bucket), search, isPublished, page (default 1), limit (default 20, max 100). Without type, stored face and template images are listed. Search matches name/description, and visibility/publication filters apply before pagination and count. Stored results include isPublished, ownerScope: "organization"; pagination returns page, limit, total, totalPages, hasMore.
type=bucket lists the caller's personal temporary folder across organizations. Results include ownerScope: "user", id: "", stable fileKey, url and isFavorite. Use contentImages: [{"url": "RETURNED_URL"}] for generation; get_asset and userImageId require a persisted asset UUID, never a bucket file key. favorite=true selects starred files, favorite=false excludes them; omission includes both. search matches file names. Bucket-only sortBy=name|createdAt and sortOrder=asc|desc default to createdAt descending. Unknown or invalid dates remain createdAt: null and sort last in either direction; ties use fileKey ascending. These three bucket filters are rejected for other asset types; isPublished is invalid for bucket files.
The service enumerates matching storage files in batches of 100, deduplicates by path and excludes non-images/placeholders before favorite filtering, sorting and public pagination. total is the filtered image count, totalPages = ceil(total / limit) and hasMore signals another page. Empty results have totals of 0; an out-of-range page is empty. Orphan favorites do not create assets. Every request enumerates the matching folder, so large folders cost more storage requests; concurrent changes are not an atomic snapshot. Any provider page failure fails the request rather than returning partial success. Temporary files cannot be deleted through /api/assets/:id.
Example: GET /api/assets?type=bucket&search=logo&favorite=true&sortBy=createdAt&sortOrder=desc&page=1&limit=20 or MCP list_assets({"type":"bucket","search":"logo","favorite":true,"sortBy":"createdAt","sortOrder":"desc","page":1,"limit":20}).
Three reference namespaces
GET /api/templates / list_templates searches catalog title, description and tags with search. scope=public (default) lists published catalog templates; scope=mine lists only templates you created, published or private. isPublished=false requires scope=mine. Existing category, isFeatured, page, limit filters remain. Responses contain templates and pagination (page, limit, total, totalPages).
A catalog UUID goes in templateId. An uploaded personal reference is found through list_assets(type="template"): use its URL as styleReferenceUrl, or its UUID as a content userImageId / prompt-assistance assetId. A temporary file uses its URL. Never interchange catalog IDs, asset IDs and file keys.
bash
curl "$BASE/api/assets?type=template&search=studio&page=1&limit=20" -H "x-api-key: $YOUTHUMB_API_KEY"
curl "$BASE/api/templates?scope=mine&isPublished=false&search=studio" -H "x-api-key: $YOUTHUMB_API_KEY"
curl -X PATCH "$BASE/api/persons/$PERSON_ID" -H "x-api-key: $YOUTHUMB_API_KEY" -H "Content-Type: application/json" -d '{"description":null}'Compact exploration and explicit counts
Preferget_generation({projectId, summary:true, page:1, limit:5}) or GET /api/thumbnails/:projectId?summary=true&page=1&limit=5 for exploration and polling. summary=true defaults to page 1 and limit 20 (1–100); status still accepts comma-separated statuses. The response contains projectId, projectName, status, isFavorite, the full-project summary, pagination, and jobs with only jobId, status, type, isFavorite, userPrompt, generatedFileUrl, createdAt. It omits project/job metadata, embedded images and persons. Full prompts are retained, so there is no fixed byte-size guarantee. Follow pagination.hasMore for further pages. For result image IDs needed by sourceResultId, request a bounded detailed page with summary:false.
summary absent or false preserves the existing detailed contract, including unbounded status-only reads. list_generations / GET /api/thumbnails/results now includes the complete userPrompt (or null) per job; no detail call is required to read prompts.
get_credits / GET /api/usage adds counts.activeGenerationProjects (non-deleted projects, all generation types) and counts.completedThumbnailJobs (completed, non-deleted jobs in visible thumbnail projects; same scope as unfiltered list_generations). These are organization-scoped counts of projects and jobs, not images or credits consumed. Existing generations statistics still count projects; generations.total equals counts.activeGenerationProjects. Credits and historical counters are unchanged.
Project favorites (generation_project), job favorites (generation_job) and personal bucket file favorites are separate. list_thumbnail_projects({favorite:true}) may correctly return zero even with many favorite jobs: it does not select projects merely containing favorite jobs. If tool parameters omit summary, page, limit or asset search, refresh/reconnect the MCP client and reload its tool list; updating the skill alone does not update cached tool schemas.