> ## Documentation Index
> Fetch the complete documentation index at: https://docs.topyappers.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Video Remix API Overview

> Process videos with the TopYappers Remix API

<Note>
  **Remove Invisible Watermarks from AI-Generated Videos**

  The Video Remix API helps you remove invisible watermarks that AI video generation platforms add to their content. By processing your videos through our API, you can ensure clean, watermark-free output for your use cases.
</Note>

## Introduction

The Video Remix API allows you to process video files by providing a URL to the video. The API downloads the video from the provided URL, applies your specified transformations, and processes it to remove invisible watermarks.

<Note>
  **Upload Your Video First**

  Before using the Remix API, you need to upload your video file to cloud storage such as **Cloudflare R2** or **AWS S3** and make it publicly accessible. The API requires a direct URL to your video file.
</Note>

## Authentication

All requests to the Remix API require authentication using an API key passed in the `x-ty-api-key` header.

```bash theme={null}
x-ty-api-key: your-api-key-here
```

## Endpoint

```
POST https://www.topyappers.com/api/v1/remix
```

## How to Upload Your Video

Before using the Remix API, you need to upload your video to cloud storage. Here are the recommended options:

### Option 1: Cloudflare R2 Storage

Cloudflare R2 offers S3-compatible storage with no egress fees.

1. Create an R2 bucket in your Cloudflare dashboard
2. Upload your video file to the bucket
3. Make the bucket or object publicly accessible
4. Use the public URL in your API request

**Example R2 URL**: `https://pub-abc123.r2.dev/my-video.mp4`

### Option 2: AWS S3 Storage

AWS S3 is a widely-used object storage service.

1. Create an S3 bucket in your AWS console
2. Upload your video file to the bucket
3. Configure the bucket policy or object ACL to allow public read access
4. Use the public URL in your API request

**Example S3 URL**: `https://my-bucket.s3.amazonaws.com/my-video.mp4`

### Other Storage Options

Any cloud storage service that provides publicly accessible URLs will work, including:

* Google Cloud Storage
* Azure Blob Storage
* DigitalOcean Spaces
* Backblaze B2

<Warning>
  **Security Note**: Only make videos publicly accessible that you're comfortable sharing. Consider using signed URLs with expiration times for sensitive content.
</Warning>

## Request Format

The API accepts JSON with the following fields:

| Field        | Type   | Required | Description                                         |
| ------------ | ------ | -------- | --------------------------------------------------- |
| `video_url`  | String | Yes      | URL to the video file (must be publicly accessible) |
| `parameters` | Object | No       | Optional processing parameters                      |

### Processing Parameters

The `parameters` field accepts an object with optional processing parameters. All parameters are optional and will use default values if not specified.

| Parameter              | Type    | Default       | Range/Values               | Description                                  |
| ---------------------- | ------- | ------------- | -------------------------- | -------------------------------------------- |
| `zoomFactor`           | number  | 1.0           | 0.1 - 5.0                  | Zoom level for the video                     |
| `hue`                  | number  | 0.0           | -180 to 180                | Hue adjustment in degrees                    |
| `playbackSpeed`        | number  | 1.0           | 0.1 - 5.0                  | Video playback speed multiplier              |
| `saturation`           | number  | 1.0           | 0.0 - 3.0                  | Color saturation multiplier                  |
| `brightness`           | number  | 0.0           | -1.0 to 1.0                | Brightness adjustment                        |
| `contrast`             | number  | 1.0           | 0.0 - 3.0                  | Contrast multiplier                          |
| `volume`               | number  | 1.0           | 0.0 - 2.0                  | Audio volume multiplier                      |
| `removeAudio`          | boolean | false         | true/false                 | Whether to remove audio from the video       |
| `algorithmFingerprint` | string  | "Fingerprint" | Any string                 | Algorithm identifier for processing          |
| `deviceMedia`          | string  | -             | See supported values below | Target device profile for media optimization |
| `hueShift`             | number  | 0.0           | -180 to 180                | Additional hue shift in degrees              |
| `gamma`                | number  | 1.0           | 0.1 - 3.0                  | Gamma correction value                       |
| `temperature`          | number  | 1.0           | 0.5 - 2.0                  | Color temperature adjustment                 |
| `noise`                | number  | 0.0           | 0.0 - 1.0                  | Amount of noise to add                       |
| `sharpness`            | number  | 1.0           | 0.0 - 3.0                  | Sharpness multiplier                         |
| `blend`                | number  | 0.0           | 0.0 - 1.0                  | Blending amount                              |
| `bilateVariation`      | number  | 1.0           | 0.0 - 2.0                  | Bilateral filter variation                   |
| `frameBlending`        | number  | 0.0           | 0.0 - 1.0                  | Amount of frame blending                     |
| `timeShift`            | number  | 0.0           | -10.0 to 10.0              | Time shift in seconds                        |

