Documentation

Home › API Management

API Management

Create and manage API keys for programmatic access to your account

Log in to your account to generate and manage API keys.

Authentication Header

Include your API key in every request using the X-API-Key header:

HTTP
X-API-Key: your_api_key_here

Rate limit: 1,000 requests per hour per API key

Endpoints

Standard Endpoints

Creates a new job/campaign with specified details. Requires multipart/form-data content type. Set approve_once_full to true to automatically approve all submissions and pay workers once the job reaches its total availabilities.

Content-Type:multipart/form-data

titlestringrequired
descriptionstringrequired
pay_ratedecimalrequired
total_availabilitiesintegerrequired
proof_required_descriptionstringrequired
categorystringrequired
sub_categorystring
campaign_imagefile
countriesarray

Omit to include all countries

excluded_countriesarray

Only when open to all countries: ISO codes to leave out, e.g. IN, BD

approve_once_fullboolean

default: false. When true, all submissions are automatically approved and workers paid once the job reaches its total availabilities

python
import requests

# Create a job without image
job_data = {
    "title": "Complete a Survey",
    "description": "Fill out our 5-minute customer satisfaction survey",
    "pay_rate": "2.50",
    "total_availabilities": "100",
    "proof_required_description": "Submit a screenshot of the completion page",
    "category": "Survey",
    "sub_category": (None, "Customer Feedback"),
    "countries": (None, '["US", "CA", "GB"]'),  # Omit to include all countries
}
response = requests.post(
    "https://api.rapidworkers.io/jobs/add",
    headers={"X-API-Key": "your_api_key_here"},
    files=job_data
)
job = response.json()
print(f"Job created: {job['job']['public_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job": {
    "public_id": "123e4567-e89b-12d3-a456-426614174000",
    "title": "Test Job",
    "status": "Active",
    "pay_rate": "5.00",
    "total_availabilities": 10
  },
  "deduction_details": {
    "total_cost": "50.00",
    "commission": "5.00",
    "total_deducted": "55.00",
    "new_balance": "945.00"
  }
}

400—Invalid data or insufficient balance

401—Invalid or missing API key

403—Job rejected by legitimacy check

Retrieves your current account balance.

Content-Type:application/json

JSON
{} // Empty body
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/account/get_balance",
    headers={"X-API-Key": "your_api_key_here"}
)
print(f"Balance: {response.json()['balance']}")
JSON
// 200 OK
{
  "balance": "1000.00"
}

401—Invalid or missing API key

404—User not found

Approves a worker's submission for your campaign.

Path Parameters

campaign_idUUID
submission_idinteger

Content-Type:application/json

JSON
{
  "notes": "Great work!", // Optional
  "tip": "2.00" // Optional: $0.01-$50.00 from your balance, paid to the worker in full with no fee
}
python
import requests

campaign_id = "your_campaign_public_id"
submission_id = 456

response = requests.post(
    f"https://api.rapidworkers.io/api/campaigns/{campaign_id}/submissions/{submission_id}/approve/",
    headers={"X-API-Key": "your_api_key_here"},
    json={"notes": "Great work!"}
)
print(f"Submission approved: {response.json()}")
JSON
// 200 OK
{
  "success": true,
  "message": "Submission approved successfully",
  "submission": {
    "id": 123,
    "user": "worker_username",
    "status": "Approved",
    "amount_paid": "5.00"
  }
}

400—Submission already processed, insufficient funds, or invalid tip

403—You don't own this campaign

404—Submission not found

Rejects a worker's submission with a reason.

Path Parameters

campaign_idUUID
submission_idinteger

Content-Type:application/json

JSON
{
  "notes": "Does not meet requirements" // Required
}
python
import requests

campaign_id = "your_campaign_public_id"
submission_id = 456

response = requests.post(
    f"https://api.rapidworkers.io/api/campaigns/{campaign_id}/submissions/{submission_id}/reject/",
    headers={"X-API-Key": "your_api_key_here"},
    json={"notes": "Screenshot does not show completion page"}
)
print(f"Submission rejected: {response.json()}")
JSON
// 200 OK
{
  "success": true,
  "message": "Submission rejected",
  "submission": {
    "id": 123,
    "user": "worker_username",
    "status": "Rejected",
    "notes": "Does not meet requirements"
  }
}

