Upscale Videos

January 20, 2026 (February 27, 2026)

Table of contents

  1. Request Headers
  2. Request Body
  3. Responses
  4. Model
  5. Examples
  6. Try It

Upscale a previously generated video to 1080p or 4K resolution.

  • Currently, video upscaling requires a paid Google AI subscription or remaining credits.
  • Currently, 4K resolution requires a Google AI Ultra subscription. Other paid accounts can only use 1080p resolution.
  • 1080p upscaling is free. 4K upscaling currently costs 50 credits.
  • Video upscaling typically completes within 30-60 seconds, with 4K taking a few minutes.
  • Upscaling the same video twice returns a cached result (no additional credits consumed). Use the video URL from the first upscale response.

https://api.useapi.net/v1/google-flow/videos/upscale

Request Headers

Authorization: Bearer {API token}
Content-Type: application/json
# Alternatively you can use multipart/form-data
# Content-Type: multipart/form-data

Request Body

{
  "mediaGenerationId": "user:12345-email:6a6f...-video:CAMaJDMx...",
  "resolution": "1080p"
}
  • mediaGenerationId is required. The mediaGenerationId from a previously generated video via POST /videos.
  • resolution is optional. Target resolution for upscaling (default: 1080p).
    Supported values: 1080p, 4K.
  • async is optional, enables fire-and-forget mode (default: false).
    When true, returns immediately with 201 Created and job metadata. Poll GET /jobs/jobId for completion status.
  • replyUrl is optional, webhook URL for job status callbacks.
    Receives POST requests with job status updates (created, started, completed, failed). The JSON payload shape matches GET /jobs/jobId response.
  • replyRef is optional, custom reference string passed back in webhook callbacks.
  • captchaToken, captchaRetry, captchaOrder are optional, mutually exclusive captcha parameters. See Captcha Parameters for details.

Responses

  • 200 OK

    Video upscaled successfully. Returns job ID, media array with video data, and operations array (deprecated) with upscaled video URLs.

    {
      "jobId": "j1737312345678v-u12345-email:jo***@gmail.com-bot:google-flow",
      "media": [
        {
          "name": "CAUSJ...redacted...OWQ5ZA",
          "projectId": "...redacted...",
          "mediaMetadata": {
            "mediaStatus": {
              "mediaGenerationStatus": "MEDIA_GENERATION_STATUS_SUCCESSFUL"
            }
          },
          "video": {
            "generatedVideo": {
              "seed": 987654321,
              "model": "veo_3_1_upsampler_1080p",
              "aspectRatio": "VIDEO_ASPECT_RATIO_LANDSCAPE",
              "isLooped": false
            },
            "operation": {
              "name": "d00af...redacted...6f7a"
            }
          },
          "mediaGenerationId": "user:12345-email:6a6f...-video:CAUSJ...redacted",
          "videoUrl": "https://storage.googleapis.com/ai-sandbox-videofx/video/...redacted..."
        }
      ],
      "operations": [
        {
          "operation": {
            "name": "d00af...redacted...6f7a",
            "metadata": {
              "@type": "type.googleapis.com/google.internal.labs.aisandbox.v1.Media",
              "name": "CAUSJ...redacted...OWQ5ZA",
              "video": {
                "seed": 987654321,
                "mediaGenerationId": "user:12345-email:6a6f...-video:CAUSJ...redacted",
                "prompt": "Original video prompt",
                "fifeUrl": "https://storage.googleapis.com/ai-sandbox-videofx/video/...redacted...",
                "mediaVisibility": "PRIVATE",
                "servingBaseUri": "https://storage.googleapis.com/ai-sandbox-videofx/image/...redacted...",
                "model": "veo_3_1_upsampler_1080p",
                "isLooped": false,
                "aspectRatio": "VIDEO_ASPECT_RATIO_LANDSCAPE"
              }
            }
          },
          "sceneId": "323c0...redacted...3ebf6",
          "mediaGenerationId": "user:12345-email:6a6f...-video:CAUSJ...redacted",
          "status": "MEDIA_GENERATION_STATUS_SUCCESSFUL"
        }
      ],
      "remainingCredits": 18760,
      "captcha": {
        "service": "AntiCaptcha",
        "taskId": "abc123...",
        "durationMs": 3500,
        "attempts": [
          {
            "service": "AntiCaptcha",
            "taskId": "abc123...",
            "durationMs": 3500,
            "success": true
          }
        ]
      }
    }
    
  • 201 Created

    Job created in async mode (async: true). Video upscaling is processing in the background.

    Use GET /jobs/jobId to poll for completion status.

    {
      "jobid": "j1737312345678v-u12345-email:jo***@gmail.com-bot:google-flow",
      "type": "video",
      "status": "created",
      "created": "2026-01-19T12:34:56.789Z",
      "request": {
        "async": true,
        "mediaGenerationId": "user:12345-email:6a6f...-video:CAMaJDMx...",
        "resolution": "1080p"
      },
      "response": {
        "operations": [
          {
            "operation": {
              "name": "1450903d...redacted...9c86f0"
            },
            "sceneId": "1450903d...redacted...9c86f0",
            "status": "MEDIA_GENERATION_STATUS_PENDING"
          }
        ],
        "captcha": {
          "service": "AntiCaptcha",
          "taskId": "14af1dbb-885c-4e25-8121-7a79489dfd0e",
          "durationMs": 5357
        }
      }
    }
    
  • 400 Bad Request

    Invalid request.

    {
      "error": "Error message"
    }
    
  • 401 Unauthorized

    Invalid API token.

    {
      "error": "Unauthorized"
    }
    
  • 403 Forbidden

    Request rejected by Google.

    Recommendations:

    • Ensure captchaRetry is set to at least 3 (default). Try increasing to a higher value (e.g., 5) to see if that helps
    • If issues persist, contact useapi.net support
    {
      "error": {
        "code": 403,
        "details": [
          {
            "@type": "type.googleapis.com/google.rpc.ErrorInfo",
            "reason": "PUBLIC_ERROR_SOMETHING_WENT_WRONG"
          }
        ],
        "message": "reCAPTCHA evaluation failed",
        "status": "PERMISSION_DENIED"
      },
      "captcha": {
        "service": "AntiCaptcha",
        "taskId": "ab0251dc-6930-4a82-966a-71fe6ab6aa42",
        "durationMs": 5789,
        "attempts": [
          {
            "service": "AntiCaptcha",
            "taskId": "ab0251dc-6930-4a82-966a-71fe6ab6aa42",
            "durationMs": 5789,
            "success": true
          }
        ]
      }
    }
    
  • 404 Not Found

    Account not found or video not found.

    {
      "error": "Google Flow account [email protected] not found"
    }
    
  • 408 Request Timeout

    Video upscaling polling timeout (after 10 minutes).

    {
      "error": "Polling timeout"
    }
    

