videojs / mux.js

Lightweight utilities for inspecting and manipulating video container formats.
Apache License 2.0
1.08k stars 211 forks source link

PIPELINE_ERROR_DECODE in Chrome Version 60.0.3112.90 #160

Closed amanea closed 5 years ago

amanea commented 6 years ago

Hello, I apologize in advance if this is not a mux.js issue but my tests indicate that it might be.

In my current project I get mp2t packets via a websocket and I am converting those packets to fmp4 using mux.js which I then send to the browser (Windows 10 Chrome Version 60.0.3112.90) via the MSE pipeline. This works great and I am able to see the video for a little while until I get a PIPELINE_ERROR_DECODE error and the stream shuts down. This usually occurs within 30-40 minutes after the video starts playing.

In an effort to narrow down the problem I took the debug index.html (which works great when loading the whole file at a time) and modified it to take a file, read it and then cut it down to 40k slices which I then then feed to the mux.js at a fast rate. I take the output from the “done” event and append it to the MSE buffer. Doing this I also seem to get the PIPELINE_ERROR_DECODE from the browser after the video displays for a few minutes.

I cannot include the file I am using for testing (cause its too big) but any .ts file that is over 20 minutes long with 24 frames per second can be loaded to test this.

Here is the html page I have modified to slice the .ts file: <!DOCTYPE html>

        <!--[if IE 7]>         <html class="no-js lt-ie9 lt-ie8"> <![endif]-->
        <!--[if IE 8]>         <html class="no-js lt-ie9"> <![endif]-->
        <!--[if gt IE 8]><!-->
        <html class="no-js">
        <!--<![endif]-->

        <head>
            <meta charset="utf-8">
            <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
            <title></title>
            <meta name="description" content="">
            <meta name="viewport" content="width=device-width">

            <link rel="stylesheet" href="css/nomalize.min.css">
            <link rel="stylesheet" href="css/main.css">

            <script src="js/vendor/modernizr-2.6.2.min.js"></script>
            <style>
                fieldset {
                    padding: 10px;
                    border: 1px solid #ccc;
                }
            </style>
        </head>

        <body>
            <!--[if lt IE 7]>
            <p class="chromeframe">You are using an <strong>outdated</strong> browser. Please <a href="http://browsehappy.com/">upgrade your browser</a> or <a href="http://www.google.com/chromeframe/?redirect=true">activate Google Chrome Frame</a> to improve your experience.</p>
            <![endif]-->

            <div class="header-container">
                <header class="wrapper clearfix">
                    <h1 class="title">Transmux Analyzer</h1>
                </header>
            </div>

            <div class="main-container">
                <div class="main wrapper clearfix">

                    <article>
                        <header>
                            <p>
                                This page can help you inspect the results of the transmuxing to mp4 files performed by videojs-contrib-hls. It's still a
                                bit tricky to create a MSE-compatible fragmented MP4. We've had luck with
                                <a
                                    href="http://www.bento4.com/developers/dash/">Bento4</a>
                                    and ffmpeg. If you have both of those utilities installed, you can create a working MP4 like this:
                                    <pre>
        ffmpeg -i movie.ts -vn -codec copy -absf aac_adtstoasc movie-audio.mp4
        mp4fragment --track audio --fragment-duration 11000 movie-audio.mp4 movie-audio.m4s</pre>
                                    <small>Looking for the <a href="legacy.html">FLV tool</a>?</small>
                        </header>
                        <section>
                            <h2>Inputs</h2>
                            <form id="inputs">
                                <legend>
                                    The input with the checked radio box will be loaded into the player on this page.
                                </legend>
                                <fieldset>
                                    <legend>M2TS Input</legend>
                                    <div>
                                        <input id="original-active" type=radio name=active checked value="original">
                                        <label>
                        Your original .TS or .AAC segment:
                        <input type="file" id="original">
                        </label>
                                        <button id="save-muxed" type="button">Save Transmuxer Output</button>
                                    </div>
                                    <div>
                                        <label><input id="combined-output" type=checkbox name=combined checked value="combined">&nbsp;Remux output into a single output?
                        </label>
                                    </div>
                                    <div>
                                        Otherwise, output only:&nbsp;
                                        <label><input id="video-output" type=radio name=output disabled checked value="video">&nbsp;Video
                        </label>
                                        <label><input id="audio-output" type=radio name=output disabled checked value="audio">&nbsp;Audio
                        </label>
                                    </div>
                                    <div>
                                        <label><input id="reset-tranmsuxer" type=checkbox name=reset checked value="reset">&nbsp;Recreate the Transmuxer &amp; MediaSource for each file open?
                        </label>
                                    </div>
                                </fieldset>
                                <fieldset>
                                    <legend>MP4 Input</legend>
                                    <input id="working-active" type=radio name=active value="working">
                                    <label>
                        A working, MP4 version of the underlying stream
                        produced by another tool:
                        <input type="file" id="working">
                    </label>
                                </fieldset>
                                <div>
                                    <label>
                        Codecs:
                        <input id="codecs" type="text" value="avc1.64001f,mp4a.40.5">
                    </label>
                                </div>
                            </form>
                        </section>
                        <section id="video-place">
                        </section>
                        <section>
                            <h2>Comparison</h2>
                            <div id="comparison">
                                A diff of the structure of the two MP4s will appear here once you've specified an input TS file and a known working MP4.
                            </div>
                        </section>
                        <section>
                            <h2>Structure</h2>
                            <div class="result-wrapper">
                                <h3>videojs-contrib-hls</h3>
                                <pre class="vjs-boxes">
                    </pre>
                            </div>
                            <div class="result-wrapper">
                                <h3>Working</h3>
                                <pre class="working-boxes"></pre>
                            </div>
                        </section>
                    </article>

                </div>
                <!-- #main -->
            </div>
            <!-- #main-container -->

            <div class="footer-container">
                <footer class="wrapper">
                    <h3>footer</h3>
                </footer>
            </div>

            <script src="../bower_modules/mux.js/dist/mux.js"></script>

            <!-- Include QUnit for object diffs -->
            <script src="../bower_modules/mux.js/node_modules/qunitjs/qunit/qunit.js"></script>
            <script>
                /*! @source http://purl.eligrey.com/github/FileSaver.js/blob/master/FileSaver.js */
                window.saveAs = function (view) { "use strict"; if (typeof navigator !== "undefined" && /MSIE [1-9]\./.test(navigator.userAgent)) { return } var doc = view.document, get_URL = function () { return view.URL || view.webkitURL || view }, save_link = doc.createElementNS("http://www.w3.org/1999/xhtml", "a"), can_use_save_link = "download" in save_link, click = function (node) { var event = new MouseEvent("click"); node.dispatchEvent(event) }, is_safari = /Version\/[\d\.]+.*Safari/.test(navigator.userAgent), webkit_req_fs = view.webkitRequestFileSystem, req_fs = view.requestFileSystem || webkit_req_fs || view.mozRequestFileSystem, throw_outside = function (ex) { (view.setImmediate || view.setTimeout)(function () { throw ex }, 0) }, force_saveable_type = "application/octet-stream", fs_min_size = 0, arbitrary_revoke_timeout = 500, revoke = function (file) { var revoker = function () { if (typeof file === "string") { get_URL().revokeObjectURL(file) } else { file.remove() } }; if (view.chrome) { revoker() } else { setTimeout(revoker, arbitrary_revoke_timeout) } }, dispatch = function (filesaver, event_types, event) { event_types = [].concat(event_types); var i = event_types.length; while (i--) { var listener = filesaver["on" + event_types[i]]; if (typeof listener === "function") { try { listener.call(filesaver, event || filesaver) } catch (ex) { throw_outside(ex) } } } }, auto_bom = function (blob) { if (/^\s*(?:text\/\S*|application\/xml|\S*\/\S*\+xml)\s*;.*charset\s*=\s*utf-8/i.test(blob.type)) { return new Blob(["\ufeff", blob], { type: blob.type }) } return blob }, FileSaver = function (blob, name, no_auto_bom) { if (!no_auto_bom) { blob = auto_bom(blob) } var filesaver = this, type = blob.type, blob_changed = false, object_url, target_view, dispatch_all = function () { dispatch(filesaver, "writestart progress write writeend".split(" ")) }, fs_error = function () { if (target_view && is_safari && typeof FileReader !== "undefined") { var reader = new FileReader; reader.onloadend = function () { var base64Data = reader.result; target_view.location.href = "data:attachment/file" + base64Data.slice(base64Data.search(/[,;]/)); filesaver.readyState = filesaver.DONE; dispatch_all() }; reader.readAsDataURL(blob); filesaver.readyState = filesaver.INIT; return } if (blob_changed || !object_url) { object_url = get_URL().createObjectURL(blob) } if (target_view) { target_view.location.href = object_url } else { var new_tab = view.open(object_url, "_blank"); if (new_tab == undefined && is_safari) { view.location.href = object_url } } filesaver.readyState = filesaver.DONE; dispatch_all(); revoke(object_url) }, abortable = function (func) { return function () { if (filesaver.readyState !== filesaver.DONE) { return func.apply(this, arguments) } } }, create_if_not_found = { create: true, exclusive: false }, slice; filesaver.readyState = filesaver.INIT; if (!name) { name = "download" } if (can_use_save_link) { object_url = get_URL().createObjectURL(blob); setTimeout(function () { save_link.href = object_url; save_link.download = name; click(save_link); dispatch_all(); revoke(object_url); filesaver.readyState = filesaver.DONE }); return } if (view.chrome && type && type !== force_saveable_type) { slice = blob.slice || blob.webkitSlice; blob = slice.call(blob, 0, blob.size, force_saveable_type); blob_changed = true } if (webkit_req_fs && name !== "download") { name += ".download" } if (type === force_saveable_type || webkit_req_fs) { target_view = view } if (!req_fs) { fs_error(); return } fs_min_size += blob.size; req_fs(view.TEMPORARY, fs_min_size, abortable(function (fs) { fs.root.getDirectory("saved", create_if_not_found, abortable(function (dir) { var save = function () { dir.getFile(name, create_if_not_found, abortable(function (file) { file.createWriter(abortable(function (writer) { writer.onwriteend = function (event) { target_view.location.href = file.toURL(); filesaver.readyState = filesaver.DONE; dispatch(filesaver, "writeend", event); revoke(file) }; writer.onerror = function () { var error = writer.error; if (error.code !== error.ABORT_ERR) { fs_error() } }; "writestart progress write abort".split(" ").forEach(function (event) { writer["on" + event] = filesaver["on" + event] }); writer.write(blob); filesaver.abort = function () { writer.abort(); filesaver.readyState = filesaver.DONE }; filesaver.readyState = filesaver.WRITING }), fs_error) }), fs_error) }; dir.getFile(name, { create: false }, abortable(function (file) { file.remove(); save() }), abortable(function (ex) { if (ex.code === ex.NOT_FOUND_ERR) { save() } else { fs_error() } })) }), fs_error) }), fs_error) }, FS_proto = FileSaver.prototype, saveAs = function (blob, name, no_auto_bom) { return new FileSaver(blob, name, no_auto_bom) }; if (typeof navigator !== "undefined" && navigator.msSaveOrOpenBlob) { return function (blob, name, no_auto_bom) { if (!no_auto_bom) { blob = auto_bom(blob) } return navigator.msSaveOrOpenBlob(blob, name || "download") } } FS_proto.abort = function () { var filesaver = this; filesaver.readyState = filesaver.DONE; dispatch(filesaver, "abort") }; FS_proto.readyState = FS_proto.INIT = 0; FS_proto.WRITING = 1; FS_proto.DONE = 2; FS_proto.error = FS_proto.onwritestart = FS_proto.onprogress = FS_proto.onwrite = FS_proto.onabort = FS_proto.onerror = FS_proto.onwriteend = null; return saveAs }(typeof self !== "undefined" && self || typeof window !== "undefined" && window || this.content); if (typeof module !== "undefined" && module.exports) { module.exports.saveAs = saveAs } else if (typeof define !== "undefined" && define !== null && define.amd != null) { define([], function () { return saveAs }) }
            </script>
            <script>
                'use strict';
                var
                    $ = document.querySelector.bind(document),
                    inputs = $('#inputs'),
                    original = $('#original'),
                    working = $('#working'),
                    saveButton = $('#save-muxed'),

                    vjsParsed,
                    workingParsed,
                    diffParsed,
                    vjsBytes,
                    workingBytes,
                    saveConfig,
                    restoreConfig,
                    saveTA,

                    vjsBoxes = $('.vjs-boxes'),
                    workingBoxes = $('.working-boxes'),
                    workingBoxes = $('.working-boxes'),

                    muxedData,
                    muxedName,
                    transmuxer,
                    video,
                    mediaSource,
                    logevent,
                    prepareSourceBuffer;

                logevent = function (event) {
                    console.log(event.type);
                };

                saveTA = function (tarr, n) { var b = new Blob([tarr], { type: 'application/octet-binary' }); return window.saveAs(b, n); }

                saveConfig = function () {
                    var inputs = [].slice.call(document.querySelectorAll('input:not([type=file])'));

                    inputs.forEach(function (element) {
                        localStorage.setItem(element.id,
                            JSON.stringify({
                                value: element.value,
                                checked: element.checked,
                                disabled: element.disabled
                            }));
                    });
                };

                restoreConfig = function () {
                    var inputs = [].slice.call(document.querySelectorAll('input:not([type=file])'));

                    inputs.forEach(function (element) {
                        var state;

                        state = JSON.parse(localStorage.getItem(element.id));
                        if (state) {
                            element.checked = state.checked;
                            element.value = state.value;
                            element.disabled = state.disabled;
                        }
                    });
                };
                document.addEventListener('DOMContentLoaded', restoreConfig);

                // output a diff of the two parsed MP4s
                diffParsed = function () {
                    var comparison, diff, transmuxed;
                    if (!vjsParsed || !workingParsed) {
                        // wait until both inputs have been provided
                        return;
                    }
                    comparison = $('#comparison');
                    transmuxed = vjsParsed;
                    diff = '<p>A <del>red background</del> indicates ' +
                        'properties present in the transmuxed file but missing from the ' +
                        'working version. A <ins>green background</ins> indicates ' +
                        'properties present in the working version but missing in the ' +
                        'transmuxed output.</p>';
                    diff += '<pre class="mp4-diff">' +
                        QUnit.diff(muxjs.mp4.tools.textify(transmuxed, null, ' '),
                            muxjs.mp4.tools.textify(workingParsed, null, ' ')) +
                        '</pre>';

                    comparison.innerHTML = diff;
                };

                prepareSourceBuffer = function (combined, outputType, callback) {
                    var
                        buffer,
                        codecs,
                        codecsArray,
                        resetTransmuxer = $('#reset-tranmsuxer').checked;

                    if (typeof combined === 'function') {
                        callback = combined;
                        combined = true;
                    }

                    // Our work here is done if the sourcebuffer has already been created
                    if (!resetTransmuxer && window.vjsBuffer) {
                        return callback();
                    }

                    video = document.createElement('video');
                    video.controls = true;
                    mediaSource = new MediaSource();
                    video.src = URL.createObjectURL(mediaSource);
                    window.vjsVideo = video;
                    window.vjsMediaSource = mediaSource;
                    $('#video-place').innerHTML = '';
                    $('#video-place').appendChild(video);

                    mediaSource.addEventListener('error', logevent);
                    mediaSource.addEventListener('opened', logevent);
                    mediaSource.addEventListener('closed', logevent);
                    mediaSource.addEventListener('sourceended', logevent);

                    codecs = $('#codecs');
                    codecsArray = codecs.value.split(',');

                    mediaSource.addEventListener('sourceopen', function () {
                        mediaSource.duration = 0;
                        if (combined) {
                            buffer = mediaSource.addSourceBuffer('video/mp4;codecs="' + codecs.value + '"');
                        } else if (outputType === 'video') {
                            buffer = mediaSource.addSourceBuffer('video/mp4;codecs="' + codecsArray[0] + '"');
                        } else if (outputType === 'audio') {
                            buffer = mediaSource.addSourceBuffer('audio/mp4;codecs="' + (codecsArray[1] || codecsArray[0]) + '"');
                        }

                        buffer.addEventListener('updatestart', logevent);
                        buffer.addEventListener('updateend', logevent);
                        buffer.addEventListener('error', logevent);
                        window.vjsBuffer = buffer;

                        video.addEventListener('error', logevent);
                        video.addEventListener('error', function () {
                            document.getElementById('video-place').classList.add('error');
                        });

                        return callback();
                    });
                };
                var fileSlices = [],
                    sliceLength = 40000,
                    sliceIndex = 0,
                    outputType = 'video',
                        remuxedSegments = [],
                        remuxedBytesLength = 0,
                        remuxedInitSegment = null,
                        bytes,
                        createInitSegment = true, i, j,
                        sliceDataBuffer = null,
                        myTimerFunction = null,
                        sliceCounterPackets = 0,
                        sliceFlushLimit = 24,
                        sliceMAXCounterPackets = 60;

                transmuxer = new muxjs.mp4.Transmuxer({ remux: false });
                function sliceFile(segment)
                {
                    if(segment && segment != null) {
                        var isSlicing = true;
                        while(isSlicing)
                        {
                            fileSlices.push(segment.slice(sliceIndex, sliceIndex+ sliceLength));
                            sliceIndex = sliceIndex + sliceLength;
                            if(sliceLength > segment.byteLength - sliceIndex)
                            {
                                fileSlices.push(segment.slice(sliceIndex, segment.byteLength));
                                isSlicing = false;
                            }
                        }
                    }
                }
                transmuxer.on('data', function (event) {
                        if (event.type === outputType) {
                            remuxedSegments.push(event);
                            remuxedBytesLength += event.data.byteLength;
                            remuxedInitSegment = event.initSegment;
                        }
                    });
                    transmuxer.on('done', function () {
                        var offset = 0;
                        if (createInitSegment) {
                            bytes = new Uint8Array(remuxedInitSegment.byteLength + remuxedBytesLength)
                            bytes.set(remuxedInitSegment, offset);
                            offset += remuxedInitSegment.byteLength;
                            createInitSegment = false;
                        } else {
                            bytes = new Uint8Array(remuxedBytesLength);
                        }

                        for (j = 0, i = offset; j < remuxedSegments.length; j++) {
                            bytes.set(remuxedSegments[j].data, i);
                            i += remuxedSegments[j].byteLength;
                        }
                        muxedData = bytes;
                        remuxedSegments = [];
                        remuxedBytesLength = 0;

                        if ($('#original-active').checked) {
                            prepareSourceBuffer(false, outputType, function () {
                                console.log('appending...');
                                try {
                                    if(!window.vjsBuffer.updating) {
                                    window.vjsBuffer.appendBuffer(bytes);
                                    video.play();
                                    } else {
                                        console.log('dropped Packets...');
                                    }
                                } catch (exp)
                                {
                                    console.error("Append Error: "+ exp.stack);
                                }
                            });
                        }
                    });
                    function concatTypedArrays(a, b) { // a, b TypedArray of same type
                            var c = new (a.constructor)(a.length + b.length);
                            c.set(a, 0);
                            c.set(b, a.length);
                            return c;
                        }
                original.addEventListener('change', function () {
                    var reader = new FileReader();

                    // do nothing if no file was chosen
                    if (!this.files[0]) {
                        return;
                    }

                    reader.addEventListener('loadend', function () {

                        var segment = new Uint8Array(reader.result),
                            combined = document.querySelector('#combined-output').checked,
                            outputType = document.querySelector('input[name="output"]:checked').value,
                            resetTransmuxer = $('#reset-tranmsuxer').checked,
                            remuxedSegments = [],
                            remuxedInitSegment = null,
                            remuxedBytesLength = 0,
                            createInitSegment = false,
                            bytes,
                            i, j;
                        sliceFile(segment);
                        myTimerFunction = setInterval( addSlicesToQueue, 100); 
                        function addSlicesToQueue() {
                                if (fileSlices.length > 0) {
                                    if (sliceDataBuffer == null) {
                                        sliceDataBuffer = new Uint8Array(0);
                                    }
                                    sliceDataBuffer = concatTypedArrays(sliceDataBuffer, fileSlices.shift());
                                    if (sliceCounterPackets > sliceFlushLimit) {
                                        transmuxer.push(sliceDataBuffer);

                                        transmuxer.flush();
                                        sliceDataBuffer = null;
                                        sliceCounterPackets = 0;
                                        if (sliceFlushLimit < sliceMAXCounterPackets) {
                                            sliceFlushLimit++;
                                        }
                                    } else {
                                        sliceCounterPackets++;
                                    }
                                } else {
                                    clearInterval(myTimerFunction);
                                }
                            }

                    });

                    muxedName = this.files[0].name.replace('.ts', '.f4m');
                    reader.readAsArrayBuffer(this.files[0]);
                }, false);

                working.addEventListener('change', function () {
                    var reader = new FileReader();

                    reader.addEventListener('loadend', function () {
                        var bytes = new Uint8Array(reader.result);

                        if ($('#working-active').checked) {
                            prepareSourceBuffer(function () {
                                window.vjsBuffer.appendBuffer(bytes);
                                video.play();
                            });
                        }

                        workingBytes = bytes;
                        workingParsed = muxjs.mp4.tools.inspect(bytes);
                        console.log('working', workingParsed);
                        diffParsed();

                        // clear old box info
                        workingBoxes.innerHTML = muxjs.mp4.tools.textify(workingParsed, null, ' ');
                    });
                    reader.readAsArrayBuffer(this.files[0]);
                }, false);

                $('#save-muxed').addEventListener('click', function () {
                    if (muxedData && muxedName) {
                        return saveTA(muxedData, muxedName);
                    }
                });

                $('#combined-output').addEventListener('change', function () {
                    Array.prototype.slice.call(document.querySelectorAll('[name="output"'))
                        .forEach(function (el) {
                            el.disabled = this.checked;
                        }, this);
                });

                [].slice.call(document.querySelectorAll('input')).forEach(function (el) {
                    el.addEventListener('change', saveConfig);
                });
            </script>
        </body>

        </html>