#### Supported `deviceMedia` Values

```typescript theme={null}
export enum DeviceModel {
  IPHONE_17_PRO_MAX = "iPhone 17 Pro Max",
  IPHONE_17_PRO = "iPhone 17 Pro",
  IPHONE_17 = "iPhone 17",
  IPHONE_16_PRO_MAX = "iPhone 16 Pro Max",
  IPHONE_16_PRO = "iPhone 16 Pro",
  IPHONE_16 = "iPhone 16",
  IPHONE_15_PRO_MAX = "iPhone 15 Pro Max",
  IPHONE_15_PRO = "iPhone 15 Pro",
  IPHONE_15 = "iPhone 15",
  IPHONE_14_PRO_MAX = "iPhone 14 Pro Max",
  IPHONE_14_PRO = "iPhone 14 Pro",
  IPHONE_14 = "iPhone 14",
  IPHONE_13_PRO_MAX = "iPhone 13 Pro Max",
  IPHONE_13_PRO = "iPhone 13 Pro",
  IPHONE_13 = "iPhone 13",
  META_RAYBAN = "Ray-Ban Meta Smart Glasses",
}
```

#### Example with Multiple Parameters

```json theme={null}
{
  "video_url": "https://pub-abc123.r2.dev/my-video.mp4",
  "parameters": {
    "playbackSpeed": 1.2,
    "brightness": 0.1,
    "contrast": 1.1,
    "saturation": 1.2,
    "hue": 15,
    "zoomFactor": 1.05,
    "removeAudio": false,
    "deviceMedia": "iPhone 16 Pro"
  }
}
```

## Response Format

### Success Response (200 OK)

```json theme={null}
{
  "data": {
    "inputVideoUrl": "https://storage.topyappers.com/uploads/abc123.mp4",
    "result": "Video processing initiated"
  }
}
```

### Error Responses

* **400 Bad Request**: Invalid video URL or parameters
* **401 Unauthorized**: Invalid or missing API key
* **413 Payload Too Large**: Video file exceeds size limit
* **429 Too Many Requests**: Rate limit exceeded

## Code Examples

