Docs / Guides / Ingesting media

Ingesting media

Get source video into open-videocore: from a URL, direct upload, presigned/multipart upload, or an object storage watch-folder.

Every asset starts as a record, then gets its source media attached to it one of four ways. Pick the one that matches where your video already lives.

1. Create the asset record

An asset always starts as a record you create explicitly, or one created for you by the ingest-from-URL shortcut below.

Request
curl -X POST https://<your-instance>/api/v1/assets \
  -H "Content-Type: application/json" \
  -d '{"title": "Keynote recording", "description": "Opening keynote, main stage"}'

See POST /api/v1/assets/ — full field list in the Assets reference.

2. Ingest from a public URL

If the source file is already reachable over HTTP(S), skip the manual create step — this creates the asset and starts the download in one call:

Request
curl -X POST https://<your-instance>/api/v1/assets/ingest-url \
  -H "Content-Type: application/json" \
  -d '{"sourceUrl": "https://example.com/video.mp4", "title": "Keynote recording"}'

This returns a Job of type ingest-url. Poll GET /api/v1/jobs/{id} until status is done; the job's assetId is the asset to work with next.

3. Direct upload (small files)

For files you already have locally and that are small enough to send in one request:

Request
curl -X PUT https://<your-instance>/api/v1/assets/<id>/upload \
  -H "Content-Type: video/mp4" \
  --data-binary @video.mp4

4. Presigned upload (browser / large single-part)

To upload directly to object storage from a browser or client without proxying bytes through the API, get a presigned URL first, upload to it, then tell the API the upload finished:

Request
curl -X POST https://<your-instance>/api/v1/assets/<id>/upload-url
# -> { "url": "https://...", ... } — PUT your file bytes to that URL, then:
curl -X POST https://<your-instance>/api/v1/assets/<id>/upload-complete

5. Multipart upload (large files)

For files too large for a single PUT, initiate a multipart upload, request a presigned URL per part, upload each part directly to storage, then complete:

  1. POST /api/v1/assets/{id}/multipart/initiate
  2. GET /api/v1/assets/{id}/multipart/{uploadId}/part-url — once per part
  3. POST /api/v1/assets/{id}/multipart/{uploadId}/complete
  4. If something goes wrong: DELETE /api/v1/assets/{id}/multipart/{uploadId} — abort

6. Watch-folder ingest

Point open-videocore at an object storage bucket and it will pick up new files automatically, without any per-file API call:

Request
curl -X POST https://<your-instance>/api/v1/storage/buckets/<bucket>/watch-folder/toggle \
  -H "Content-Type: application/json" \
  -d '{"enabled": true}'

See Storage reference for bucket listing and the poller's own start/stop controls in Admin.

Every path above ends at the same place: an Asset with status moving from uploading to processing to ready (or failed). Watch that field, or an asset.ready / asset.failed webhook, rather than polling the job directly once the source file has landed.