Encode a video
POST /api/transcode queues an H.264 HLS ladder.
Send the API key as a Bearer token from your server.
source_path is a key in the bucket stored on that API key.
A 202 response includes job_id.
<?php
$apiKey = getenv('CC_ENCODE_API_KEY');
if ($apiKey === false || $apiKey === '') {
throw new RuntimeException('CC_ENCODE_API_KEY is not set');
}
$payload = json_encode([
'source_path' => 'videos/source.mp4',
'qualities' => ['1080p', '720p', '480p'],
'webhook_url' => 'https://yourapp.com/webhooks/transcode',
], JSON_THROW_ON_ERROR);
$ch = curl_init('https://services.closedcircuit.io/api/transcode');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => [
'Authorization: Bearer '.$apiKey,
'Content-Type: application/json',
'Accept: application/json',
],
CURLOPT_POSTFIELDS => $payload,
]);
$body = curl_exec($ch);
if ($body === false) {
throw new RuntimeException(curl_error($ch));
}
$status = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
$job = json_decode($body, true, 512, JSON_THROW_ON_ERROR);
// $status is 202. $job['job_id'] is the encode.
use Illuminate\Support\Facades\Http;
// config/services.php
// 'cc_encode' => ['key' => env('CC_ENCODE_API_KEY')],
$response = Http::withToken(config('services.cc_encode.key'))
->acceptJson()
->post('https://services.closedcircuit.io/api/transcode', [
'source_path' => 'videos/source.mp4',
'qualities' => ['1080p', '720p', '480p'],
'webhook_url' => 'https://yourapp.com/webhooks/transcode',
])
->throw();
$jobId = $response->json('job_id');
const apiKey = process.env.CC_ENCODE_API_KEY;
if (!apiKey) {
throw new Error('CC_ENCODE_API_KEY is not set');
}
type EncodeJob = {
job_id: string;
status: string;
estimated_credits?: number;
};
const response = await fetch('https://services.closedcircuit.io/api/transcode', {
method: 'POST',
headers: {
Authorization: `Bearer ${apiKey}`,
'Content-Type': 'application/json',
Accept: 'application/json',
},
body: JSON.stringify({
source_path: 'videos/source.mp4',
qualities: ['1080p', '720p', '480p'],
webhook_url: 'https://yourapp.com/webhooks/transcode',
}),
});
if (!response.ok) {
throw new Error(await response.text());
}
const job = (await response.json()) as EncodeJob;
const apiKey = process.env.CC_ENCODE_API_KEY;
if (!apiKey) {
throw new Error('CC_ENCODE_API_KEY is not set');
}
const response = await fetch('https://services.closedcircuit.io/api/transcode', {
method: 'POST',
headers: {
Authorization: `Bearer ${apiKey}`,
'Content-Type': 'application/json',
Accept: 'application/json',
},
body: JSON.stringify({
source_path: 'videos/source.mp4',
qualities: ['1080p', '720p', '480p'],
webhook_url: 'https://yourapp.com/webhooks/transcode',
}),
});
if (!response.ok) {
throw new Error(await response.text());
}
const job = await response.json();
curl -X POST https://services.closedcircuit.io/api/transcode \
-H "Authorization: Bearer $API_KEY" \
-H "Content-Type: application/json" \
-d '{"source_path":"videos/source.mp4","qualities":["1080p","720p","480p"],"webhook_url":"https://yourapp.com/webhooks/transcode"}'
Read the job with GET /api/transcode/{job_id} and the same token.
status is completed when the ladder is in the bucket.
Omit webhook_url if you will poll.
Product page: CC Encode.