Model

  • Video upscaling completed. Returns upscaled video data with signed URLs. Re-upscaling the same video returns rawBytes (base64 video data) instead of URLs.

    {
      jobId: string                              // Job identifier
      media: Array<{                             // Preferred — use this instead of operations
        name: string                             // Media identifier (raw UUID)
        projectId: string
        mediaMetadata: {
          mediaStatus: {
            mediaGenerationStatus: string        // MEDIA_GENERATION_STATUS_SUCCESSFUL | FAILED
            error?: { code: number; message: string }
          }
          visibility?: string
        }
        video?: {
          generatedVideo: {
            seed: number
            model: string                        // veo_3_1_upsampler_1080p | veo_3_1_upsampler_4k
            aspectRatio: string                  // VIDEO_ASPECT_RATIO_LANDSCAPE | PORTRAIT
            isLooped: boolean
          }
          operation: { name: string }
        }
        mediaGenerationId: string                // Encoded reference ID for use in subsequent API calls
        videoUrl?: string                        // Signed video download URL (MP4, valid ~24h)
      }>
      operations: Array<{                        // Deprecated — will be removed in a future release
        operation?: {
          name: string
          metadata: {
            '@type': string
            name: string
            video: {
              seed: number
              mediaGenerationId: string          // Reference ID for the upscaled video
              prompt: string                     // Original video prompt
              fifeUrl: string                    // Signed video URL (MP4, valid ~24h)
              mediaVisibility: string
              servingBaseUri: string             // Signed thumbnail URL (JPEG, valid ~24h)
              model: string                      // veo_3_1_upsampler_1080p | veo_3_1_upsampler_4k
              isLooped: boolean
              aspectRatio: string                // VIDEO_ASPECT_RATIO_LANDSCAPE | PORTRAIT
            }
          }
        }
        rawBytes?: string                        // Base64 video data (present when re-upscaling same video)
        sceneId: string
        mediaGenerationId: string
        status: string                           // MEDIA_GENERATION_STATUS_SUCCESSFUL | FAILED
      }>
      remainingCredits?: number
      captcha?: {                                // Captcha metadata
        service: string                          // "CapSolver" | "AntiCaptcha" | "YesCaptcha" | "CapMonster" | "SolveCaptcha" | "2Captcha" | "EzCaptcha" | "UserProvided"
        taskId?: string
        durationMs: number
        attempts: Array<{
          service: string
          taskId?: string
          durationMs: number
          success: boolean
          error?: string
        }>
      }
    }
    
  • Job created and processing in background. Structure matches GET /jobs/jobId response.

    {
      jobid: string                              // Job identifier
      type: 'video'                              // Job type
      status: 'created'                          // Job status
      created: string                            // ISO 8601 timestamp
      request: {
        async: true
        mediaGenerationId: string                // Original video reference
        resolution?: string                      // "1080p" | "4K"
        replyUrl?: string
        replyRef?: string
      }
      response: {
        operations: Array<{
          operation: {
            name: string                         // Operation identifier
          }
          sceneId: string                        // Scene identifier
          status: 'MEDIA_GENERATION_STATUS_PENDING'
        }>
        captcha?: {                              // Present when captcha was used
          service: string                        // Provider or "UserProvided"
          taskId?: string                        // Absent for UserProvided
          durationMs: number
        }
      }
    }
    
  • Error response structure.

    {
      jobId?: string                             // Present for job-related errors
      error: string                              // Error summary message
      code?: number                              // HTTP status code
      response?: {                               // API response with error details
        error?: {
          code: number
          message: string
          status: string
          details?: Array<{
            '@type': string
            reason: string
          }>
        }
      }
    }
    