<CodeGroup>
  ```python Python theme={null}
  import requests
  import json

  API_KEY = "your-api-key-here"
  BASE_URL = "https://www.topyappers.com"
  # Video URL from Cloudflare R2 or AWS S3
  VIDEO_URL = "https://pub-abc123.r2.dev/my-video.mp4"

  # Optional parameters for video processing
  parameters = {
      "playbackSpeed": 1.2,
      "brightness": 0.1,
      "contrast": 1.1,
      "saturation": 1.2,
      "hue": 15,
      "zoomFactor": 1.05,
      "deviceMedia": "iPhone 16 Pro"
  }

  def process_video():
      url = f"{BASE_URL}/api/v1/remix"
      
      headers = {
          "x-ty-api-key": API_KEY,
          "Content-Type": "application/json"
      }
      
      payload = {
          "video_url": VIDEO_URL,
          "parameters": parameters
      }
      
      print(f"Processing {VIDEO_URL}...")
      response = requests.post(url, headers=headers, json=payload)
      
      if response.status_code == 200:
          result = response.json()
          print("✅ Success!")
          print(f"Input URL: {result['data']['inputVideoUrl']}")
          if 'result' in result['data']:
              print(f"Result: {result['data']['result']}")
          return result
      else:
          print(f"❌ Error {response.status_code}: {response.text}")
          return None

  if __name__ == "__main__":
      result = process_video()
      if result:
          print(f"\nFull response:\n{json.dumps(result, indent=2)}")
  ```

  ```javascript JavaScript theme={null}
  const fetch = require('node-fetch');

  const API_KEY = 'your-api-key-here';
  const BASE_URL = 'https://www.topyappers.com';
  // Video URL from Cloudflare R2 or AWS S3
  const VIDEO_URL = 'https://my-bucket.s3.amazonaws.com/my-video.mp4';

  // Optional parameters for video processing
  const parameters = {
    playbackSpeed: 1.2,
    brightness: 0.1,
    contrast: 1.1,
    saturation: 1.2,
    hue: 15,
    zoomFactor: 1.05,
    deviceMedia: "iPhone 16 Pro"
  };

  async function processVideo() {
    const url = `${BASE_URL}/api/v1/remix`;
    
    const payload = {
      video_url: VIDEO_URL,
      parameters: parameters
    };
    
    try {
      const response = await fetch(url, {
        method: 'POST',
        headers: {
          'x-ty-api-key': API_KEY,
          'Content-Type': 'application/json'
        },
        body: JSON.stringify(payload)
      });
      
      const result = await response.json();
      
      if (response.ok) {
        console.log('✅ Success!');
        console.log(`Input URL: ${result.data.inputVideoUrl}`);
        if (result.data.result) {
          console.log(`Result: ${result.data.result}`);
        }
        return result;
      } else {
        console.error(`❌ Error ${response.status}: ${JSON.stringify(result)}`);
        return null;
      }
    } catch (error) {
      console.error(`❌ Error: ${error.message}`);
      return null;
    }
  }

  processVideo();
  ```

  ```typescript TypeScript theme={null}
  async function processVideo(
    videoUrl: string,
    parameters: object,
    apiKey: string
  ): Promise<any> {
    const baseUrl = 'https://www.topyappers.com';
    
    const response = await fetch(`${baseUrl}/api/v1/remix`, {
      method: 'POST',
      headers: {
        'x-ty-api-key': apiKey,
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        video_url: videoUrl,
        parameters: parameters,
      }),
    });

    if (!response.ok) {
      throw new Error(`API error: ${response.status}`);
    }

    return await response.json();
  }

  // Usage with R2 URL
  const result = await processVideo(
    'https://pub-abc123.r2.dev/video.mp4',
    { playbackSpeed: 1.2, brightness: 0.1, deviceMedia: "iPhone 16 Pro" },
    'YOUR_API_KEY'
  );

  console.log('🎉 Processing complete:', result);
  ```

  ```bash cURL theme={null}
  curl -X POST https://www.topyappers.com/api/v1/remix \
    -H "x-ty-api-key: your-api-key-here" \
    -H "Content-Type: application/json" \
    -d '{
      "video_url": "https://pub-abc123.r2.dev/video.mp4",
      "parameters": {
        "playbackSpeed": 1.2,
        "brightness": 0.1,
        "contrast": 1.1,
        "saturation": 1.2,
        "hue": 15,
        "zoomFactor": 1.05,
        "deviceMedia": "iPhone 16 Pro"
      }
    }'
  ```
</CodeGroup>

## React Example (Complete Component)