400—Missing rejection reason

403—You don't own this campaign

404—Submission not found

Approve all pending submissions for a campaign at once.

Path Parameters

campaign_idUUID

Content-Type:application/json

JSON
{
  "notes": "Bulk action notes" // Optional
}
python
import requests

campaign_id = "your_campaign_public_id"

# Bulk approve all pending
response = requests.post(
    f"https://api.rapidworkers.io/api/campaigns/{campaign_id}/submissions/bulk_action/",
    headers={"X-API-Key": "your_api_key_here"},
    json={"notes": "All submissions verified"}
)
print(f"Bulk action result: {response.json()}")
JSON
// 200 OK
{
  "success": true,
  "message": "All submissions approved successfully.",
  "submissions": [
    { "id": 123, "status": "Approved", "user": "worker1" },
    { "id": 124, "status": "Approved", "user": "worker2" }
  ]
}

403—You don't own this campaign

404—No pending submissions found

Retrieves all campaigns owned by the authenticated user, with optional status filtering.

statusstring

"Active", "Pending", "Completed", "Canceled"

languagestring

default: "en"

python
import requests

# List all campaigns
response = requests.get(
    "https://api.rapidworkers.io/api/campaigns/",
    headers={"X-API-Key": "your_api_key_here"}
)
campaigns = response.json()
for campaign in campaigns["results"]:
    print(f"{campaign['jobTitle']} - {campaign['jobStatus']}")

# Filter by status
response = requests.get(
    "https://api.rapidworkers.io/api/campaigns/?status=Active",
    headers={"X-API-Key": "your_api_key_here"}
)
JSON
// 200 OK
[
  {
    "jobId": "123e4567-e89b-12d3-a456-426614174000",
    "jobTitle": "Complete a Survey",
    "jobCategory": "Survey",
    "jobPay": "2.50",
    "jobLocation": "In",
    "jobCreatedAt": "2025-01-15T10:30:00Z",
    "jobStatus": "Active",
    "jobInstancesCompleted": 45,
    "jobTotalAvailabilities": 100,
    "jobSuccessRate": "40%",
    "description": "Fill out our customer satisfaction survey",
    "canceled": false,
    "remainingAvailabilities": 55,
    "pendingSubmissions": 12,
    "approvedSubmissions": 40,
    "rejectedSubmissions": 5
  }
]

401—Invalid or missing API key

Retrieves detailed information about a specific campaign including submission counts and remaining availability.

Path Parameters

campaign_idUUID
languagestring

default: "en"

python
import requests

campaign_id = "123e4567-e89b-12d3-a456-426614174000"
response = requests.get(
    f"https://api.rapidworkers.io/api/campaigns/detail/{campaign_id}/",
    headers={"X-API-Key": "your_api_key_here"}
)
campaign = response.json()
print(f"Remaining slots: {campaign['remaining_availabilities']}")
print(f"Pending: {campaign['pending_submissions']}")
JSON
// 200 OK
{
  "jobId": "123e4567-e89b-12d3-a456-426614174000",
  "jobTitle": "Complete a Survey",
  "jobCategory": "Survey",
  "jobPay": "2.50",
  "jobLocation": "In",
  "jobCreatedAt": "2025-01-15T10:30:00Z",
  "jobStatus": "Active",
  "jobInstancesCompleted": 45,
  "jobTotalAvailabilities": 100,
  "jobSuccessRate": "40%",
  "description": "Fill out our customer satisfaction survey",
  "canceled": false,
  "remainingAvailabilities": 55,
  "pendingSubmissions": 12,
  "approvedSubmissions": 40,
  "rejectedSubmissions": 5
}

401—Invalid or missing API key

403—You don't own this campaign

404—Campaign not found

Retrieves all submissions for a specific campaign with worker metadata, optional status filtering, and pagination.

