Examples
The Weave API is available to customers on the Weave Enterprise plan only
This section provides examples of how the Weave API endpoints work together, from running a single tool through uploading a file to run it on, to the way iterators and failures shape the run status response.
The IDs in these examples, such as wf_xyz and run_abc123, are placeholders.
Run a tool and poll for its result
A single run of wf_xyz, the tool described by the GET inspect example — six inputs. Every input has to be set, so this request sends the two that matter here and takes the rest from the values the tool was published with, using use_default. Start the run, then poll GET runs until it reaches a terminal status.
Start the run
POST https://developer.api.weavy.ai/v1/tools/wf_xyz/runs
Example request body
{
"inputs": [
{
"id": "b97a8c27-2dbe-4159-b5d5-33df6a329ea3",
"value": { "type": "string", "value": "a red panda in space" }
},
{
"id": "2d8e4f6a-9b1c-4d3e-8f5a-7c6b0e9d2a14",
"value": { "type": "media", "value": "https://example.com/reference.png", "kind": "image" }
},
{ "id": "3f2504e0-4f89-4d3a-9a0c-0305e82c3301", "use_default": true },
{ "id": "7c9e6679-7425-40de-944b-e07fc1f90ae7", "use_default": true },
{ "id": "1ff8a7b5-2c3d-4e6f-8a1b-9c0d2e3f4a5b", "use_default": true },
{ "id": "6fa459ea-ee8a-4ca4-894e-db77e160355e", "use_default": true }
]
}
Example response body
202 Accepted
{
"runs": [
{
"id": "run_abc123",
"tool_id": "wf_xyz",
"status": "running"
}
]
}
Poll for status
GET https://developer.api.weavy.ai/v1/tools/wf_xyz/runs?run_ids=run_abc123
While the run is in progress, status is running and progress_percentage reports how far it has progressed. There is no completed_at, and no outputs yet.
{
"runs": [
{
"id": "run_abc123",
"tool_id": "wf_xyz",
"status": "running",
"progress_percentage": 40,
"created_at": "2026-05-06T10:00:00Z"
}
],
"workspace_credits_remaining": 850
}
Once the run finishes, status is completed, completed_at is set, progress_percentage is omitted, and the outputs are available.
{
"runs": [
{
"id": "run_abc123",
"tool_id": "wf_xyz",
"status": "completed",
"created_at": "2026-05-06T10:00:00Z",
"completed_at": "2026-05-06T10:00:42Z",
"outputs": [
{
"id": "b3f9c2a1-7d4e-4f86-a0b5-2e8c91d4f7a6",
"name": "Hero image",
"assets": [
{ "type": "image", "url": "https://cdn.figma.com/..." }
]
}
]
}
],
"workspace_credits_remaining": 850
}
Generate variations with a single request
Set count to start several runs of the same inputs at once. wf_xyz publishes its Seed input as random, so defaulting it — as this request does — gives each run a different result. count accepts a value between 1 and 10.
Start the runs
POST https://developer.api.weavy.ai/v1/tools/wf_xyz/runs
Example request body
{
"count": 3,
"inputs": [
{
"id": "b97a8c27-2dbe-4159-b5d5-33df6a329ea3",
"value": { "type": "string", "value": "a red panda in space" }
},
{
"id": "2d8e4f6a-9b1c-4d3e-8f5a-7c6b0e9d2a14",
"value": { "type": "media", "value": "https://example.com/reference.png", "kind": "image" }
},
{ "id": "3f2504e0-4f89-4d3a-9a0c-0305e82c3301", "use_default": true },
{ "id": "7c9e6679-7425-40de-944b-e07fc1f90ae7", "use_default": true },
{ "id": "1ff8a7b5-2c3d-4e6f-8a1b-9c0d2e3f4a5b", "use_default": true },
{ "id": "6fa459ea-ee8a-4ca4-894e-db77e160355e", "use_default": true }
]
}
Example response body
202 Accepted
{
"runs": [
{ "id": "run_abc123", "tool_id": "wf_xyz", "status": "running" },
{ "id": "run_abc124", "tool_id": "wf_xyz", "status": "running" },
{ "id": "run_abc125", "tool_id": "wf_xyz", "status": "running" }
]
}
Poll for status
Pass every run ID to a single GET runs call. Each run finishes on its own, so one response can carry runs at different statuses.
GET https://developer.api.weavy.ai/v1/tools/wf_xyz/runs?run_ids=run_abc123,run_abc124,run_abc125
{
"runs": [
{
"id": "run_abc123",
"tool_id": "wf_xyz",
"status": "completed",
"created_at": "2026-05-06T10:00:00Z",
"completed_at": "2026-05-06T10:00:40Z",
"outputs": [
{
"id": "b3f9c2a1-7d4e-4f86-a0b5-2e8c91d4f7a6",
"name": "Hero image",
"assets": [
{ "type": "image", "url": "https://cdn.figma.com/variation-1.png" }
]
}
]
},
{
"id": "run_abc124",
"tool_id": "wf_xyz",
"status": "completed",
"created_at": "2026-05-06T10:00:00Z",
"completed_at": "2026-05-06T10:00:44Z",
"outputs": [
{
"id": "b3f9c2a1-7d4e-4f86-a0b5-2e8c91d4f7a6",
"name": "Hero image",
"assets": [
{ "type": "image", "url": "https://cdn.figma.com/variation-2.png" }
]
}
]
},
{
"id": "run_abc125",
"tool_id": "wf_xyz",
"status": "running",
"progress_percentage": 70,
"created_at": "2026-05-06T10:00:00Z"
}
],
"workspace_credits_remaining": 830
}
Run a tool with an iterator
wf_xyz's Colors input (6fa459ea-ee8a-4ca4-894e-db77e160355e) is an iterator. Running it with 3 values — ["red", "green", "blue"] — fans the run out over its one output node, "Hero image", producing one output entry per iteration.
HTTP endpoint
GET https://developer.api.weavy.ai/v1/tools/wf_xyz/runs?run_ids=run_abc123
Example response body
{
"runs": [
{
"id": "run_abc123",
"tool_id": "wf_xyz",
"status": "completed",
"created_at": "2026-05-06T10:00:00Z",
"completed_at": "2026-05-06T10:01:30Z",
"outputs": [
{
"id": "b3f9c2a1-7d4e-4f86-a0b5-2e8c91d4f7a6",
"name": "Hero image",
"iteration_index": 0,
"assets": [
{ "type": "image", "url": "https://cdn.figma.com/red.png" }
]
},
{
"id": "b3f9c2a1-7d4e-4f86-a0b5-2e8c91d4f7a6",
"name": "Hero image",
"iteration_index": 1,
"assets": [
{ "type": "image", "url": "https://cdn.figma.com/green.png" }
]
},
{
"id": "b3f9c2a1-7d4e-4f86-a0b5-2e8c91d4f7a6",
"name": "Hero image",
"iteration_index": 2,
"assets": [
{ "type": "image", "url": "https://cdn.figma.com/blue.png" }
]
}
]
}
],
"workspace_credits_remaining": 820
}
In this example:
- For a tool with N output nodes and M iterations, the
outputsarray has N×M entries. Group entries by(id, iteration_index). iteration_indexmatches the order of the iterator values in the run request, so index0is"red",1is"green", and2is"blue".iteration_indexis only present when the output comes from an iterator branch. Outputs on branches without an iterator omit the field entirely.- With a single iterator,
iteration_indexis positional, as above. For a tool with more than one iterator it identifies the branch without being a position you can decode, so group outputs by(id, iteration_index)rather than deriving which value produced which. The iterator mode is fixed by the tool, not chosen in the request.
Upload a file and run a tool on it
A media input can take a file you upload to Weave instead of a URL the API fetches. Uploading takes three calls — POST uploads to get a write URL, a PUT of the file to that URL, then POST commit — after which the asset_id can be used as a run input.
The PUT is the only call in the Weave API that does not go to developer.api.weavy.ai: it goes to the storage service, and the URL carries its own authorization. Do not send your X-Figma-Token with it.
Initiate the upload
POST https://developer.api.weavy.ai/v1/assets/uploads
Headers
X-Figma-Token: [WEAVE API TOKEN]
Content-Type: application/json
Declare the file's exact size in bytes and its content type. The write URL is signed for both values, so anything that does not match them is rejected at upload time.
Example request body
{
"file_name": "panda.png",
"file_size": 182734,
"content_type": "image/png"
}
Example response body
{
"asset_id": "9c85f3a1-2d47-4b6e-8f10-5a3c7d9e1b24",
"upload_url": "https://storage.figma.com/weave-uploads/...",
"content_type": "image/png",
"expires_at": "2026-05-06T22:00:00Z"
}
upload_url is valid until expires_at, 12 hours after it is issued. If it expires before the file is uploaded, initiate a new upload.
Available content types
content_type must be one of the accepted content types on the endpoints page, which also gives the maximum file size.
Upload the file
PUT https://storage.figma.com/weave-uploads/...
Headers
Content-Type: image/png
If-None-Match: *
Both headers are required, and Content-Type must be exactly the content_type from the initiate response. If-None-Match: * is always the literal *; it makes the write fail rather than overwrite if something is already stored there.
Example request
curl -X PUT "https://storage.figma.com/weave-uploads/..." \
-H "Content-Type: image/png" \
-H "If-None-Match: *" \
--data-binary @panda.png
A successful upload returns 200 with an empty body. Note that:
- The body must be exactly the
file_sizeyou declared.Content-Lengthis part of the signature, so send the file as a single sized body — a client that streams it withTransfer-Encoding: chunkedwill be rejected. - The URL works once. A second
PUTto the same URL fails. - The file is not usable yet. Until it is committed, the
asset_idis rejected as a run input.
Commit the upload
POST https://developer.api.weavy.ai/v1/assets/uploads/9c85f3a1-2d47-4b6e-8f10-5a3c7d9e1b24/commit
Headers
X-Figma-Token: [WEAVE API TOKEN]
There is no request body. The call verifies that what landed matches what was declared, then marks the asset committed. It is idempotent, so committing twice returns the same response.
Example response body
{
"asset_id": "9c85f3a1-2d47-4b6e-8f10-5a3c7d9e1b24",
"status": "committed"
}
A 409 here means the file has not been uploaded yet — retry once the PUT succeeds — or that the upload was rejected because it did not match what was declared, in which case start a new upload.
Run a tool with the asset
Pass the asset_id on the media input instead of a value URL. kind can be left out — it comes from the content_type the asset was uploaded with.
wf_abc, the Product shot upscaler from the GET tools example, takes two inputs: a media input for the photo, and a string prompt. Both are set below.
POST https://developer.api.weavy.ai/v1/tools/wf_abc/runs
Example request body
{
"inputs": [
{
"id": "5e1b9c47-3a2d-4e88-9f7c-1b6a0d4e8352",
"value": { "type": "media", "asset_id": "9c85f3a1-2d47-4b6e-8f10-5a3c7d9e1b24" }
},
{
"id": "8c3f6d21-7e94-4a05-b8d3-2f1e9a7c4b60",
"value": { "type": "string", "value": "make the background a snowy forest" }
}
]
}
Example response body
202 Accepted
{
"runs": [
{
"id": "run_abc789",
"tool_id": "wf_abc",
"status": "running"
}
]
}
Poll GET runs from here as in the first example. A committed asset can be reused across runs — upload once, then reference the same asset_id on as many runs as you like.
Handle a failed run
The run-level status is failed when the run encounters an error, such as a quota exhausted at validation time or a model blocked for the workspace. The error is reported in the run's error field, and no outputs are produced.
Example response body
{
"runs": [
{
"id": "run_runlevel_fail",
"tool_id": "wf_xyz",
"status": "failed",
"created_at": "2026-05-07T10:00:00Z",
"completed_at": "2026-05-07T10:00:01Z",
"outputs": [],
"error": {
"message": "flux-pro is blocked for use. Contact your admin."
}
}
],
"workspace_credits_remaining": 850
}
In this example, outputs is empty because no outputs were produced, and the error field carries the reason the run failed.