```tsx theme={null}
import { useState } from 'react';

export function VideoRemixProcessor() {
  const [videoUrl, setVideoUrl] = useState('');
  const [result, setResult] = useState<any>(null);
  const [loading, setLoading] = useState(false);
  const [error, setError] = useState('');

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!videoUrl) return;

    setLoading(true);
    setError('');
    setResult(null);

    try {
      const response = await fetch('https://www.topyappers.com/api/v1/remix', {
        method: 'POST',
        headers: {
          'Content-Type': 'application/json',
          'x-ty-api-key': process.env.NEXT_PUBLIC_API_KEY!,
        },
        body: JSON.stringify({
          video_url: videoUrl,
          parameters: {
            playbackSpeed: 1.2,
            brightness: 0.1,
            contrast: 1.1,
            deviceMedia: "iPhone 16 Pro",
          },
        }),
      });

      if (!response.ok) {
        throw new Error(`API error: ${response.status}`);
      }

      const data = await response.json();
      setResult(data);
    } catch (err) {
      setError(err.message);
    } finally {
      setLoading(false);
    }
  };

  return (
    <form onSubmit={handleSubmit}>
      <input
        type="url"
        placeholder="https://pub-abc123.r2.dev/video.mp4"
        value={videoUrl}
        onChange={(e) => setVideoUrl(e.target.value)}
        required
      />
      <p className="hint">Enter URL from Cloudflare R2 or AWS S3</p>
      
      <button type="submit" disabled={!videoUrl || loading}>
        {loading ? 'Processing...' : 'Process Video'}
      </button>
      
      {error && (
        <div className="error">
          <p>❌ Error: {error}</p>
        </div>
      )}
      
      {result && (
        <div className="result">
          <h3>✅ Complete!</h3>
          <pre>{JSON.stringify(result, null, 2)}</pre>
        </div>
      )}
    </form>
  );
}
```

## Video URL Requirements

Your video must be uploaded to cloud storage (Cloudflare R2, AWS S3, etc.) before processing. The URL must meet these requirements:

* **Publicly Accessible**: The video URL must be publicly accessible (no authentication required)
* **Cloud Storage**: Must be hosted on Cloudflare R2, AWS S3, or similar cloud storage
* **Supported Formats**: MP4, MOV, AVI, WebM
* **Max File Size**: 150MB
* **Direct Links**: URL must point directly to the video file (not a webpage)

## Error Handling

### 400 Bad Request

```json theme={null}
{
  "error": "Invalid video URL or parameters"
}
```

### 401 Unauthorized

```json theme={null}
{
  "error": "Invalid API key"
}
```

### 429 Too Many Requests

```json theme={null}
{
  "error": "Daily limit exceeded. Upgrade your plan or try in 24 hours.",
  "retryAfter": 86400,
  "limit": 100
}
```

### 413 File Too Large

```json theme={null}
{
  "error": "Video file too large. Maximum size is 150MB"
}
```

## Retry Logic Example

```typescript theme={null}
async function processVideoWithRetry(
  videoUrl: string,
  parameters: object,
  apiKey: string,
  maxRetries = 3
) {
  for (let i = 0; i < maxRetries; i++) {
    try {
      return await processVideo(videoUrl, parameters, apiKey);
    } catch (error) {
      if (i === maxRetries - 1) throw error;
      const delay = Math.pow(2, i) * 1000; // 1s, 2s, 4s
      await new Promise(resolve => setTimeout(resolve, delay));
    }
  }
}
```

## Best Practices

1. **Valid URLs**: Ensure video URLs are publicly accessible and point directly to video files
2. **File Size**: Keep video files under 150MB for optimal processing
3. **File Formats**: Use supported formats (MP4, MOV, AVI, WebM)
4. **Error Handling**: Always implement proper error handling for network and API errors
5. **Rate Limits**: Be mindful of rate limits and implement retry logic with exponential backoff
6. **API Keys**: Keep your API keys secure and never commit them to version control

## Rate Limits

Please refer to the [Rate Limits](/rate-limits) documentation for information about API rate limits and best practices.