Path Parameters

campaign_idUUID
statusstring

"Pending", "Approved", "Rejected"

searchstring

search by worker name

pageinteger

default: 1

rowsPerPageinteger

default: 1000

languagestring

default: "en"

python
import requests

campaign_id = "123e4567-e89b-12d3-a456-426614174000"

# List all submissions
response = requests.get(
    f"https://api.rapidworkers.io/api/campaigns/{campaign_id}/submissions/",
    headers={"X-API-Key": "your_api_key_here"}
)
data = response.json()
for sub in data["results"]["submissions"]:
    print(f"#{sub['submissionId']} - {sub['status']} - Age: {sub['worker_account_age_days']}d")

# Filter pending only
response = requests.get(
    f"https://api.rapidworkers.io/api/campaigns/{campaign_id}/submissions/?status=Pending",
    headers={"X-API-Key": "your_api_key_here"}
)
JSON
// 200 OK
{
  "count": 45,
  "next": null,
  "previous": null,
  "results": {
    "submissions": [
      {
        "submissionId": 123,
        "userId": "abc-def-123",
        "userName": "WorkerName",
        "userAvatar": "https://...",
        "campaignId": "123e4567-e89b-12d3-a456-426614174000",
        "campaignTitle": "Complete a Survey",
        "status": "Pending",
        "country_name": "United States",
        "submittedAt": "2025-01-16T14:30:00Z",
        "proof_text": "Completed the survey as requested",
        "images": [
          { 
            "id": "img_1", 
            "url": "https://...", 
            "thumbnailUrl": "https://..." 
          }
        ],
        "notes": null,
        "workerAccountAgeDays": 120,
        "workerApprovalRate": "85%",
        "workerTotalCompleted": 47
      }
    ],
    "pagination": {
      "totalCount": 45,
      "pageCount": 1,
      "currentPage": 1,
      "rowsPerPage": 1000
    }
  }
}

401—Invalid or missing API key

403—You don't own this campaign

404—Campaign not found

Blocks a worker from submitting proofs to any of your campaigns. Blocked workers will not see your campaigns in their job list.

Content-Type:application/json

JSON
{
  "worker_id": 12345 // Worker public ID
}
python
import requests

worker_id = 12345

response = requests.post(
    "https://api.rapidworkers.io/api/workers/block/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={"worker_id": worker_id}
)
print(f"Worker blocked: {response.json()}")
JSON
// 201 Created
{
  "success": true,
  "message": "Worker blocked successfully",
  "worker_id": 12345
}

400—Missing worker_id, self-block attempt, or worker already blocked

401—Invalid or missing API key

404—Worker not found

Unblocks a previously blocked worker, allowing them to see and submit proofs to your campaigns again.

Content-Type:application/json

JSON
{
  "worker_id": 12345
}
python
import requests

worker_id = 12345

response = requests.post(
    "https://api.rapidworkers.io/api/workers/unblock/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={"worker_id": worker_id}
)
print(f"Worker unblocked: {response.json()}")
JSON
// 200 OK
{
  "success": true,
  "message": "Worker unblocked successfully",
  "worker_id": 12345
}

400—Missing worker_id or worker is not blocked

401—Invalid or missing API key

404—Worker not found

Retrieves the list of all workers you have blocked.

Request
No request body required.
python
import requests

response = requests.get(
    "https://api.rapidworkers.io/api/workers/blocked/",
    headers={"X-API-Key": "your_api_key_here"}
)
blocked = response.json()
for worker in blocked:
    print(f"Blocked: {worker['worker_name']} (ID: {worker['worker_id']})")
JSON
// 200 OK
[
  {
    "worker_id": 12345,
    "worker_name": "WorkerName",
    "blocked_at": "2025-01-15T10:30:00Z"
  }
]

401—Invalid or missing API key

Creates an AI data task (image, video, audio or text collection, data labeling). Workers upload files straight to private storage; you review and approve each submission. Accepts JSON, or multipart/form-data when attaching reference images.

Content-Type:application/json