Examples

  • # First generate a video
    curl -X POST \
         -H "Authorization: Bearer YOUR_API_TOKEN" \
         -H "Content-Type: application/json" \
         -d '{"prompt": "A serene mountain landscape at sunset"}' \
         "https://api.useapi.net/v1/google-flow/videos" > generate.json
    
    # Extract mediaGenerationId from the response (prefer media[] over deprecated operations[])
    MEDIA_ID=$(jq -r '.media[0].mediaGenerationId' generate.json)
    
    # Upscale the video to 1080p
    curl -X POST \
         -H "Authorization: Bearer YOUR_API_TOKEN" \
         -H "Content-Type: application/json" \
         -d "{\"mediaGenerationId\": \"$MEDIA_ID\", \"resolution\": \"1080p\"}" \
         "https://api.useapi.net/v1/google-flow/videos/upscale" > upscale.json
    
    # Extract upscaled video URL and download (prefer media[] over deprecated operations[])
    VIDEO_URL=$(jq -r '.media[0].videoUrl' upscale.json)
    curl "$VIDEO_URL" --output upscaled_video.mp4
    
  • const token = 'YOUR_API_TOKEN';
    
    // First generate a video
    const generateResponse = await fetch('https://api.useapi.net/v1/google-flow/videos', {
      method: 'POST',
      headers: {
        'Authorization': `Bearer ${token}`,
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({
        prompt: 'A serene mountain landscape at sunset'
      })
    });
    
    const generated = await generateResponse.json();
    // Prefer media[] over deprecated operations[]
    const mediaGenerationId = generated.media[0].mediaGenerationId;
    
    // Upscale the video
    const upscaleResponse = await fetch('https://api.useapi.net/v1/google-flow/videos/upscale', {
      method: 'POST',
      headers: {
        'Authorization': `Bearer ${token}`,
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({
        mediaGenerationId,
        resolution: '1080p'
      })
    });
    
    const upscaled = await upscaleResponse.json();
    // Prefer media[] over deprecated operations[]
    const videoUrl = upscaled.media[0].videoUrl;
    
    // Download upscaled video (Node.js)
    const videoResponse = await fetch(videoUrl);
    const videoBuffer = await videoResponse.arrayBuffer();
    require('fs').writeFileSync('upscaled_video.mp4', Buffer.from(videoBuffer));
    console.log('Upscaled video saved!');
    
  • import requests
    
    token = 'YOUR_API_TOKEN'
    headers = {
        'Authorization': f'Bearer {token}',
        'Content-Type': 'application/json'
    }
    
    # First generate a video
    generate_response = requests.post(
        'https://api.useapi.net/v1/google-flow/videos',
        headers=headers,
        json={'prompt': 'A serene mountain landscape at sunset'}
    )
    generated = generate_response.json()
    # Prefer media[] over deprecated operations[]
    media_generation_id = generated['media'][0]['mediaGenerationId']
    
    # Upscale the video
    upscale_response = requests.post(
        'https://api.useapi.net/v1/google-flow/videos/upscale',
        headers=headers,
        json={
            'mediaGenerationId': media_generation_id,
            'resolution': '1080p'
        }
    )
    upscaled = upscale_response.json()
    # Prefer media[] over deprecated operations[]
    video_url = upscaled['media'][0]['videoUrl']
    
    # Download upscaled video
    video_response = requests.get(video_url)
    with open('upscaled_video.mp4', 'wb') as f:
        f.write(video_response.content)
    print('Upscaled video saved!')
    

Try It