HLS

Features

HLS extension capabilities

HLS Streaming Server

Serve master playlists, media playlists, and segments over HTTP with standard HLS protocol compliance. The extension registers HTTP routes for playlist and segment serving:

EndpointDescription
GET /hls/:streamID/master.m3u8Master playlist with all quality variants
GET /hls/:streamID/variants/:variantID/playlist.m3u8Media playlist for a specific variant
GET /hls/:streamID/variants/:variantID/segment_:num.tsIndividual media segment
POST /hls/streams/:streamID/ingestIngest a segment for a live stream

Stream Lifecycle

Full lifecycle management for both live and VOD streams:

manager := hls.MustGet(app.Container())

// Create a live stream
stream, _ := manager.CreateStream(ctx, hls.StreamOptions{
    Title:       "Conference Stream",
    Type:        hls.StreamTypeLive,
    TargetDuration: 6,    // Segment duration in seconds
    DVRWindowSize:  10,   // Sliding window of segments
    TranscodeProfiles: hls.DefaultProfiles(),
})

// Start live streaming
manager.StartLiveStream(ctx, stream.ID)

// Stop live streaming
manager.StopLiveStream(ctx, stream.ID)

// Delete a stream
manager.DeleteStream(ctx, stream.ID)

// List all streams
streams, _ := manager.ListStreams(ctx)

// Get a specific stream
stream, _ := manager.GetStream(ctx, streamID)

Each Stream tracks:

  • ID, Title, Description, Type (live/VOD/event)
  • Status (created/live/stopped/ended)
  • Variants -- quality variants with playlists
  • ViewerCount, TotalViews, TotalBandwidth
  • CreatedAt, StartedAt, EndedAt, Duration

Adaptive Bitrate Streaming

Master playlists reference multiple quality variants so clients automatically switch between bitrates based on network conditions:

// Get the master playlist
master, _ := manager.GetMasterPlaylist(ctx, stream.ID)
// Contains references to all quality variants:
// #EXT-X-STREAM-INF:BANDWIDTH=800000,RESOLUTION=640x360
// variants/360p/playlist.m3u8
// #EXT-X-STREAM-INF:BANDWIDTH=2800000,RESOLUTION=1280x720
// variants/720p/playlist.m3u8

Default Transcode Profiles

ProfileResolutionVideo BitrateAudio Bitrate
360p640x360800 kbps64 kbps
480p854x4801400 kbps96 kbps
720p1280x7202800 kbps128 kbps
1080p1920x10805000 kbps192 kbps
4K3840x216014000 kbps256 kbps

Custom profiles can be defined:

profile := hls.TranscodeProfile{
    Name:       "custom-480p",
    VideoCodec: "h264",
    AudioCodec: "aac",
    Width:      854,
    Height:     480,
    Bitrate:    1500000,
    FrameRate:  24.0,
    Preset:     "fast",
}

Multi-Variant Transcoding

FFmpeg-based transcoding generates multiple quality profiles from ingested media:

// Transcode a stream into multiple variants
manager.TranscodeVideo(ctx, stream.ID, []hls.TranscodeProfile{
    hls.Profile720p,
    hls.Profile480p,
    hls.Profile360p,
})

The transcoder supports:

  • File-based transcoding: TranscodeFile(ctx, inputPath, profile)
  • Stream-based transcoding: TranscodeStream(ctx, input, output, profile)
  • Job management: StartJob, GetJob, CancelJob
  • Video info extraction: GetVideoInfo(ctx, inputPath)

Segment Ingestion

Push segments to the server for live streams:

manager.IngestSegment(ctx, stream.ID, &hls.Segment{
    VariantID:   "720p",
    SequenceNum: 42,
    Duration:    6.0,
    Data:        segmentBytes,
})

The Segment struct contains:

  • StreamID, VariantID -- which stream and quality variant
  • SequenceNum -- monotonically increasing segment number
  • Duration -- segment duration in seconds
  • Data -- raw segment bytes (TS format)
  • Size -- computed from data length
  • CreatedAt -- timestamp

DVR Window

Configurable sliding window of segments in live playlists for time-shifted playback:

hls.StreamOptions{
    DVRWindowSize: 10, // Keep 10 segments in the live playlist
}

Older segments beyond the DVR window are removed from the playlist but remain in storage until the retention policy deletes them. This allows viewers to rewind within the window.

VOD (Video on Demand)

Create on-demand streams from pre-recorded content:

// From a reader
stream, _ := manager.CreateVOD(ctx, sourceReader, hls.VODOptions{
    Title:             "Recorded Talk",
    TranscodeProfiles: hls.DefaultProfiles(),
})

// From a file path
stream, _ := manager.CreateVODFromFile(ctx, "/path/to/video.mp4", hls.VODOptions{
    Title:             "Recorded Talk",
    TranscodeProfiles: hls.DefaultProfiles(),
})

VOD streams have a fixed playlist with all segments available from the start.

Storage Integration

Segments and playlists are stored via the Forge storage extension, supporting any configured backend (local filesystem, S3, etc.):

// Segments are automatically stored via the storage extension
// Retrieve a segment URL for CDN delivery
url, _ := manager.GetSegmentURL(ctx, streamID, variantID, segmentNum)

Segment retention is configurable (default: 24 hours) with periodic cleanup of expired segments.

Stream Statistics

Per-stream monitoring of viewer count, bandwidth, and segment metrics:

stats, _ := manager.GetStreamStats(ctx, stream.ID)
// stats.ViewerCount    -- current viewers
// stats.TotalViews     -- total unique views
// stats.TotalBandwidth -- total bytes served
// stats.SegmentCount   -- total segments ingested
// stats.Duration       -- stream duration

viewers, _ := manager.GetActiveViewers(ctx, stream.ID)

Distributed Mode

Scale across multiple nodes using the consensus extension for leader election and stream ownership routing:

hls.NewExtension(
    hls.WithDistributed(true),
    hls.WithNodeID("node-1"),
)

In distributed mode:

  • Each stream is owned by a single node.
  • If a stream owner goes down, another node takes over (automatic failover).
  • Segment ingestion is routed to the owning node.
  • Playlist serving can be handled by any node.

Additional Features

  • CORS support -- configurable CORS headers for cross-origin playback from web players.
  • Authentication -- optional auth requirement for stream access.
  • Caching -- configurable caching of playlists and segments with TTL (default: 5 minutes).
  • Limits -- configurable max streams, max viewers per stream, and max bandwidth per stream.
  • Stream types -- live (sliding window), VOD (complete playlist), and event (growing playlist).

How is this guide?

On this page