JSON
{
  "task_type": "image_collection", // Required: image_collection | video_collection | audio_collection | text_collection | custom_data_collection
  "capture_mode": "both", // Optional, audio/video tasks only: both | upload | record (how workers provide files)
  "title": "Submit 10 photos of your face", // Required
  "description": "<p>Take 10 clear photos from different angles...</p>", // Required, HTML allowed
  "submission_instructions": "Front, left, right, up, down and 5 more angles. No filters.", // Required
  "required_file_count": 10, // Required (1-200). Exact count for image/video/audio tasks, maximum for others
  "pay_rate": "0.50", // Required (minimum: 0.10)
  "total_availabilities": 100, // Required (10-20000)
  "length_in_minutes": 10, // Optional
  "countries": ["All"], // Required. ["All"] for every country, or ISO codes like ["US", "GB"]
  "excluded_countries": ["IN", "BD"], // Optional, only with ["All"]: every country except these
  "reference_upload_ids": [12, 13], // Optional: sample/instructional media uploaded via /api/ai-tasks/reference-uploads/
  "submission_fields": [ // Required for custom_data_collection only: the worker form, in display order (max 30)
    { "type": "select", "label": "Category", "required": true, "options": ["Electricity", "Insurance"] },
    // Dependent dropdown: its options follow the answer to an earlier plain dropdown.
    // parent_key is that dropdown's position as "field_<n>" (the first field is field_1).
    // options_by_parent needs a list (1-1000 options) for every parent option, 5000 options in total.
    // Workers can only submit an option listed under the parent option they chose.
    { "type": "select", "label": "Biller / Company Name", "required": true, "parent_key": "field_1",
      "options_by_parent": { "Electricity": ["B.E.S.T Mumbai", "TP Ajmer Distribution Ltd"], "Insurance": ["HDFC Life Insurance"] } },
    { "type": "image", "label": "Bill screenshot", "required": true, "min_files": 1, "max_files": 1, "help_text": "Upload the original SMS screenshot" },
    { "type": "consent", "label": "I consent to share this data", "required": true }
    // type: short_text | long_text | select | datetime | consent | image | audio | video
  ]
}

// Alternatively send multipart/form-data with up to 30 reference_images (JPG, PNG or WEBP, 5MB each)
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/ai-tasks/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "task_type": "image_collection",
        "title": "Submit 10 photos of your face",
        "description": "<p>Take 10 clear photos of your face from different angles.</p>",
        "submission_instructions": "Front, left, right, up, down and 5 more angles. No filters.",
        "required_file_count": 10,
        "pay_rate": "0.50",
        "total_availabilities": 100,
        "length_in_minutes": 10,
        "countries": ["All"]
    }
)
task = response.json()
print(f"Task created: {task['task_id']}")
JSON
// 201 Created
{
  "message": "AI task created successfully",
  "task_id": "123e4567-e89b-12d3-a456-426614174000",
  "status": "Active"
}

400—Invalid data, insufficient balance, or no deposit on the account

401—Invalid or missing API key

403—AI tasks are not enabled for this account yet

Lists every AI task you have created with submission counts.

Request
No parameters
python
import requests

response = requests.get(
    "https://api.rapidworkers.io/api/ai-tasks/mine/",
    headers={"X-API-Key": "your_api_key_here"}
)
for task in response.json()["tasks"]:
    print(task["title"], task["pendingSubmissions"], "pending")
JSON
// 200 OK
{
  "tasks": [
    {
      "taskPublicId": "123e4567-e89b-12d3-a456-426614174000",
      "taskType": "image_collection",
      "title": "Submit 10 photos of your face",
      "pay": "0.50",
      "countries": ["All"],
      "lengthInMinutes": 10,
      "requiredFileCount": 10,
      "referenceImages": [],
      "completedCount": 12,
      "totalAvailabilities": 100,
      "pendingSubmissions": 3,
      "status": "Active",
      "createdAt": "2025-01-15T10:30:00Z"
    }
  ]
}

401—Invalid or missing API key

Retrieves one AI task, including its submission rules and reference images.

Path Parameters

