Nodeflux Central
VoD (Video Upload)

API Reference: VoD

Endpoint unggah video per chunk dengan resume, pengelolaan video unggahan, thumbnail, dan playback berbasis waktu untuk video.

Liodra tidak memiliki otentikasi API sendiri; batasi akses port 9080 di tingkat jaringan atau reverse proxy. Basis URL memakai variabel LIODRA_API_URL (default http://localhost:9080). Semua endpoint di halaman ini memerlukan --with-vod (ENABLE_VOD=true), jika tidak menjawab 404. Semua waktu dalam UTC.


Unggah

Unggah Chunk

POST
/api/v1/videos/upload

Query Parameters

autoplay?boolean

Daftarkan video sebagai device file di channel vod setelah unggah selesai.

Defaultfalse

Request Body

multipart/form-data

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

application/json

curl -X POST "http://localhost:9080/api/v1/videos/upload?autoplay=true" \  -F file="string" \  -F filename="cctv lobby 20260915103000.mp4" \  -F chunk_index="0" \  -F total_chunks="10" \  -F total_size="10485760"
{  "success": true,  "data": {    "message": "Chunk processed successfully",    "session_id": "a1b2c3d4e5f6",    "video_id": "9876543210ab",    "chunk_index": 0,    "chunks_received": 1,    "total_chunks": 10,    "bytes_written": 1048576,    "total_size": 10485760,    "progress": 10,    "status": "uploading"  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Status Resume (Chunk yang Hilang)

GET
/api/v1/videos/upload/resume/{session_id}

Path Parameters

session_id*string

Query Parameters

filename?string

Validasi nama file (opsional).

video_id?string

Validasi ID video (opsional).

Response Body

application/json

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/videos/upload/resume/a1b2c3d4e5f6?filename=myvideo.mp4&video_id=9876543210ab"
{  "success": true,  "data": {    "message": "Session resume status retrieved",    "session_id": "a1b2c3d4e5f6",    "video_id": "9876543210ab",    "original_filename": "myvideo.mp4",    "status": "uploading",    "chunks_received": 5,    "total_chunks": 10,    "bytes_written": 5242880,    "total_size": 10485760,    "progress": 50,    "missing_chunks": [      5,      6,      7,      8,      9    ],    "can_reuse_session": true  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Status Unggahan

GET
/api/v1/videos/upload/status/{session_id}

Path Parameters

session_id*string

Response Body

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/videos/upload/status/a1b2c3d4e5f6"
{  "success": true,  "data": {    "session_id": "a1b2c3d4e5f6",    "video_id": "9876543210ab",    "original_filename": "myvideo.mp4",    "status": "uploading",    "chunks_received": 5,    "total_chunks": 10,    "bytes_written": 5242880,    "total_size": 10485760,    "progress": 50,    "missing_chunks": [      5,      6,      7,      8,      9    ],    "can_reuse_session": true,    "created_at": "2019-08-24T14:15:22Z",    "updated_at": "2019-08-24T14:15:22Z"  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Batalkan Unggahan

POST
/api/v1/videos/upload/cancel/{session_id}

Path Parameters

session_id*string

Response Body

application/json

application/json

application/json

curl -X POST "http://localhost:9080/api/v1/videos/upload/cancel/a1b2c3d4e5f6"
{  "success": true,  "data": {    "message": "Upload cancelled successfully",    "session_id": "a1b2c3d4e5f6"  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Video

Daftar Video

GET
/api/v1/videos

Query Parameters

search?string

Pencarian parsial (tidak peka huruf besar/kecil) pada id dan original_filename.

sort_by?string
Default"created_at"
Value in"original_filename" | "file_size" | "duration" | "started_at" | "created_at"
sort_order?string

Default desc untuk field waktu, asc untuk lainnya.

Value in"asc" | "desc"
page?integer
Default1
Range1 <= value
per_page?integer

0 = semua item tanpa paginasi.

Default0
Range0 <= value

Response Body

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/videos?search=lobby"
{  "success": true,  "data": {    "videos": [      {        "id": "9876543210ab",        "original_filename": "cctv lobby 20260915103000.mp4",        "file_path": "./storage/vods/cctv lobby 20260915103000.mp4",        "file_size": 10485760,        "duration": 120.5,        "started_at": "2026-09-15T10:30:00Z",        "ended_at": "2026-09-15T10:32:00Z",        "started_at_src": "filename",        "created_at": "2026-09-15T11:00:00Z",        "status": "completed",        "device": {          "name": "9876543210ab",          "url": "file://./storage/vods/cctv lobby 20260915103000.mp4",          "scheme": "file",          "channel": "vod",          "silent_audio": true,          "status": "active",          "publish_url": "rtmp://127.0.0.1:1935/vod/9876543210ab",          "uptime": "2h15m30s"        }      }    ],    "count": 1,    "pagination": {      "current_page": 1,      "per_page": 0,      "total_items": 1,      "total_pages": 1    }  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Detail Video

GET
/api/v1/videos/{id}

Path Parameters

id*string

Response Body

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/videos/9876543210ab"
{  "success": true,  "data": {    "video": {      "id": "9876543210ab",      "original_filename": "cctv lobby 20260915103000.mp4",      "file_path": "./storage/vods/cctv lobby 20260915103000.mp4",      "file_size": 10485760,      "duration": 120.5,      "started_at": "2026-09-15T10:30:00Z",      "ended_at": "2026-09-15T10:32:00Z",      "started_at_src": "filename",      "started_at_src_info": "Extracted from filename",      "created_at": "2019-08-24T14:15:22Z",      "status": "completed",      "device": {        "name": "camera_front",        "url": "rtsp://admin:***@192.168.1.100:554/stream1",        "scheme": "rtsp",        "channel": "live",        "silent_audio": true,        "status": "active",        "publish_url": "rtmp://127.0.0.1:1935/live/camera_front",        "message": "string",        "created_at": "2019-08-24T14:15:22Z",        "updated_at": "2019-08-24T14:15:22Z",        "last_seen": "2019-08-24T14:15:22Z",        "error_count": 0,        "restart_count": 0,        "suspended": false,        "uptime": "2h15m30s",        "warning": "string",        "srs_stream": {          "id": "12345",          "vhost": "__defaultVhost__",          "app": "live",          "name": "camera_front",          "video": {            "codec": "H264",            "profile": "High",            "level": "4.0"          },          "audio": {            "codec": "AAC",            "sample_rate": 44100,            "channels": 2          },          "clients": 3        }      }    }  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Perbarui Metadata Video

PATCH
/api/v1/videos/{id}

Path Parameters

id*string

Request Body

application/json

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

application/json

application/json

curl -X PATCH "http://localhost:9080/api/v1/videos/9876543210ab" \  -H "Content-Type: application/json" \  -d '{    "started_at": "2026-09-15T10:30:00Z",    "started_at_src": "manual"  }'
{  "success": true,  "data": {    "message": "string",    "video": {      "id": "9876543210ab",      "original_filename": "cctv lobby 20260915103000.mp4",      "file_path": "./storage/vods/cctv lobby 20260915103000.mp4",      "file_size": 10485760,      "duration": 120.5,      "started_at": "2026-09-15T10:30:00Z",      "ended_at": "2026-09-15T10:32:00Z",      "started_at_src": "filename",      "started_at_src_info": "Extracted from filename",      "created_at": "2019-08-24T14:15:22Z",      "status": "completed",      "device": {        "name": "camera_front",        "url": "rtsp://admin:***@192.168.1.100:554/stream1",        "scheme": "rtsp",        "channel": "live",        "silent_audio": true,        "status": "active",        "publish_url": "rtmp://127.0.0.1:1935/live/camera_front",        "message": "string",        "created_at": "2019-08-24T14:15:22Z",        "updated_at": "2019-08-24T14:15:22Z",        "last_seen": "2019-08-24T14:15:22Z",        "error_count": 0,        "restart_count": 0,        "suspended": false,        "uptime": "2h15m30s",        "warning": "string",        "srs_stream": {          "id": "12345",          "vhost": "__defaultVhost__",          "app": "live",          "name": "camera_front",          "video": {            "codec": "H264",            "profile": "High",            "level": "4.0"          },          "audio": {            "codec": "AAC",            "sample_rate": 44100,            "channels": 2          },          "clients": 3        }      }    }  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Hapus Video

DELETE
/api/v1/videos/{id}

Path Parameters

id*string

Response Body

application/json

application/json

application/json

curl -X DELETE "http://localhost:9080/api/v1/videos/9876543210ab"
{  "success": true,  "data": {    "message": "Video deleted successfully",    "video_id": "9876543210ab"  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Distribusi dan Thumbnail

Distribusi Harian

GET
/api/v1/videos/{id}/daily

Path Parameters

id*string

Response Body

application/json

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/videos/9876543210ab/daily"
{  "success": true,  "data": [    {      "year": 2026,      "month": 9,      "days": [        {          "day": 15,          "available": true,          "date": "2026-09-15"        }      ]    }  ]}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Distribusi Per Jam

GET
/api/v1/videos/{id}/hourly

Path Parameters

id*string

Query Parameters

date?string
Formatdate

Response Body

application/json

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/videos/9876543210ab/hourly?date=2026-09-15"
{  "success": true,  "data": {    "date": "2026-09-28",    "hours": [      {        "hour": 14,        "minute": 0,        "available": true,        "duration": 1800,        "time": "14:00",        "ranges": [          {            "start": "14:05",            "end": "14:15"          }        ]      }    ]  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Thumbnail

GET
/api/v1/videos/{id}/thumbnail

Path Parameters

id*string

Response Body

image/jpeg

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/videos/9876543210ab/thumbnail"
"string"
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Buat Ulang Thumbnail

POST
/api/v1/videos/{id}/thumbnail

Path Parameters

id*string

Response Body

application/json

application/json

application/json

curl -X POST "http://localhost:9080/api/v1/videos/9876543210ab/thumbnail"
{  "success": true,  "data": {    "message": "string",    "video_id": "string",    "thumbnail": {      "video_id": "9876543210ab",      "file_path": "./storage/vods/myvideo.mp4.thumb.jpg",      "file_size": 45678    }  }}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

Playback

Playback Video Unggahan

GET
/api/v1/playbacks/vod/{id}

Path Parameters

id*string

Query Parameters

start?string
Formatdate-time
duration?number
Formatfloat
transcode?boolean
download?boolean

Response Body

application/json

application/json

application/json

curl -X GET "http://localhost:9080/api/v1/playbacks/vod/9876543210ab?start=2026-09-15T10%3A30%3A30Z&duration=60&transcode=false&download=false"
{  "success": true,  "data": [    {      "start": "2026-09-15T10:30:00Z",      "duration": 120.5,      "url": "/api/v1/playbacks/vod/9876543210ab?start=2026-09-15T10:30:00Z&duration=120.5"    }  ]}
{  "success": false,  "error": "Requested start time outside video boundaries"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}
{  "success": false,  "error": "Not found",  "details": "Resource does not exist"}

On this page