tiktok_shop_video and tiktok_shop_photo.
Before you start
- Send your organization API key in
Authorization: Bearer .... - The key creator must remain a workspace member with access to the selected TikTok Shop connection.
- Media preparation and new submissions require an active Pro or higher plan and publishing enabled for your workspace.
- Video submissions use your API wallet. See current pricing. Photo submissions, reads, media preparation, and cancellation are free.
Publishing returns a task with
task_id and kind. Read it through /publishing/tasks/{kind}/{task_id}. The generation and cleaning /jobs endpoints do not track publishing tasks.Find a connection and product
data array. Select its connection_uid, then inspect the connection and its capabilities:
For products, use
query, source=showcase|shop, and eligibility=publishable|addable|all. The default eligibility is publishable. page_size defaults to 20 and accepts 1–100. page_token is a numeric offset. Set include_total=true when you need a total.
For music, provide exactly one of query or url. Keyword searches accept search_id, page_token, region, language, and page_size (1–50, default 20). URL lookup does not accept search pagination or locale overrides.
For photo destinations, pass type=category or type=collection. Only collection lookup accepts page_token. Query parameters must not be repeated.
Upload and prepare a video
Follow the Files upload flow to upload your video. Complete the multipart upload before preparing it. Publishing accepts the returnedfile_id, not a URL or storage path. To publish a generated video, download its result and upload the file through this flow.
Replace the example file ID and connection UID with your own values:
200 response contains id, kind, connection_uid, and status: "prepared". Save the pm_... ID as prepared_video_id. A prepared ID belongs to one workspace, connection, and media kind.
For a custom cover, upload an image and repeat this request with kind: "cover". Save its ID as prepared_cover_id. Do not send cover_uri in a submission.
Submit a video
Save a new idempotency key before submitting. Replace the connection UID, prepared media ID, and product ID below with values from the preceding steps.202 response is the publishing task. Acceptance does not mean the video has been published. Save kind and task_id for polling.
Use snake_case for all publishing request fields, including nested provider_options fields. Unknown options are rejected.
media.prepared_video_id is required for video. You may also include media.prepared_cover_id. Do not include media.file_ids for video.
Submit a photo set
Upload each image through Files. Submit their file IDs directly; photo sets do not use/publishing/media.
Send this body to POST /publishing/tasks with a fresh Idempotency-Key:
title (up to 5,000 characters), is_ai_generated, and selected_music in addition to the fields for the selected post_type:
For category and collection links, include
shop_link.group_id from destination discovery. Omit it for MAIN_PAGE. Only collection links accept shop_link.page_token.
Schedule publishing
timezone is required even for immediate submissions. Use an enum value from the API reference, such as EST or GMT+8.
Omit schedule to submit immediately. For a scheduled submission, set schedule.at to a future Unix timestamp in milliseconds. It must be at least 60 seconds in the future and no more than 30 days in the future. Compute it when you submit; do not reuse an old timestamp.
Track and cancel tasks
Follow
Retry-After when present. The API suggests 10 seconds for queued, scheduled, running, and unknown tasks. Task timestamps (created_at, schedule_time, and completed_at) use Unix milliseconds; the latter two may be null. publish_job_id may be null for older tasks.
List tasks with GET /publishing/tasks?kind=tiktok_shop_video. kind is required. Optional filters include connection_uid, client_source, status, created_after_ms, and created_before_ms. Pagination uses page (default 1) and page_size (1–100, default 20). The response contains data, page, page_size, total, and has_more.
Lists include authorized tasks across creation sources. Set client_source=openapi to select API-created tasks. Use client_source=unknown for tasks without a recorded source.
Cancel an eligible unsent task with POST /publishing/tasks/{kind}/{task_id}/cancel. No body is required. A task that can no longer be canceled returns 409 with task_not_cancellable. Cancellation cannot remove an already published post.
cost.amount_usd and cost.refunded_usd show booked wallet transactions as six-decimal USD strings. Confirmed failures and eligible cancellations refund the original charge. An unknown outcome does not trigger an automatic resend or refund.
Recover an interrupted submission
Publishing idempotency keys are scoped to your workspace across organization API keys. Repeating the same key and body returns the current original task with HTTP202, including failed tasks. Reusing a key with a different body returns 409 with idempotency_key_reused.
If submission times out or the result cannot be read, recover with the original key:
task_not_found when it cannot find the attempt, or result_unavailable when an accepted attempt cannot currently be read.
Rate limits and errors
Publishing defaults to 120 read requests and 30 write requests per minute per workspace. Workspace-specific limits can differ. On429, follow Retry-After before retrying.
Errors use the standard error format. Common codes include plan_required, permission_denied, connection_not_found, capability_disabled, invalid_media_reference, invalid_parameter, and publishing_rejected. A 503 with service_unavailable indicates temporary admission unavailability; follow its Retry-After header.