task_idUUID
Request
No parameters
python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
response = requests.get(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/",
    headers={"X-API-Key": "your_api_key_here"}
)
task = response.json()["task"]
print(f"Approved: {task['approvedSubmissions']} / {task['totalAvailabilities']}")
JSON
// 200 OK
{
  "task": {
    "taskPublicId": "123e4567-e89b-12d3-a456-426614174000",
    "taskType": "image_collection",
    "title": "Submit 10 photos of your face",
    "description": "<p>Take 10 clear photos...</p>",
    "submissionInstructions": "Front, left, right, up, down and 5 more angles.",
    "pay": "0.50",
    "countries": ["All"],
    "requiredFileCount": 10,
    "referenceImages": ["https://.../example.jpg"],
    "rules": {
      "allowedTypes": ["image/heic", "image/heif", "image/jpeg", "image/png", "image/webp"],
      "maxBytes": 15728640,
      "exactCount": true,
      "textRequired": false,
      "fileCount": 10
    },
    "completedCount": 12,
    "totalAvailabilities": 100,
    "pendingSubmissions": 3,
    "approvedSubmissions": 9,
    "rejectedSubmissions": 1,
    "reservedAmount": "50.00",
    "paidOutAmount": "4.50",
    "status": "Active",
    "createdAt": "2025-01-15T10:30:00Z"
  }
}

401—Invalid or missing API key

404—Task not found

Lists submissions for an AI task with the worker's written response and expiring download links for each uploaded file. Links are valid for 1 hour; request again for fresh ones.

Path Parameters

task_idUUID
statusstring

Pending, Approved, Rejected

python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
response = requests.get(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/submissions/",
    headers={"X-API-Key": "your_api_key_here"},
    params={"status": "Pending"}
)
for submission in response.json()["submissions"]:
    for file in submission["files"]:
        data = requests.get(file["url"]).content  # download while the link is valid
        open(file["name"], "wb").write(data)
JSON
// 200 OK
{
  "task": { "taskPublicId": "123e4567-...", "title": "Submit 10 photos of your face", "status": "Active" },
  "submissions": [
    {
      "submissionId": 42,
      "userId": 1234,
      "userName": "Jane Doe",
      "countryName": "Canada",
      "status": "Pending",
      "paymentStatus": "Not_Paid",
      "amountPaid": null,
      "textResponse": "",
      "notes": "",
      "fileCount": 10,
      "files": [
        {
          "id": 501,
          "name": "front.jpg",
          "contentType": "image/jpeg",
          "size": 2451234,
          "url": "https://bucket.s3.amazonaws.com/private/ai-tasks/...?X-Amz-Expires=3600&..." // Valid for 1 hour
        }
      ],
      "isBlocked": false,
      "submittedAt": "2025-01-16T08:12:00Z"
    }
  ]
}

401—Invalid or missing API key

403—You don't own this task

404—Task not found

Approves an AI task submission and pays the worker from the task's reserved funds.

Path Parameters

task_idUUID
submission_idinteger

Content-Type:application/json

JSON
{
  "notes": "Great photos, thank you", // Optional
  "tip": "2.00" // Optional: $0.01-$50.00 from your balance, paid to the worker in full with no fee
}
python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
submission_id = 42
response = requests.post(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/submissions/{submission_id}/approve/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={"notes": "Great photos, thank you"}
)
print(response.json()["message"])
JSON
// 200 OK
{
  "success": true,
  "message": "Submission approved",
  "submission": {
    "submissionId": 42,
    "status": "Approved",
    "paymentStatus": "Paid",
    "amountPaid": "0.50"
  }
}

400—Not enough reserved funds for this task, not enough balance for the tip, or invalid tip

401—Invalid or missing API key

403—You don't own this task

404—Submission not found

Rejects an AI task submission with a reason. The worker can fix the issues and submit again.

Path Parameters

task_idUUID
submission_idinteger

Content-Type:application/json

