From 3f52d27652244365053f071e1df4759512582897 Mon Sep 17 00:00:00 2001 From: Mariusz Nowak Date: Wed, 7 Mar 2018 17:06:02 +0100 Subject: [PATCH] feat(promise): promise.timeout method --- promise_/timeout.js | 34 ++++++++++++++++++++++++ test/promise_/.eslintrc.json | 3 +++ test/promise_/timeout.js | 50 ++++++++++++++++++++++++++++++++++++ 3 files changed, 87 insertions(+) create mode 100644 promise_/timeout.js create mode 100644 test/promise_/.eslintrc.json create mode 100644 test/promise_/timeout.js diff --git a/promise_/timeout.js b/promise_/timeout.js new file mode 100644 index 0000000..6527178 --- /dev/null +++ b/promise_/timeout.js @@ -0,0 +1,34 @@ +"use strict"; + +var customError = require("es5-ext/error/custom") + , isValue = require("es5-ext/object/is-value") + , ensurePromise = require("es5-ext/object/ensure-promise") + , nextTick = require("next-tick") + , ensureTimeout = require("../valid-timeout"); + +module.exports = function (/* timeout */) { + ensurePromise(this); + var timeout = arguments[0]; + if (isValue(timeout)) timeout = ensureTimeout(timeout); + return new this.constructor( + function (resolve, reject) { + var isSettled = false; + this.then( + function (value) { + isSettled = true; + resolve(value); + }, + function (reason) { + isSettled = true; + reject(reason); + } + ); + var timeoutCallback = function () { + if (isSettled) return; + reject(customError("Operation timeout", "PROMISE_TIMEOUT")); + }; + if (isValue(timeout)) setTimeout(timeoutCallback, timeout); + else nextTick(timeoutCallback); + }.bind(this) + ); +}; diff --git a/test/promise_/.eslintrc.json b/test/promise_/.eslintrc.json new file mode 100644 index 0000000..95a6242 --- /dev/null +++ b/test/promise_/.eslintrc.json @@ -0,0 +1,3 @@ +{ + "globals": { "Promise": true } +} diff --git a/test/promise_/timeout.js b/test/promise_/timeout.js new file mode 100644 index 0000000..8947caa --- /dev/null +++ b/test/promise_/timeout.js @@ -0,0 +1,50 @@ +"use strict"; + +var delay = require("../../delay"); + +module.exports = function (t, a) { + if (typeof Promise !== "function") return null; + return { + Success: function (d) { + var promise = t.call( + new Promise(function (resolve) { + setTimeout(function () { + resolve("foo"); + }, 20); + }), + 40 + ); + + promise.then( + // Delay to escape error swallowing + delay(function (result) { + a(result, "foo"); + d(); + }), + delay(d) + ); + }, + Timeout: function (d) { + var promise = t.call( + new Promise(function (resolve) { + setTimeout(function () { + resolve("foo"); + }, 40); + }), + 20 + ); + + promise.then( + // Delay to escape error swallowing + delay(function () { + a.never(); + d(); + }), + delay(function (err) { + a(err.code, "PROMISE_TIMEOUT"); + d(); + }) + ); + } + }; +};