Generate Canvas Assets

Generate pending node images and/or transition videos for your canvas. One call kicks off all requested jobs and returns a summary of what was queued, skipped, already complete, and reverse/free. Use dry_run: true first to preview planned work, prompts, and credit cost without spending credits.

curl -X POST https://api.masko.ai/v1/collections/COLLECTION_ID/canvases/CANVAS_ID/generate-all \
  -H "Authorization: Bearer masko_YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "dry_run": true,
    "targets": "animations",
    "skip_completed": true,
    "duration": 4
  }'

How It Works

The endpoint scans the canvas and dispatches missing node images and/or edge videos based on targets. The skip_completed parameter defaults to true, meaning graph parts that already have assigned assets are skipped so running the endpoint twice does not duplicate in-flight or completed work.

The response separates generation accounting into:

  • dry_run: true when no jobs/assets were created and no credits were deducted.
  • planned_jobs: node, sticker, and edge work that would be queued, including prompts. Planned animation and sticker jobs include signed source/target asset URLs when those input images already exist; media that would be generated by the run is represented by its prompt and cost, not a fake preview URL.
  • generated: newly queued node or edge jobs.
  • skipped: legacy skipped edge count.
  • skipped_items: graph parts not queued, including target-filtered nodes/edges and graph parts with existing asset IDs.
  • reverse_free: reverse edges that cost 0 credits because they reuse a forward transition.
  • already_complete: nodes and edges whose assigned assets are already completed.
  • estimated_cost: cost calculated before dispatch.
  • actual_cost: credits deducted for this request.
  • would_charge_credits: dry-run estimate for the credits a real request would deduct.

Each generated job follows the same lifecycle as a regular animation job - you can poll individual jobs or read the status field on the canvas detail response to track overall progress.

Edge Classification

Not all edges cost the same. The endpoint classifies each edge before generation:

TypeConditionCostNotes
Loopsource == targetPaidLooping animation on a single pose
Forwardsource != targetPaidTransition from one pose to another
ReverseAuto-generated from forward0 creditsTriggered automatically when forward completes
Any Statesource = "*"SkippedVirtual edges resolved at runtime, no video needed

Cost Calculation

Only loops and forward transitions cost credits. The formula is:

(loops + forwards) x 5 x duration

For example, a canvas with 4 loop edges and 3 forward edges at 4 seconds each:

Paid edges: 4 loops + 3 forwards = 7
Cost per edge: 5 credits/sec x 4 sec = 20 credits
Total: 7 x 20 = 140 credits

Reverse edges (auto): 3 (one per forward) = 0 credits
Any State edges: skipped = 0 credits

The response includes estimated_cost, actual_cost, and legacy total_cost fields so you know the exact cost. If you do not have enough credits, the request returns a 402 error with the required amount.

This endpoint returns 200 OK with the list of queued jobs - generation runs asynchronously.

Auto-Reverse

When a forward transition completes (e.g. Idle to Waving), the reverse transition (Waving to Idle) is automatically triggered at 0 credits. You do not need to request it separately. The reverse job appears in the canvas status response alongside the forward jobs.

If a forward edge already has a matching reverse edge in the canvas, the auto-reverse fills in the reverse edge video. If no reverse edge exists, one is created automatically.

Poll Progress

After kicking off generation, fetch the canvas and read the status field to track overall progress:

curl https://api.masko.ai/v1/collections/COLLECTION_ID/canvases/CANVAS_ID \
  -H "Authorization: Bearer masko_YOUR_API_KEY"

# Response:
# {
#   "data": {
#     "id": "abc-123",
#     "graph": { ... },
#     "status": {
#       "nodes": { "total": 4, "completed": 4, "pending": 0 },
#       "edges": { "total": 14, "completed": 10, "pending": 3, "failed": 1 },
#       "ready": false,
#       "failed_edges": []
#     }
#   }
# }
Tip

When status.media.generation.ready is true, every node image and every non-Any-State edge video has a completed parent asset. Assigned pending asset IDs do not count as ready. For editor playback, wait for status.media.preview.ready; if status.media.preview.waiting_edges > 0, keep polling, and if status.media.preview.repairable is true, dry-run preview-media repair.

Regenerate a Single Edge

To re-run one edge without re-dispatching the whole canvas, use the per-edge endpoint:

curl -X POST https://api.masko.ai/v1/collections/COLLECTION_ID/canvases/CANVAS_ID/edges/EDGE_ID/generate \
  -H "Authorization: Bearer masko_YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "duration": 4
  }'

The endpoint returns 202 Accepted and a job_id. Only non-reverse edges can be dispatched individually. Poll the job as usual.

Use this when one edge failed or you updated the edge prompt and want to regenerate it without spending credits on the rest of the canvas.