JSON
{
  "notes": "Photos are blurry, please retake in better light" // Required
}
python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
submission_id = 42
response = requests.post(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/submissions/{submission_id}/reject/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={"notes": "Photos are blurry, please retake in better light"}
)
print(response.json()["message"])
JSON
// 200 OK
{
  "success": true,
  "message": "Submission rejected",
  "submission": {
    "submissionId": 42,
    "status": "Rejected",
    "notes": "Photos are blurry, please retake in better light"
  }
}

400—Missing rejection reason, or submission already approved

401—Invalid or missing API key

403—You don't own this task

404—Submission not found

Issues presigned S3 URLs for sample or instructional media (images, video, audio). Upload the bytes with PUT, then pass the returned upload ids as reference_upload_ids when creating a task.

Content-Type:application/json

JSON
{
  "files": [
    { "name": "sample.mp4", "content_type": "video/mp4", "size": 18422311 }, // Images up to 15MB, audio 50MB, video 500MB
    { "name": "front.jpg", "content_type": "image/jpeg", "size": 2451234 }
  ]
}
python
import requests

with open("sample.mp4", "rb") as f:
    data = f.read()

issued = requests.post(
    "https://api.rapidworkers.io/api/ai-tasks/reference-uploads/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={"files": [{"name": "sample.mp4", "content_type": "video/mp4", "size": len(data)}]}
).json()["uploads"][0]

requests.put(issued["url"], data=data, headers=issued["headers"]).raise_for_status()
upload_id = issued["uploadId"]  # pass in reference_upload_ids when creating the task
JSON
// 201 Created
{
  "uploads": [
    {
      "uploadId": 12,
      "name": "sample.mp4",
      "url": "https://bucket.s3.amazonaws.com/private/ai-task-references/...?X-Amz-Expires=3600&...",
      "headers": { "Content-Type": "video/mp4" }
    }
  ]
}

// PUT each file's bytes to its url with exactly those headers, then pass the uploadIds
// as reference_upload_ids when creating the task. URLs expire after 1 hour.

400—Unsupported type or file too large

401—Invalid or missing API key

429—Too many pending uploads

Approves every pending submission on an AI task and pays each worker.

Path Parameters

task_idUUID

Content-Type:application/json

JSON
{
  "notes": "Thanks everyone" // Optional
}
python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
response = requests.post(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/submissions/bulk_approve/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={}
)
print(response.json()["message"])
JSON
// 200 OK
{
  "success": true,
  "message": "12 submission(s) approved",
  "approved": 12,
  "error": null
}

400—Not enough reserved funds

401—Invalid or missing API key

403—You don't own this task

404—Task not found

Adds slots to an AI task. Charged at the task's pay rate plus commission. A completed task becomes active again.

Path Parameters

task_idUUID

Content-Type:application/json

JSON
{
  "additional_availabilities": 50 // Required. Charged at pay_rate x 50 plus commission
}
python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
response = requests.post(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/extend/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={"additional_availabilities": 50}
)
print(response.json()["task"]["totalAvailabilities"])
JSON
// 200 OK
{
  "message": "Task extended",
  "task": { "taskPublicId": "123e4567-...", "totalAvailabilities": 150, "status": "Active" }
}

400—Insufficient balance, task not active, or over the 20,000 limit

401—Invalid or missing API key

403—You don't own this task

404—Task not found

Edits an AI task the way campaigns are edited: the task is canceled and its unspent funds refunded, and a new version with your changes replaces it (charged fresh). Send every field, as when creating. Allowed while the task is pending or active, has no submissions waiting for review, and has been edited fewer than 10 times.

Path Parameters

task_idUUID

Content-Type:application/json

