Build with Sluby
Upload a video from your server, wait until it is ready, and play it in a React app.
In this walkthrough you upload a video from a Node.js script with @sluby/sdk, wait until Sluby has transcoded it and stored it on Sia, and play it in the browser with @sluby/player. The API key stays on your server; the browser plays the public video without one.
You need the address of a Sluby server, for example https://sluby.example.com, and a Studio account on it.
Create an API key
In the Studio, open API keys under Developers and click Create key. Give the key a name and keep the scopes upload and read selected: upload sends the file and read checks when it is ready. Click Create key and copy the key. The Studio shows it only once.
Keep the key on your server, for example in an environment variable:
SLUBY_URL=https://sluby.example.com
SLUBY_API_KEY=sluby_...Create and manage API keys covers the page in detail, and API conventions lists what each scope allows.
Install the packages
On the server, install the SDK. Check that your Node.js version is one the SDK supports (package facts).
npm install @sluby/sdkIn your React app, install the SDK and the player (supported React versions):
npm install @sluby/sdk @sluby/playerUpload the video and wait until it is ready
This script runs on your server. It uploads video.mp4, prints the id of the new video asset, and waits until processing has finished.
import { openAsBlob } from 'node:fs';
import { SlubyClient } from '@sluby/sdk';
const { SLUBY_URL, SLUBY_API_KEY } = process.env;
if (!SLUBY_URL || !SLUBY_API_KEY) throw new Error('Set SLUBY_URL and SLUBY_API_KEY.');
const client = new SlubyClient({ baseUrl: SLUBY_URL, apiKey: SLUBY_API_KEY });
// a Blob backed by the file: the SDK reads it one chunk at a time
const file = await openAsBlob('./video.mp4');
const upload = client.uploads.upload(file, {
title: 'My first video',
onProgress: (percent) => console.log(`uploaded ${percent}%`),
});
const assetId = await upload.assetId;
console.log(`asset ${assetId} created`);
await upload;
const asset = await client.assets.waitForReady(assetId, { timeout: 30 * 60_000 });
console.log(`ready: ${asset.id}, ${asset.resolution}`);Run it with your environment loaded:
node --env-file=.env upload.mjsupload.assetId resolves as soon as the server has created the upload, before the bytes finish. waitForReady polls the asset until its status is ready, and the 30 minute timeout gives a long video time to process. Wait for processing covers its defaults and errors.
Play the video
A public video plays from its stream URL, which the SDK builds without a request and without a key. This component runs in the browser:
import { SlubyClient } from '@sluby/sdk';
import { SlubyPlayer } from '@sluby/player';
// no API key: a public video plays from its stream URL
const client = new SlubyClient({ baseUrl: 'https://sluby.example.com' });
export function Video({ assetId }: { assetId: string }) {
return (
<SlubyPlayer src={client.playback.streamUrl(assetId)} controls style={{ width: '100%' }} />
);
}Render <Video assetId="..." /> with the id the script printed.
Next steps
Upload videos from your app
Progress, pause, resume and cancel, files that start in a browser, and uploads with any tus client.
Play videos in React
Stream from Sia, pick a delivery mode, show a quality menu and build your own controls.
Play videos without React
Drive hls.js yourself, with or without the Sia loaders.
Serve private videos
Mint signed URLs on your server, renew them during playback and revoke them.
Manage your library from a server
List, search, edit, retry and delete videos.
Receive webhooks
Get a signed request when a video is ready or fails.
Reference
API conventions
Authentication, scopes, errors, pagination and rate limits.
@sluby/sdk reference
Every SDK namespace, method and error class.
@sluby/player reference
Every player prop, the handle, useVideo and the loaders.
Webhook events
Event types, payloads, headers and the signature scheme.
To learn how Sluby works inside, start with Architecture.