Schedule, update, publish, and manage posts programmatically across Threads, TikTok, YouTube, X, LinkedIn, Bluesky, Pinterest, Instagram, Facebook, and Reddit.
All API requests require an authenticated session. Sign in at viral-cat.com with your Google account. Requests use cookie-based session authentication (NextAuth).
// All requests must include your session cookie.
// Use the same browser session or forward cookies from your client.
//
// Unauthenticated requests return:
{ "error": "Unauthorized" } // 401Base URL: https://viral-cat.com/api
Create, read, update, and delete scheduled posts. Each post targets one platform.
/api/postsList scheduled posts. Optionally filter by month/year and brand. Add ?summary=true for count + next-scheduled-date only.
month number optional 1-12
year number optional e.g. 2026
brandId string optional filter by brand
summary boolean optional returns count aggregates only{
"success": true,
"scheduledVideos": [
{
"id": 42,
"platform": "youtube",
"caption": "Check this out!",
"scheduledDate": "2026-06-15T07:00:00.000Z",
"status": "scheduled",
"videoFileName": "promo.mp4",
"googleDriveFileId": "1abc...",
"brandId": "brand_123",
"ctaUrl": "https://example.com",
"hashtags": ["#viral", "#ai"]
}
]
}/api/postsSchedule a new post. Creates one row per platform. Platforms that already have a scheduled post for the same brand + day are skipped (dedup). Incompatible media/platform combos are filtered automatically.
{
"caption": "My awesome post",
"scheduledDate": "2026-06-15T07:00:00.000Z",
"scheduledTime": "07:00",
"platforms": ["youtube", "twitter", "threads"],
"googleDriveFileId": "1abc...",
"videoFileName": "promo.mp4",
"ctaUrl": "https://example.com",
"hashtags": ["#viral"],
"brandId": "brand_123"
}{
"success": true,
"posts": [
{ "id": 43, "platform": "youtube", "status": "scheduled" },
{ "id": 44, "platform": "threads", "status": "scheduled" }
]
}
// 402 when monthly post limit reached (includes upgrade URL)/api/postsUpdate a scheduled post. Only posts with status 'scheduled' can be edited. Returns 409 if the post has already been published or is currently posting.
{
"id": 43,
"caption": "Updated caption",
"scheduledDate": "2026-06-16T09:00:00.000Z",
"scheduledTime": "09:00",
"platform": "youtube",
"ctaUrl": "https://example.com",
"hashtags": ["#updated"],
"videoFileName": "promo.mp4",
"googleDriveFileId": "1abc..."
}{
"success": true,
"scheduledVideo": { "id": 43, "status": "scheduled" }
}
// 409 if post is not in "scheduled" status/api/posts?id=43Delete a scheduled post by ID. Drive files are never deleted; only the DB row is removed.
{
"success": true,
"message": "Scheduled video deleted successfully"
}/api/postsBatch assign a brand to multiple posts (up to 500).
{
"ids": [43, 44, 45],
"brandId": "brand_123"
}{ "success": true, "updated": 3 }Trigger immediate publishing. Server-side rate limiting (5s per platform) is enforced automatically.
/api/posts/publishPublish a post immediately. Accepts scheduled, posting (resume), and failed (retry) statuses. Returns 422 on publish failure with error details.
{ "videoId": 43 }// Success
{
"success": true,
"result": { "success": true, "postUrl": "https://..." }
}
// Failure (422)
{
"success": false,
"result": { "success": false, "error": "Token expired" }
}Skip auto-posting for a brand on a specific day, or restore a previously skipped day.
/api/posts/skipSkip a brand's auto-post for a given day. Idempotent: re-skipping the same day is a no-op.
{
"brandId": "brand_123",
"date": "2026-06-15"
}{ "success": true, "created": 1 }/api/posts/skipRestore a skipped day. Cancelled posts are re-scheduled; skip markers are removed.
{
"brandId": "brand_123",
"date": "2026-06-15"
}{ "success": true, "restored": 1, "deleted": 0 }Manage multi-platform post bundles. A bundle is a group of posts sharing the same content, scheduled for the same day across different platforms.
/api/posts/bundleUpdate a bundle. Provide the full desired state: existing posts are updated, new platforms are added, and removed platforms are deleted. Orphan rows from race conditions are cleaned up automatically.
{
"postIds": [43, 44],
"caption": "Shared caption across platforms",
"ctaUrl": "https://example.com",
"platforms": [
{ "postId": 43, "platform": "youtube", "scheduledDate": "2026-06-15T07:00:00Z" },
{ "postId": 44, "platform": "threads", "scheduledDate": "2026-06-15T07:00:00Z" },
{ "platform": "twitter", "scheduledDate": "2026-06-15T07:00:00Z" }
]
}{ "success": true }/api/posts/bundleDelete all posts in a bundle.
{ "postIds": [43, 44, 45] }{ "success": true, "deleted": 3 }Check connection status for all linked platforms.
/api/platforms/statusGet connection status for all platforms. Returns which platforms are connected, token validity, and last-checked timestamps.
{
"statuses": {
"youtube": { "connected": true, "valid": true },
"tiktok": { "connected": true, "valid": true },
"twitter": { "connected": false }
}
}/api/platforms/statusRun a health check across all connected platforms. Validates tokens and refreshes expired ones.
{
"health_check": {
"youtube": { "healthy": true },
"tiktok": { "healthy": true, "refreshed": true }
}
}TikTok posts are published as inbox drafts. Poll for approval status.
/api/posts/tiktok-statusCheck the status of pending TikTok drafts. Updates post URLs when drafts are approved and published. Marks posts as failed if TikTok rejects them.
{
"updated": 1,
"pending": 2,
"results": [
{ "id": 50, "status": "PUBLISHED", "url": "https://tiktok.com/..." },
{ "id": 51, "status": "PROCESSING_DOWNLOAD" }
]
}YouTube
Video
TikTok
Video (draft)
Image, Video
Threads
Image, Video, Text
X
Text (OG card)
Image, Video
Bluesky
Image, Text
Image
Image, Video
Text, Link
5-second per-platform delay enforced server-side. No client-side throttling needed.
Monthly post limits are enforced per subscription tier. A 402 response includes an upgradeUrl.
400Bad request / missing fields401Not authenticated402Plan limit reached404Post not found409Post not editable (already published / posting)422Publish failed (platform error)500Internal error