JSON
// The same fields as creating a task (all of them, not just the changes), plus:
{
  "task_type": "image_collection",
  "title": "Submit 10 photos of your face",
  "description": "<p>Take 10 clear photos from different angles...</p>",
  "submission_instructions": "<p>Front, left, right, up, down and 5 more angles.</p>", // HTML allowed
  "required_file_count": 10,
  "pay_rate": "0.50",
  "total_availabilities": 100,
  "length_in_minutes": 10,
  "countries": ["All"],
  "keep_reference_ids": [41, 42] // Optional: ids of the task's current reference files to keep (from the task detail)
}
python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
task = {
    "task_type": "image_collection",
    "title": "Submit 10 photos of your face",
    "description": "<p>Take 10 clear photos of your face from different angles.</p>",
    "submission_instructions": "Front, left, right, up, down and 5 more angles. No filters.",
    "required_file_count": 10,
    "pay_rate": "0.60",
    "total_availabilities": 100,
    "length_in_minutes": 10,
    "countries": ["All"]
}
response = requests.post(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/edit/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json=task
)
print(f"New version: {response.json()['task_id']}")
JSON
// 200 OK
{
  "message": "AI task updated successfully",
  "task_id": "9b2f6c1e-...", // The new version's id: use it from now on
  "status": "Active",
  "times_edited": 1
}

400—Invalid data, insufficient balance, submissions waiting for review, task not pending or active, or 10 edits reached

401—Invalid or missing API key

403—You don't own this task

404—Task not found

Stops an AI task and refunds funds not held by pending submissions. Pending submissions can still be approved and paid.

Path Parameters

task_idUUID
Request
No parameters
python
import requests

task_id = "123e4567-e89b-12d3-a456-426614174000"
response = requests.post(
    f"https://api.rapidworkers.io/api/ai-tasks/{task_id}/cancel/",
    headers={"X-API-Key": "your_api_key_here"}
)
print(f"Refunded: {response.json()['refund']}")
JSON
// 200 OK
{
  "message": "Task canceled",
  "refund": "37.50",
  "task": { "taskPublicId": "123e4567-...", "status": "Canceled" }
}

400—Task already canceled

401—Invalid or missing API key

403—You don't own this task

404—Task not found

Prefilled Job Endpoints

Simplified endpoints for common social media engagement tasks. Only requires a link and quantity. All prefilled jobs have automatic approval enabled: submissions are automatically approved and workers paid once the job reaches its total availabilities.

