Description
It is not sufficiently easy for application to control retry behavior. We allow detailed configuration at the networking level (NetworkingEngine
and the various retryParameters
configs) but not at the streaming level (StreamingEngine
and streaming
config).
Summary of previous discussions and work in this area:
- In 403 errors are ignored #762, @Ross-cz filed a bug that the library would infinitely retry failed requests, because
StreamingEngine
didn't give up, even afterNetworkingEngine
failed an individual request. - In Infinite retries even on CRITICAL severity #830, @bhh1988 filed a similar bug about infinite retries being unkind to servers.
- Pull Stop infinitely retrying on network errors for VOD #842 landed, in which @bhh1988 adds config setting
streaming.infiniteRetriesForLiveStreams
to decide behavior for live streams (infinite retry or no retries), while VOD never retries at the streaming level. - The PR was cherry-picked and released in v2.1.3.
- In 403 errors are ignored #762 (comment), @Ross-cz asked for something more general and robust, with more application control over behavior.
- In Segment Requests are not being cancelled/aborted on custom retryParameters #922, @worg, @vhuerta, @msol, and @migvz complain about retry and timeout behavior. At this point, we believe this issue to be unrelated, but we are not certain.
- In SHAKA and Offline Events #937, @boredom2 filed a bug in which going offline causes a temporary network error. Because Shaka Player no longer retries on VOD, there is no way for the app to retry streaming when it comes back online.
Previous behavior (v2.0.0 - v2.1.2):
- all types: keep retrying on failure
Current behavior (v2.1.3 - v2.1.6):
- VOD: stop on failure
- live: use
streaming.infiniteRetriesForLiveStreams
config to decide behavior (defaulttrue
)
Proposed new behavior (v2.2.0+):
- all types: invoke a configurable callback to decide behavior
The default callback would be along these lines and would reproduce current default behavior:
function defaultStreamingFailureCallback(error) {
if (player.isLive()) {
if (player.getConfiguration().streaming.infiniteRetriesForLiveStreams) {
player.retryStreaming();
}
}
}
The infiniteRetriesForLiveStreams
config would become deprecated and scheduled for removal in v2.3.0.
The application could achieve any of the previous behaviors through the callback, or any custom logic desired. For example:
function alwaysRetryOnFailureCallback(error) {
player.retryStreaming();
}
function neverRetryCallback(error) {}
function retryLiveOnFailureCallback(error) {
if (player.isLive()) {
player.retryStreaming();
}
}
function retryOnSpecificHttpErrorsCallback(error) {
if (error.code == shaka.util.Error.Code.BAD_HTTP_STATUS) {
var statusCode = error.data[1];
var retryCodes = [ 502, 503, 504, 520 ];
if (retryCodes.indexOf(statusCode >= 0)) {
player.retryStreaming();
}
}
}
The retryStreaming()
method would be exported from Player
and could be called from outside the callback as well. The callback would not replace or modify the behavior of existing error events. So applications could:
- choose to delay action until a user has been prompted
- react to a dispatched error event instead of through the callback mechanism
- delay action while offline and retry streaming once the browser is back online
Would this proposal meet everyone's needs? Would it be best to keep the default behavior as-is (no auto-retry for VOD, infinite auto-retry for live)? Or should we select a new default starting in v2.2 or v2.3 (such as no auto-retries at all)?