Whisper API
High-performance audio transcription powered by OpenAI Whisper. Upload files or provide URLs for fast, accurate speech-to-text with subtitle generation, word timestamps, and batch processing.
https://whisper.ipsecure.ca
Returns server health status, current queue statistics, and upstream GX10 Whisper engine availability. Use this for monitoring and readiness checks.
Response
{
"status": "ok",
"uptime": 84321,
"queue": {
"pending": 2,
"processing": 1,
"completed": 1047,
"failed": 3
},
"gx10": {
"status": "online",
"responseTime": 42
}
}# Health check curl https://whisper.ipsecure.ca/health
const res = await fetch("https://whisper.ipsecure.ca/health"); const data = await res.json(); console.log(data);
import requests res = requests.get("https://whisper.ipsecure.ca/health") print(res.json())
Transcribe a single audio file. Upload a file via multipart/form-data or provide a remote URL. Supports synchronous mode (wait for result) and asynchronous mode (fire and forget with optional webhook callback).
wait=true). For large files, set wait=false to receive a job ID and poll or use a callback URL.Request Parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
| file | file | conditional | Audio file upload (multipart/form-data). Required if url is not provided. | |
| url | string | conditional | Remote URL of the audio file. Required if file is not provided. | |
| language | string | no | auto | ISO 639-1 language code (e.g. en, fr, es). Auto-detected if omitted. |
| task | string | no | transcribe | transcribe or translate (translates to English). |
| word_timestamps | boolean | no | false | Include per-word timestamps in the response. |
| vad_filter | boolean | no | false | Enable voice activity detection to filter silence and reduce hallucinations. |
| format | string | no | json | Response format: json, text, srt, or vtt. |
| wait | boolean | no | true | If true, waits for completion. If false, returns immediately with a job ID. |
| callbackUrl | string | no | Webhook URL to receive the result when transcription completes. |
Response — Synchronous (wait=true, format=json)
{
"success": true,
"jobId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"text": "Hello, this is a transcription of the audio file.",
"language": "en",
"language_probability": 0.98,
"duration": 12.45,
"processing_time": 3.21,
"word_count": 10,
"segments": [
{
"start": 0.0,
"end": 4.8,
"text": "Hello, this is a transcription"
}
],
"words": [
{ "word": "Hello", "start": 0.0, "end": 0.42 }
]
}Response — Asynchronous (wait=false)
{
"success": true,
"jobId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"status": "queued",
"statusUrl": "https://whisper.ipsecure.ca/transcribe/status/a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"estimatedWait": 15
}# Single file transcription (synchronous) curl -X POST https://whisper.ipsecure.ca/transcribe \ -F "file=@recording.wav" \ -F "language=en" \ -F "format=json"
const fs = require("fs"); const form = new FormData(); form.append("file", new Blob([fs.readFileSync("recording.wav")]), "recording.wav"); form.append("language", "en"); form.append("format", "json"); const res = await fetch("https://whisper.ipsecure.ca/transcribe", { method: "POST", body: form }); const data = await res.json(); console.log(data.text);
import requests res = requests.post( "https://whisper.ipsecure.ca/transcribe", files={"file": open("recording.wav", "rb")}, data={"language": "en", "format": "json"} ) print(res.json()["text"])
# Single file from URL curl -X POST https://whisper.ipsecure.ca/transcribe \ -H "Content-Type: application/json" \ -d '{ "url": "https://example.com/call.wav", "language": "en", "vad_filter": true }'
const res = await fetch("https://whisper.ipsecure.ca/transcribe", { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ url: "https://example.com/call.wav", language: "en", vad_filter: true }) }); const data = await res.json(); console.log(data);
import requests res = requests.post( "https://whisper.ipsecure.ca/transcribe", json={ "url": "https://example.com/call.wav", "language": "en", "vad_filter": True } ) print(res.json())
# Async transcription (fire and forget) curl -X POST https://whisper.ipsecure.ca/transcribe \ -F "file=@longfile.mp3" \ -F "wait=false" \ -F "callbackUrl=https://yourserver.com/webhook"
const fs = require("fs"); const form = new FormData(); form.append("file", new Blob([fs.readFileSync("longfile.mp3")]), "longfile.mp3"); form.append("wait", "false"); form.append("callbackUrl", "https://yourserver.com/webhook"); const res = await fetch("https://whisper.ipsecure.ca/transcribe", { method: "POST", body: form }); const { jobId, statusUrl } = await res.json(); console.log("Job queued:", jobId);
import requests res = requests.post( "https://whisper.ipsecure.ca/transcribe", files={"file": open("longfile.mp3", "rb")}, data={ "wait": "false", "callbackUrl": "https://yourserver.com/webhook" } ) job = res.json() print(f"Job queued: {job['jobId']}")
Check the status of a transcription job. Returns the current state, queue position (if pending), and the result when complete.
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| jobId | string | yes | The unique job identifier returned from a transcribe request. |
Response
{
"success": true,
"jobId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"status": "completed",
"queuePosition": 0,
"result": {
"text": "Transcribed text here...",
"language": "en",
"duration": 12.45,
"segments": [...]
}
}# Check job status curl https://whisper.ipsecure.ca/transcribe/status/YOUR_JOB_ID
const jobId = "YOUR_JOB_ID"; const res = await fetch(`https://whisper.ipsecure.ca/transcribe/status/${jobId}`); const data = await res.json(); console.log(data.status, data.result);
import requests job_id = "YOUR_JOB_ID" res = requests.get(f"https://whisper.ipsecure.ca/transcribe/status/{job_id}") data = res.json() print(data["status"], data.get("result"))
Submit a batch of audio files for transcription. Upload up to 200 files via multipart/form-data or provide an array of URLs in a JSON body. All jobs are processed asynchronously.
Request Parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
| file[] | file[] | conditional | Array of audio files (multipart). Required if urls not provided. | |
| urls | string[] | conditional | Array of remote audio URLs (JSON body). Required if file[] not provided. | |
| language | string | no | auto | Language code applied to all files in the batch. |
| vad_filter | boolean | no | false | Enable VAD filtering for all files. |
| callbackUrl | string | no | Webhook URL to receive batch completion notification. |
Response
{
"success": true,
"batchId": "batch-9f8e7d6c-5b4a-3210-fedc-ba0987654321",
"total": 3,
"jobIds": [
"job-aaa111",
"job-bbb222",
"job-ccc333"
],
"statusUrl": "https://whisper.ipsecure.ca/transcribe/batch/batch-9f8e7d6c-5b4a-3210-fedc-ba0987654321",
"callbackUrl": "https://yourserver.com/webhook/batch-done"
}# Batch transcription from URLs curl -X POST https://whisper.ipsecure.ca/transcribe/batch \ -H "Content-Type: application/json" \ -d '{ "urls": [ "https://yourserver.com/recordings/call1.wav", "https://yourserver.com/recordings/call2.wav", "https://yourserver.com/recordings/call3.wav" ], "language": "en", "vad_filter": true, "callbackUrl": "https://yourserver.com/webhook/batch-done" }'
const res = await fetch("https://whisper.ipsecure.ca/transcribe/batch", { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ urls: [ "https://yourserver.com/recordings/call1.wav", "https://yourserver.com/recordings/call2.wav", "https://yourserver.com/recordings/call3.wav" ], language: "en", vad_filter: true, callbackUrl: "https://yourserver.com/webhook/batch-done" }) }); const batch = await res.json(); console.log("Batch ID:", batch.batchId);
import requests res = requests.post( "https://whisper.ipsecure.ca/transcribe/batch", json={ "urls": [ "https://yourserver.com/recordings/call1.wav", "https://yourserver.com/recordings/call2.wav", "https://yourserver.com/recordings/call3.wav" ], "language": "en", "vad_filter": True, "callbackUrl": "https://yourserver.com/webhook/batch-done" } ) batch = res.json() print(f"Batch ID: {batch['batchId']}")
Check the status of a batch transcription request. Returns progress percentage, individual job statuses, and results for completed jobs.
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| batchId | string | yes | The batch identifier returned from a batch transcribe request. |
Response
{
"success": true,
"batchId": "batch-9f8e7d6c-5b4a-3210-fedc-ba0987654321",
"status": "processing",
"total": 3,
"completed": 1,
"failed": 0,
"progress": 33.3,
"jobs": [
{ "jobId": "job-aaa111", "status": "completed" },
{ "jobId": "job-bbb222", "status": "processing" },
{ "jobId": "job-ccc333", "status": "queued" }
]
}# Check batch status curl https://whisper.ipsecure.ca/transcribe/batch/YOUR_BATCH_ID
const batchId = "YOUR_BATCH_ID"; const res = await fetch(`https://whisper.ipsecure.ca/transcribe/batch/${batchId}`); const data = await res.json(); console.log(`Progress: ${data.progress}%`);
import requests batch_id = "YOUR_BATCH_ID" res = requests.get(f"https://whisper.ipsecure.ca/transcribe/batch/{batch_id}") data = res.json() print(f"Progress: {data['progress']}%")
Retrieve the transcription result for a completed job. Supports multiple output formats including plain text, SRT subtitles, WebVTT, and full JSON with segments and word timestamps.
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| jobId | string | yes | The unique job identifier. |
Query Parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
| format | string | no | json | Output format: json, text, srt, or vtt. |
# Get result as plain text curl "https://whisper.ipsecure.ca/transcribe/result/YOUR_JOB_ID?format=text"
const jobId = "YOUR_JOB_ID"; const res = await fetch(`https://whisper.ipsecure.ca/transcribe/result/${jobId}?format=text`); const text = await res.text(); console.log(text);
import requests job_id = "YOUR_JOB_ID" res = requests.get(f"https://whisper.ipsecure.ca/transcribe/result/{job_id}", params={"format": "text"}) print(res.text)
# Get result as SRT subtitles curl "https://whisper.ipsecure.ca/transcribe/result/YOUR_JOB_ID?format=srt"
const jobId = "YOUR_JOB_ID"; const res = await fetch(`https://whisper.ipsecure.ca/transcribe/result/${jobId}?format=srt`); const srt = await res.text(); console.log(srt);
import requests job_id = "YOUR_JOB_ID" res = requests.get(f"https://whisper.ipsecure.ca/transcribe/result/{job_id}", params={"format": "srt"}) print(res.text)
Cancel a pending or in-progress transcription job, or delete a completed job and its results. Returns the final status of the job.
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| jobId | string | yes | The unique job identifier to cancel or delete. |
Response
{
"success": true,
"jobId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"status": "cancelled"
}# Cancel or delete a job curl -X DELETE https://whisper.ipsecure.ca/transcribe/job/YOUR_JOB_ID
const jobId = "YOUR_JOB_ID"; const res = await fetch(`https://whisper.ipsecure.ca/transcribe/job/${jobId}`, { method: "DELETE" }); const data = await res.json(); console.log(data.status);
import requests job_id = "YOUR_JOB_ID" res = requests.delete(f"https://whisper.ipsecure.ca/transcribe/job/{job_id}") print(res.json())
Webhook Callbacks
When you provide a callbackUrl, the API sends a POST request with a JSON body to your endpoint when transcription completes. Ensure your endpoint returns a 2xx status code.
Single Transcription Callback
{
"event": "transcription.complete",
"jobId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"success": true,
"result": {
"text": "Transcribed text here...",
"language": "en",
"language_probability": 0.98,
"duration": 12.45,
"processing_time": 3.21,
"word_count": 10,
"segments": [...]
}
}Batch Completion Callback
{
"event": "batch.complete",
"batchId": "batch-9f8e7d6c-5b4a-3210-fedc-ba0987654321",
"total": 3,
"succeeded": 3,
"failed": 0,
"results": [
{
"jobId": "job-aaa111",
"success": true,
"text": "First file transcription..."
},
{
"jobId": "job-bbb222",
"success": true,
"text": "Second file transcription..."
},
{
"jobId": "job-ccc333",
"success": true,
"text": "Third file transcription..."
}
]
}