Create a simplified job for getting Facebook post likes. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://facebook.com/post/123", // Required
  "quantity": 50, // Required (minimum: 6)
  "countries": ["US", "GB"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/facebook-likes/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://facebook.com/post/123",
        "quantity": 50  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "2.50"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for getting Facebook post shares. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://facebook.com/post/123", // Required
  "quantity": 25, // Required (minimum: 6)
  "countries": ["US", "CA"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/facebook-shares/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://facebook.com/post/123",
        "quantity": 25  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "1.25"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Creates a ready-made AI training task where each worker submits photos of their own face from different angles. Only requires the number of workers. Default: 10 photos per worker at $0.10.

Content-Type:application/json

JSON
{
  "quantity": 50, // Required: number of workers (10-20000)
  "rate": "0.25", // Optional (default: 0.10, minimum: 0.10)
  "required_file_count": 10, // Optional (default: 10, maximum: 200) photos per worker
  "extra_instructions": "Wear no glasses in any photo.", // Optional, appended to the standard instructions
  "countries": ["US", "GB"] // Omit for all countries
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/ai-image-collection/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "quantity": 50,  # Minimum: 10
        "required_file_count": 10,
        "extra_instructions": "Wear no glasses in any photo."
    }
)
task = response.json()
print(f"Task created: {task['task_id']}")
JSON
// 201 Created
{
  "message": "Job created successfully",
  "task_id": "123e4567-e89b-12d3-a456-426614174000",
  "status": "Active",
  "total_cost": "12.50"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

403—AI tasks are not enabled for this account yet

Creates a ready-made AI training task where each worker records short voice clips in their browser. Only requires the number of workers. Default: 5 clips per worker at $0.10.

Content-Type:application/json

JSON
{
  "quantity": 50, // Required: number of workers (10-20000)
  "rate": "0.25", // Optional (default: 0.10, minimum: 0.10)
  "required_file_count": 5, // Optional (default: 5, maximum: 200) clips per worker
  "capture_mode": "both", // Optional: both | upload | record
  "extra_instructions": "Read these sentences aloud: ...", // Optional, appended to the standard instructions
  "countries": ["US", "GB"] // Omit for all countries
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/ai-audio-collection/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "quantity": 50,  # Minimum: 10
        "required_file_count": 5,
        "extra_instructions": "Read these sentences aloud: The quick brown fox..."
    }
)
task = response.json()
print(f"Task created: {task['task_id']}")
JSON
// 201 Created
{
  "message": "Job created successfully",
  "task_id": "123e4567-e89b-12d3-a456-426614174000",
  "status": "Active",
  "total_cost": "12.50"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

403—AI tasks are not enabled for this account yet

Create a simplified job for getting Instagram post likes. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://instagram.com/ABC123", // Required
  "quantity": 100, // Required (minimum: 6)
  "countries": ["US", "GB"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/instagram-likes/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://instagram.com/ABC123",
        "quantity": 100  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "5.00"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for gaining Instagram followers. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://instagram.com/username", // Required
  "quantity": 50, // Required (minimum: 6)
  "countries": ["US", "CA"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/instagram-followers/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://instagram.com/username",
        "quantity": 50  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "2.50"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for getting Twitter/X post likes. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://twitter.com/user/status/123", // Required
  "quantity": 75, // Required (minimum: 6)
  "countries": ["US", "GB"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/twitter-likes/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://twitter.com/user/status/123",
        "quantity": 75  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "3.75"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for gaining Twitter/X followers. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://twitter.com/username", // Required
  "quantity": 50, // Required (minimum: 6)
  "countries": ["US", "CA"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/twitter-followers/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://twitter.com/username",
        "quantity": 50  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "2.50"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for getting Twitter/X retweets. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://twitter.com/user/status/123", // Required
  "quantity": 30, // Required (minimum: 6)
  "countries": ["US", "GB"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/twitter-retweets/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://twitter.com/user/status/123",
        "quantity": 30  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "1.50"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for getting Trustpilot reviews. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://trustpilot.com/review/example.com", // Required
  "quantity": 20, // Required (minimum: 6)
  "countries": ["US", "CA"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/trustpilot-reviews/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://trustpilot.com/review/example.com",
        "quantity": 20  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "1.00"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for getting 9GAG upvotes. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://9gag.com/gag/abc123", // Required
  "quantity": 50, // Required (minimum: 6)
  "countries": ["US", "GB"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/9gag-upvotes/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://9gag.com/gag/abc123",
        "quantity": 50  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "2.50"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Create a simplified job for getting YouTube video likes. Only requires a link and quantity. Auto-pricing: $0.05 per job. Submissions are automatically approved once the job is full.

Content-Type:application/json

JSON
{
  "link": "https://youtube.com/watch?v=abc123", // Required
  "quantity": 100, // Required (minimum: 6)
  "countries": ["US", "CA"], // Omit to include all countries
  "language": "en", // Optional
  "approve_once_full": false // Optional (default: false). Set true to auto-approve all submissions once job is full
}
python
import requests

response = requests.post(
    "https://api.rapidworkers.io/api/jobs/youtube-likes/",
    headers={"X-API-Key": "your_api_key_here", "Content-Type": "application/json"},
    json={
        "link": "https://youtube.com/watch?v=abc123",
        "quantity": 100  # Minimum: 10
    }
)
job = response.json()
print(f"Job created: {job['job_id']}")
JSON
// 201 Created
{
  "success": true,
  "message": "Job created successfully",
  "job_id": "123e4567-e89b-12d3-a456-426614174000",
  "total_cost": "5.00"
}

400—Invalid data, insufficient balance, or quantity below minimum (10)

401—Invalid or missing API key

Error Handling

All API errors follow a consistent format:

JSON
{
  "error": "Error message describing what went wrong"
}

Common HTTP Status Codes:

Status CodeStatusDescription
200OKRequest succeeded
201CreatedResource created successfully
400Bad RequestInvalid request data
401UnauthorizedMissing or invalid API key
403ForbiddenInsufficient permissions
404Not FoundResource not found
429Rate LimitedRate limit exceeded (1,000/hour)
500Server ErrorServer-side error