---
title: Players and the OTT/DVR reserve
url: https://doc2.pstreamer.tv/en/manual/extras/ott_players.html
lang: en
product: Perfect Streamer
version: 2.0.2.423
---

# Players and the OTT/DVR reserve

> **Important**
>
> **Beta version 2.1.** What is described here exists only in beta version 2.1: it is installed from the beta repository and only with a licence; the stable version 2.0.2 and the demo edition do not have it. The beta version comes without warranty, and support is best effort ([Beta testing programme](beta.md#extras-beta)).

The OTT/DVR reserve protects viewers of OTT delivery in two ways, and which of them are available depends on the player ([OTT groups](../webui/reserves.md#webui-fleet-reserves-ott)):

- **Move during playback.** The HLS master playlist names up to two other nodes of the OTT group as backup variants. A player that can switch to backup variants moves to another node by itself when its node stops serving the live window, and the viewer does not leave the player ([Moving viewers to another node](../webui/reserves.md#webui-fleet-reserves-ott-failover)).
- **Redirect on opening.** The node answers with a `302` redirect to another node of the group if the viewer opens a stream that is not running here, or asks for an archive period outside this node’s archive range; gaps within the range the node serves itself. If the period is not recorded on any node, the response is `404` (`reserve: no recording for this period`) ([Redirecting viewers](../webui/reserves.md#webui-fleet-reserves-ott-redirects)).

## What the player gets

The node decides by the player’s User-Agent header and the `rsv` parameter in the master playlist address whether to give it backup variants. The table shows what the node serves to each player. The node’s responses have been tested for every User-Agent rule. The switch to the backup node itself has been tested only in Chrome on Windows (hls.js 1.5, page over HTTP); on the other players and devices it has not been tested in this beta version, and neither has the move by `302`.

| Player | Backup variants (move during playback) | `302` redirect (new viewer, archive) |
| --- | --- | --- |
| Safari, iOS, tvOS, Apple TV (AVPlayer) | Yes; switching not tested | Yes; not tested |
| ExoPlayer and Media3 (Android, Android TV) | Yes; switching not tested | Yes; not tested |
| Browser players: hls.js, Shaka Player, Video.js | Yes, if the browser sends the `Sec-Fetch-Mode` or `Sec-Fetch-Dest` headers (modern browsers over HTTPS). Since version 2.1.0.469 also without them, for example over HTTP: if the request carries an `Origin` header, or a `Referer` of a page of the node itself (below). Switching tested in Chrome on Windows (hls.js 1.5, over HTTP, without `rsv=1`); in other browsers not tested | Yes; not tested |
| Smart TV apps on a browser player (Tizen, webOS), Chromecast | If the device’s browser engine sends the `Sec-Fetch` headers, and since version 2.1.0.469 also without them, by the same rule as browsers over HTTP. Not tested | Yes; not tested |
| Built-in Smart TV players (AVPlay on Tizen, the webOS media player) | No: they get no backup variants except with `rsv=1`. Not tested | Yes; not tested |
| VLC and LibVLC, ffmpeg-based players, mpv, Kodi, GStreamer, ijkplayer, exteplayer | No, not even with `rsv=1`: they work as before | Yes. For VLC, the archive from another node has been tested; the others not tested |
| Set-top boxes and players without a User-Agent | No, not even with `rsv=1`: they work as before | Yes; not tested |
| The operator’s own application | With `rsv=1` in the master playlist address; `rsv=0` turns it off | Yes |

**Browser player without Sec-Fetch headers** (since version 2.1.0.469). Browsers send the `Sec-Fetch` headers only to HTTPS addresses, so a browser player on an HTTP page used to get no backup variants. Now a request without these headers counts as a browser request if its User-Agent contains `Mozilla/`, it is neither a range request (`Range`) nor a page load, and it carries an `Origin` header or, for a player page served by the node itself, a `Referer` with this node’s address and port. Tested in Chrome on Windows with hls.js 1.5: the master playlist named a backup without `rsv=1`, and when the node’s input was paused the player moved to another node. Other browsers over HTTP have not been tested.

The node serves the `302` redirect to any player, for HLS, LL-HLS and DASH: it is an ordinary HTTP redirect to the full address of another node before playback starts. Players usually follow redirects by themselves.

Players from the “No, not even with `rsv=1`” list open all variants one after another at start or on a `404` response to a playlist, so the node never gives them backup lines. A player that is not in the table and does not look like a browser player gets no backup variants either; add `rsv=1` to the address if it can use them, and test the move on your player. How many master playlists the node has served without a backup because of the player is shown by the “Masters with no backup lines” row of the “OTT view key” block ([Moving viewers to another node](../webui/reserves.md#webui-fleet-reserves-ott-failover)).

## Limitations and tips

- **Single HLS streams only.** In this beta version backup variants are given only to single streams whose members on different nodes take the same source. Adaptive bundles and LL-HLS cannot move during playback yet, but the redirect on opening works for them.
- **DASH.** For DASH this beta version has only the redirect on opening.
- **hls.js timeouts.** Set short playlist and segment loading timeouts, about one target segment duration, 2–3 seconds: then the player quickly leaves a stalled node.
- **Address scheme.** The backup node must be reachable by the viewer over the same scheme: an HTTPS page needs an HTTPS address of the backup node. Set each node’s HTTP server “Host name” to the name its certificate is issued for ([Streaming HTTP server](../webui/administration.md#webui-http-server)).
- **Audio in the browser.** Since version 2.1.0.469 the HLS master playlist names the stream’s real audio codec ([Delivery modes](../streamer/ott_dvr.md#streamer-ott-modes)); before that, every channel was announced as AAC, and a channel with MP2 audio did not play in the browser.

  - All browser players support AAC.
  - MP2: hls.js in Chromium now plays it (tested with audio only); Google Chrome, Edge, Firefox and Safari not tested. MP3 not tested.
  - AC-3 and E-AC-3: hls.js and Shaka in desktop Chrome and Firefox do not accept such a variant. Safari and Edge on Windows not tested.
  - In LL-HLS and DASH the segments carry only AAC or AC-3 audio: MP2, MP3 or E-AC-3 audio is not there at all.

  The most reliable option for browser viewers is an AAC track in the channel or a transcoder.
- **VLC and other players without backup variants** do not carry an open viewing session over to another node. When the node’s input stops, VLC plays out its buffer, stops, and only on a new opening gets a `302` to another node; in the test this took about 40–50 seconds. The redirect to another node’s archive has been tested in VLC.
- **Interlaced video in the browser.** Browser players (hls.js and similar MSE-based players) do not decode interlaced H.264 with field coding (PAFF, MBAFF) reliably, and that is how broadcast SD 576i and HD 1080i usually come. Playback stops after a few seconds with a decoding error (`PIPELINE_ERROR_DECODE`); this happened, for example, in Chrome on Windows with a 576i H.264 Main channel, while VLC showed the same channel normally. For browser viewers, give the channel a progressive copy through a transcoder with the “Deinterlace” setting ([Encoder settings](../streamer/transcoder.md#streamer-transcoder-encoder)). Set-top boxes, Smart TVs and VLC play interlaced video as usual.

  An interlaced channel can be seen in the stream statistics: in the “Format” field the rate is followed by `i`, for example `1920x1080@50i` (for interlaced video this is the field rate, twice the frame rate), and progressive video has `p`. With “Deep analysis” on, the “Scan type” row of the “Video codec passport” block shows the same: 2 is interlaced, 1 is progressive. For H.264 the `i` flag is set when the stream allows field coding, even if the encoder actually codes only frames.
- **Decoding errors in your own player.** On a decoding error hls.js 1.5 moves to the backup address as it does on a node failure, and the playback element stays broken afterwards. Handle media errors by calling `hls.recoverMediaError()`, and if that does not help, `hls.swapAudioCodec()` and `hls.recoverMediaError()` again, with a small limit on the number of attempts. Do not count such a move as a node failure in your statistics.
- **Subtitles** stay on the original node after the move.
- **Cache and CDN** in front of the nodes: [8.1. OTT/DVR reserve and CDN](ott_caching.md#extras-ott-cdn-reserve).