Here is the error log I get from the chrome://media-internals when I run that page.

Timestamp Property Value
00:00:00 00 pipeline_state kCreated
00:00:00 00 origin_url http://127.0.0.1:8080/
00:00:00 00 url blob:http://127.0.0.1:8080/9f477dc7-3a9e-4a62-8712-921cf2a59d61
00:00:00 00 pipeline_state kStarting
00:00:00 05 found_video_stream true
00:00:00 05 video_codec_name h264
00:00:00 06 debug Video rendering in low delay mode.
00:00:00 06 video_dds false
00:00:00 06 video_decoder FFmpegVideoDecoder
00:00:00 06 pipeline_state kPlaying
00:00:00 09 video_buffering_state BUFFERING_HAVE_ENOUGH
00:00:00 48 height 480
00:00:00 48 width 640
00:00:00 48 pipeline_buffering_state BUFFERING_HAVE_ENOUGH
00:00:00 48 event PLAY
00:00:00 08 duration 14.124988
00:00:02 698 duration 15.958321
00:00:02 700 duration 29.624977
00:00:05 480 duration 30.958321
00:00:05 483 duration 45.666654
00:00:08 375 duration 46.916665
00:00:08 378 duration 62.166654
00:00:11 371 duration 63.916665
00:00:11 374 duration 79.374977
00:00:14 483 duration 80.916665
00:00:14 489 duration 97.083343
00:00:17 676 duration 98.958355
00:00:17 680 duration 115.416688
00:00:20 981 duration 116.916665
00:00:20 982 duration 134.333343
00:00:24 374 duration 135.916699
00:00:24 376 duration 153.916688
00:00:27 875 duration 154.916665
00:00:27 878 duration 173.958343
00:00:31 476 duration 174.916699
00:00:31 479 duration 194.458377
00:00:35 456 duration 195.916699
00:00:35 459 duration 215.708377
00:00:39 187 duration 216.916699
00:00:39 189 duration 237.333377
00:00:43 88 duration 238.916699
00:00:43 90 duration 259.708377
00:00:47 86 duration 260.875021
00:00:47 88 duration 282.541688
00:00:51 180 duration 283.874988
00:00:51 184 duration 306.041654
00:00:55 382 duration 307.874999
00:00:55 390 duration 330.041666
00:00:59 685 duration 331.916677
00:00:59 687 duration 354.624988
00:01:04 81 duration 355.874988
00:01:04 84 duration 379.833343
00:01:08 589 duration 380.875021
00:01:08 597 duration 405.541688
00:01:13 188 duration 406.916665
00:01:13 191 duration 431.916654
00:01:17 884 duration 432.874988
00:01:17 886 duration 458.791654
00:01:22 687 duration 459.874988
00:01:22 695 duration 486.083343
00:01:27 590 duration 487.875021
00:01:27 592 duration 514.12501
00:01:32 597 duration 515.874988
00:01:32 606 duration 542.874977
00:01:37 692 duration 543.833321
00:01:37 695 duration 572.041654
00:01:42 888 duration 573.874999
00:01:42 891 duration 601.833354
00:01:48 204 duration 602.916699
00:01:48 207 duration 632.083377
00:01:53 618 duration 634.000021
00:01:53 622 duration 663.041688
00:01:59 109 duration 664.833332
00:01:59 113 duration 694.416666
00:02:04 701 duration 695.874988
00:02:04 706 duration 726.499977
00:02:10 399 duration 727.833321
00:02:10 404 duration 759.083343
00:02:16 213 duration 760.958355
00:02:16 216 duration 792.208377
00:02:22 111 duration 793.833355
00:02:22 114 duration 826.083377
00:02:28 101 duration 827.958355
00:02:28 104 duration 860.333377
00:02:34 212 duration 861.833355
00:02:34 214 duration 895.166688
00:02:40 399 duration 896.833321
00:02:40 402 duration 930.708343
00:02:46 602 duration 931.833355
00:02:46 604 duration 966.083377
00:02:52 812 duration 967.875021
00:02:52 825 duration 1001.583377
00:02:59 08 duration 1002.833355
00:02:59 12 duration 1037.083377
00:03:05 197 duration 1038.916699
00:03:05 201 duration 1072.583377
00:03:11 402 duration 1073.833355
00:03:11 405 duration 1108.083377
00:03:17 626 duration 1109.958355
00:03:17 631 duration 1143.50001
00:03:23 808 duration 1144.83331
00:03:23 812 duration 1178.999977
00:03:30 15 duration 1180.833332
00:03:30 20 duration 1214.499988
00:03:36 217 duration 1215.833321
00:03:36 233 duration 1249.999977
00:03:42 401 duration 1250.874988
00:03:42 404 duration 1285.333343
00:03:48 607 duration 1286.833355
00:03:48 610 duration 1320.916688
00:03:54 801 duration 1321.874988
00:03:54 805 duration 1356.208343
00:04:01 00 duration 1357.833355
00:04:01 14 duration 1391.791688
00:04:07 195 duration 1392.833321
00:04:07 200 duration 1427.083343
00:06:19 701 debug FFmpegVideoDecoder: avcodec_decode_video2(): Invalid data found when processing input, at timestamp: 379833355 duration: 0 size: 1726 side_data_size: 0 is_key_frame: 0 encrypted: 0 discard_padding (ms): (0, 0)
00:06:19 701 error video decode error
00:06:19 735 pipeline_error PIPELINE_ERROR_DECODE
00:06:19 735 pipeline_state kStopping
00:06:19 735 pipeline_state kStopped
00:06:19 735 event PAUSE

Thank you very much in advance for your help.

amanea commented 6 years ago

I was able to upload .ts file somewhere were I can share it:

medium.js

forbesjo commented 5 years ago

Sorry for the slow response but are you still seeing this issue?