# Wan 2.7 API Wan 2.7: reliable Tongyi Wanxiang video with first/last-frame control, 2–15 s, 720p/1080p. Base URL: https://01router.com/api/v1 Model ID: wan-2.7 Documentation: https://01router.com/gateway/wan-2.7#api ## Quick start Set API_KEY to your project key, then run a sample from your server. Replace example media URLs with your own public URLs. ```bash export API_KEY="YOUR_API_KEY" curl "https://01router.com/api/v1/generations" \ -H "Authorization: Bearer $API_KEY" \ -H "Content-Type: application/json" \ --data-binary @- <<'JSON' { "model": "wan-2.7", "input": { "prompt": "A cinematic shot of a red fox running through snow", "duration": 5, "resolution": "720p", "aspect_ratio": "16:9" } } JSON ``` ## Endpoints | Method | Path | Authentication | Description | | --- | --- | --- | --- | | POST | /api/v1/generations | API key required | Create a generation (charges credits) | | GET | /api/v1/generations/{id} | API key required | Get a generation; polls the provider while running | | POST | /api/v1/generations/{id}/cancel | API key required | Cancel a running generation (credits refunded) | | POST | /api/v1/quote | Public · no key | Price a request on every provider (no charge, no key needed) | | GET | /api/v1/models/wan-2.7 | Public · no key | Get one model | ## Authentication Send your API key as a Bearer token. Requests are billed to the key owner's credits. `Authorization: Bearer ` ## Input Send JSON with Content-Type: application/json. Model parameters belong inside input; model, provider and callback_url are top-level fields. | Name | Type | Required | Description | | --- | --- | --- | --- | | model | string | Yes | "wan-2.7" | | provider | string | No | Pin a provider; omit to auto-route to the cheapest. One of: fal \| replicate \| wavespeed \| apimart \| evolink \| atlascloud \| vercel | | input | object | Yes | Model parameters, see the input fields below. | | callback_url | string | No | Optional public HTTPS webhook URL. The final task result is signed and delivered here; polling remains available. | ### input Required fields are marked explicitly. Other fields use the listed defaults when omitted. | Name | Type | Required | Description | Default | | --- | --- | --- | --- | --- | | input.prompt | string | Yes | Prompt | — | | input.negative_prompt | string | No | Negative prompt | — | | input.image_url | string | No | Optional start image (image-to-video) | — | | input.end_image_url | string | No | Last frame | — | | input.duration | integer | No | Duration (s); min: 2; max: 15 | 5 | | input.resolution | string | No | Resolution; options: ["720p","1080p"] | "720p" | | input.aspect_ratio | string | No | Aspect ratio; options: ["16:9","9:16","1:1","4:3","3:4"] | "16:9" | | input.seed | integer | No | Seed; min: 0; max: 2147483647 | — | Auto-routing chooses a provider that supports the request. Select a provider to see its input constraints and pinned request examples. ### Provider input schemas ```json [ { "provider": "fal", "params": [ { "name": "prompt", "type": "text", "label": "Prompt", "required": true }, { "name": "negative_prompt", "type": "string", "label": "Negative prompt" }, { "name": "image_url", "type": "image", "label": "First frame", "description": "Optional start image (image-to-video)" }, { "name": "end_image_url", "type": "image", "label": "Last frame" }, { "name": "duration", "type": "integer", "label": "Duration (s)", "min": 2, "max": 15, "default": 5 }, { "name": "resolution", "type": "enum", "label": "Resolution", "options": [ "720p", "1080p" ], "default": "720p" }, { "name": "aspect_ratio", "type": "enum", "label": "Aspect ratio", "options": [ "16:9", "9:16", "1:1", "4:3", "3:4" ], "default": "16:9" }, { "name": "seed", "type": "integer", "label": "Seed", "min": 0, "max": 2147483647 } ] }, { "provider": "replicate", "params": [ { "name": "prompt", "type": "text", "label": "Prompt", "required": true }, { "name": "negative_prompt", "type": "string", "label": "Negative prompt" }, { "name": "image_url", "type": "image", "label": "First frame", "description": "Optional start image (image-to-video)" }, { "name": "end_image_url", "type": "image", "label": "Last frame" }, { "name": "duration", "type": "integer", "label": "Duration (s)", "min": 2, "max": 15, "default": 5 }, { "name": "resolution", "type": "enum", "label": "Resolution", "options": [ "720p" ], "default": "720p" }, { "name": "aspect_ratio", "type": "enum", "label": "Aspect ratio", "options": [ "16:9", "9:16", "1:1", "4:3", "3:4" ], "default": "16:9" }, { "name": "seed", "type": "integer", "label": "Seed", "min": 0, "max": 2147483647 } ] }, { "provider": "wavespeed", "params": [ { "name": "prompt", "type": "text", "label": "Prompt", "required": true }, { "name": "negative_prompt", "type": "string", "label": "Negative prompt" }, { "name": "image_url", "type": "image", "label": "First frame", "description": "Optional start image (image-to-video)" }, { "name": "end_image_url", "type": "image", "label": "Last frame" }, { "name": "duration", "type": "integer", "label": "Duration (s)", "min": 2, "max": 15, "default": 5 }, { "name": "resolution", "type": "enum", "label": "Resolution", "options": [ "720p", "1080p" ], "default": "720p" }, { "name": "aspect_ratio", "type": "enum", "label": "Aspect ratio", "options": [ "16:9", "9:16", "1:1", "4:3", "3:4" ], "default": "16:9" }, { "name": "seed", "type": "integer", "label": "Seed", "min": 0, "max": 2147483647 } ] }, { "provider": "apimart", "params": [ { "name": "prompt", "type": "text", "label": "Prompt", "required": true }, { "name": "negative_prompt", "type": "string", "label": "Negative prompt" }, { "name": "duration", "type": "integer", "label": "Duration (s)", "min": 2, "max": 15, "default": 5 }, { "name": "resolution", "type": "enum", "label": "Resolution", "options": [ "720p", "1080p" ], "default": "720p" }, { "name": "aspect_ratio", "type": "enum", "label": "Aspect ratio", "options": [ "16:9", "9:16", "1:1", "4:3", "3:4" ], "default": "16:9" }, { "name": "seed", "type": "integer", "label": "Seed", "min": 0, "max": 2147483647 } ] }, { "provider": "evolink", "params": [ { "name": "prompt", "type": "text", "label": "Prompt", "required": true }, { "name": "negative_prompt", "type": "string", "label": "Negative prompt" }, { "name": "image_url", "type": "image", "label": "First frame", "description": "Optional start image (image-to-video)" }, { "name": "end_image_url", "type": "image", "label": "Last frame" }, { "name": "duration", "type": "integer", "label": "Duration (s)", "min": 2, "max": 15, "default": 5 }, { "name": "resolution", "type": "enum", "label": "Resolution", "options": [ "720p", "1080p" ], "default": "720p" }, { "name": "aspect_ratio", "type": "enum", "label": "Aspect ratio", "options": [ "16:9", "9:16", "1:1", "4:3", "3:4" ], "default": "16:9" }, { "name": "seed", "type": "integer", "label": "Seed", "min": 0, "max": 2147483647 } ] }, { "provider": "atlascloud", "params": [ { "name": "prompt", "type": "text", "label": "Prompt", "required": true }, { "name": "negative_prompt", "type": "string", "label": "Negative prompt" }, { "name": "image_url", "type": "image", "label": "First frame", "description": "Optional start image (image-to-video)" }, { "name": "end_image_url", "type": "image", "label": "Last frame" }, { "name": "duration", "type": "integer", "label": "Duration (s)", "min": 2, "max": 15, "default": 5 }, { "name": "resolution", "type": "enum", "label": "Resolution", "options": [ "720p" ], "default": "720p" }, { "name": "aspect_ratio", "type": "enum", "label": "Aspect ratio", "options": [ "16:9", "9:16", "1:1", "4:3", "3:4" ], "default": "16:9" }, { "name": "seed", "type": "integer", "label": "Seed", "min": 0, "max": 2147483647 } ] }, { "provider": "vercel", "params": [ { "name": "prompt", "type": "text", "label": "Prompt", "required": true }, { "name": "negative_prompt", "type": "string", "label": "Negative prompt" }, { "name": "duration", "type": "integer", "label": "Duration (s)", "min": 2, "max": 15, "default": 5 }, { "name": "resolution", "type": "enum", "label": "Resolution", "options": [ "720p", "1080p" ], "default": "720p" }, { "name": "aspect_ratio", "type": "enum", "label": "Aspect ratio", "options": [ "16:9", "9:16", "1:1", "4:3", "3:4" ], "default": "16:9" }, { "name": "seed", "type": "integer", "label": "Seed", "min": 0, "max": 2147483647 } ] } ] ``` ## Output Creating a task does not mean generation has finished. Keep its id, poll until succeeded or failed, then read outputs or error. Amounts below are illustrative; actual charges depend on the request. | Name | Type | Required | Description | | --- | --- | --- | --- | | id | string | Yes | Generation ID. Use it to query or cancel this task. | | object | string | Yes | generation | | model | string | Yes | wan-2.7 | | type | string | Yes | video | | provider | string | Yes | Provider | | status | string | Yes | queued → processing → succeeded / failed. Stop polling at either terminal state. | | input | object | Yes | Model parameters, see the input fields below. | | outputs | string[] | Yes | Result URLs. Empty while processing; read after succeeded and save the files promptly. | | error | string \| null | Yes | Failure reason, or null when no failure is reported. | | credits | number | Yes | Credits charged for this request. | | price_usd | number | Yes | Request price in USD. | | created_at | string | Yes | Creation time in ISO 8601 format. | | completed_at | string \| null | Yes | Completion time in ISO 8601 format; null before completion. | ### Task submitted ```json { "id": "gen_example", "object": "generation", "model": "wan-2.7", "type": "video", "provider": "fal", "status": "processing", "input": { "prompt": "A cinematic shot of a red fox running through snow", "duration": 5, "resolution": "720p", "aspect_ratio": "16:9" }, "outputs": [], "error": null, "credits": 0, "price_usd": 0, "created_at": "2026-10-25T08:00:00.000Z", "completed_at": null } ``` ### Task completed ```json { "id": "gen_example", "object": "generation", "model": "wan-2.7", "type": "video", "provider": "fal", "status": "succeeded", "input": { "prompt": "A cinematic shot of a red fox running through snow", "duration": 5, "resolution": "720p", "aspect_ratio": "16:9" }, "outputs": [ "https://example.com/output.mp4" ], "error": null, "credits": 0, "price_usd": 0, "created_at": "2026-10-25T08:00:00.000Z", "completed_at": "2026-10-25T08:01:00.000Z" } ``` ## Get the result Poll every few seconds until status is succeeded or failed. Output URLs are provider-hosted and may expire — download them promptly. Or pass callback_url to get the result pushed. ```bash curl "https://01router.com/api/v1/generations/GENERATION_ID" -H "Authorization: Bearer $API_KEY" ``` ## Cancel a task Cancellation depends on provider support and task state. A confirmed cancellation returns status: failed and error: Canceled by user. Unsupported or completed tasks return 409 not_cancelable. ```bash curl -X POST "https://01router.com/api/v1/generations/GENERATION_ID/cancel" -H "Authorization: Bearer $API_KEY" ``` ## Quote Same body as creating a generation. Returns every available provider sorted by price, plus the ones that cannot serve the request and why. ```bash curl "https://01router.com/api/v1/quote" -H "Content-Type: application/json" --data-binary @- <<'JSON' { "model": "wan-2.7", "input": { "prompt": "A cinematic shot of a red fox running through snow", "duration": 5, "resolution": "720p", "aspect_ratio": "16:9" } } JSON ``` ## Callbacks Optional public HTTPS webhook URL. The final task result is signed and delivered here; polling remains available. See https://01router.com/docs/callback for signature verification. ## Errors Check the HTTP status and error.message. Fix the request before retrying validation or authentication errors. A failed generation is reported in status and error on the task itself. ```json { "error": { "message": "Invalid or missing API key", "code": "unauthorized" } } ``` HTTP 400: invalid request; 401: unauthorized; 402: insufficient credits; 404: not found; 409: not cancelable; 429: rate/concurrency/quota limit; 5xx: upstream/server error. Full API reference: https://01router.com/docs/errors