Bug 1208373 - Check that we don't get "ended" event for tracks after calling stop(). r?jib
MozReview-Commit-ID: K9gOZtUNQ5K
--- a/dom/media/tests/mochitest/head.js
+++ b/dom/media/tests/mochitest/head.js
@@ -585,16 +585,38 @@ function createOneShotEventWrapper(wrapp
obj[onx] = e => {
info(wrapper + ': "on' + event + '" event fired');
e.wrapper = wrapper;
wrapper[onx](e);
wrapper[onx] = unexpected;
};
}
+/**
+ * Returns a promise that resolves when `target` has raised an event with the
+ * given name. Cancel the returned promise by passing in a `cancelPromise` and
+ * resolve it.
+ *
+ * @param {object} target
+ * The target on which the event should occur.
+ * @param {string} name
+ * The name of the event that should occur.
+ * @param {promise} cancelPromise
+ * A promise that on resolving rejects the returned promise,
+ * so we can avoid logging results after a test has finished.
+ */
+function haveEvent(target, name, cancelPromise) {
+ var listener;
+ var p = Promise.race([
+ (cancelPromise || new Promise()).then(e => Promise.reject(e)),
+ new Promise(resolve => target.addEventListener(name, listener = resolve))
+ ]);
+ p.then(() => target.removeEventListener(name, listener));
+ return p;
+};
/**
* This class executes a series of functions in a continuous sequence.
* Promise-bearing functions are executed after the previous promise completes.
*
* @constructor
* @param {object} framework
* A back reference to the framework which makes use of the class. It is
--- a/dom/media/tests/mochitest/mediaStreamPlayback.js
+++ b/dom/media/tests/mochitest/mediaStreamPlayback.js
@@ -50,27 +50,37 @@ MediaStreamPlayback.prototype = {
var elem = this.mediaElement;
var waitForEnded = () => new Promise(resolve => {
elem.addEventListener('ended', function ended() {
elem.removeEventListener('ended', ended);
resolve();
});
});
- // TODO (bug 910249) Also check that all the tracks are local.
- this.mediaStream.getTracks().forEach(t => t.stop());
+ var noTrackEnded = Promise.all(this.mediaStream.getTracks().map(t => {
+ let onNextLoop = wait(0);
+ let p = Promise.race([
+ onNextLoop,
+ haveEvent(t, "ended", onNextLoop)
+ .then(() => Promise.reject("Unexpected ended event for track " + t.id),
+ () => Promise.resolve())
+ ]);
+ t.stop();
+ return p;
+ }));
// XXX (bug 1208316) When we implement MediaStream.active, do not stop
// the stream. We just do it now so the media element will raise 'ended'.
if (!this.mediaStream.stop) {
return;
}
this.mediaStream.stop();
return timeout(waitForEnded(), ENDED_TIMEOUT_LENGTH, "ended event never fired")
- .then(() => ok(true, "ended event successfully fired"));
+ .then(() => ok(true, "ended event successfully fired"))
+ .then(() => noTrackEnded);
},
/**
* Starts media with a media stream, runs it until a canplaythrough and
* timeupdate event fires, and stops the media.
*
* @param {Boolean} isResume specifies if this media element is being resumed
* from a previous run