├── .gitignore
├── .npmignore
├── README.md
├── build.js
├── dist
├── promise.common.js
├── promise.esm.js
└── promise.min.js
├── index.html
├── index.js
├── package.json
├── src
├── async_callback.js
├── core.js
├── es6_extensions.js
└── index.js
├── test.js
├── test.png
└── webpack.config.js
/.gitignore:
--------------------------------------------------------------------------------
1 | # vim
2 | *~
3 | *.sw?
4 |
5 | # misc editing tools
6 | .vscode/
7 | tags
8 |
9 | #mac
10 | *.DS_Store
11 |
12 | # build tools
13 | node_modules/
14 |
15 | # logfiles
16 | *.log
17 | .idea/
18 |
19 | #npm
20 | yarn.lock
21 | package-lock.json
--------------------------------------------------------------------------------
/.npmignore:
--------------------------------------------------------------------------------
1 | # vim
2 | *~
3 | *.sw?
4 |
5 | # generic editing tools
6 | tags
7 | tags.lock
8 |
9 | # mac
10 | *.DS_Store
11 |
12 | # wandows
13 | .vscode/
14 |
15 | # build tools
16 | node_modules/
17 |
18 | # logfiles
19 | *.log
20 | .idea/
21 |
22 | # dev artifacts
23 | yarn.lock
24 | package-lock.json
25 |
26 | # misc
27 | README.md
28 |
29 | # source maps
30 | *.js.map
31 |
32 | # source files
33 | lib/
34 |
35 | # test projects
36 | test.js
37 | test.png
38 |
39 | # self
40 | .npmignore
41 | .gitignore
42 |
43 | #example
44 | example/
45 |
46 | #docs
47 | docs/
48 |
49 | #src
50 | src/
51 |
52 | # other configs
53 | webpack.config.js
54 | index.js
55 | index.html
56 | webpack.config.js
57 | build.js
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | ## Promise/es6
2 | [![NPM version][npm-image]][npm-url]
3 |
4 | This `Promise` case is implemented in `es6`, and it is compatible with the native `async/await` function through the official unit test of the promise. This case is for study only, if it is used in a production environment, you can use the files in the `dist` directory.
5 |
6 | ### test
7 | You can use `npm i` or `yarn` install dependencies, then use `npm run test` or `yarn test` to test.
8 |
9 | 
10 |
11 | [npm-url]: https://www.npmjs.com/package/es2015-promise
12 | [npm-image]: https://img.shields.io/npm/v/es2015-promise.svg
13 |
--------------------------------------------------------------------------------
/build.js:
--------------------------------------------------------------------------------
1 | const rollup = require('rollup')
2 | const babel = require('rollup-plugin-babel')
3 | const cleanup = require('rollup-plugin-cleanup')
4 |
5 | const esm = {
6 | input: 'src/index.js',
7 | output: {
8 | file: 'dist/promise.esm.js',
9 | format: 'es',
10 | }
11 | }
12 |
13 | const umd = {
14 | input: 'src/index.js',
15 | output: {
16 | file: 'dist/promise.min.js',
17 | format: 'umd',
18 | name: 'Promise',
19 | }
20 | }
21 |
22 | const cjs = {
23 | input: 'src/index.js',
24 | output: {
25 | file: 'dist/promise.common.js',
26 | format: 'cjs',
27 | }
28 | }
29 |
30 | async function build (cfg) {
31 | const bundle = await rollup.rollup({
32 | input: cfg.input,
33 | plugins: [
34 | cleanup(),
35 | babel({
36 | exclude: 'node_modules/**',
37 | presets: ['es2015-rollup'],
38 | }),
39 | ]
40 | })
41 | await bundle.generate(cfg.output)
42 | await bundle.write(cfg.output)
43 | }
44 |
45 | build(esm)
46 | build(cjs)
47 | build(umd)
48 |
49 |
--------------------------------------------------------------------------------
/dist/promise.common.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | var capacity = 1024;
4 | var queue = [];
5 | var index = 0;
6 | var flushing = false;
7 | var requestFlush = void 0;
8 | var BrowserMutationObserver = void 0;
9 | var isNode = typeof module !== 'undefined' && module.exports;
10 | function createMutationObserverCallback(callback) {
11 | var toggle = 1;
12 | var observer = new BrowserMutationObserver(callback);
13 | var node = document.createTextNode('');
14 | observer.observe(node, { characterData: true });
15 | return function () {
16 | toggle = -toggle;
17 | node.data = toggle;
18 | };
19 | }
20 | function createTimerCallback(callback) {
21 | return function () {
22 | var t = setTimeout(handleTimer);
23 | var i = setInterval(handleTimer, 50);
24 | function handleTimer() {
25 | clearTimeout(t);
26 | clearInterval(i);
27 | t = null;
28 | i = null;
29 | callback();
30 | }
31 | };
32 | }
33 | function setImmediateOrNexttick(callback) {
34 | return function () {
35 | if (flushing && typeof setImmediate === 'function') {
36 | setImmediate(callback);
37 | } else {
38 | process.nextTick(callback);
39 | }
40 | };
41 | }
42 | if (isNode) {
43 | requestFlush = setImmediateOrNexttick(_requestFlush);
44 | } else {
45 | var scope = typeof global !== 'undefined' ? global : self;
46 | BrowserMutationObserver = scope.MutationObserver || scope.WebKitMutationObserver;
47 | requestFlush = typeof BrowserMutationObserver === 'function' ? createMutationObserverCallback(_requestFlush) : createTimerCallback(_requestFlush);
48 | }
49 | function _requestFlush() {
50 | while (index < queue.length) {
51 | var currentIndex = index;
52 | index++;
53 | queue[currentIndex].call();
54 | if (index > capacity) {
55 | var newLength = queque.length - index;
56 | for (var i = 0; i < newLength; i++) {
57 | queue[i] = queue[index + i];
58 | }
59 | queue.length -= index;
60 | index = 0;
61 | }
62 | }
63 | queue.length = 0;
64 | index = 0;
65 | flushing = false;
66 | }
67 | function ascb(task) {
68 | if (!queue.length) {
69 | requestFlush();
70 | flushing = true;
71 | }
72 | queue[queue.length] = task;
73 | }
74 |
75 | var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) {
76 | return typeof obj;
77 | } : function (obj) {
78 | return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
79 | };
80 |
81 | var classCallCheck = function (instance, Constructor) {
82 | if (!(instance instanceof Constructor)) {
83 | throw new TypeError("Cannot call a class as a function");
84 | }
85 | };
86 |
87 | var createClass = function () {
88 | function defineProperties(target, props) {
89 | for (var i = 0; i < props.length; i++) {
90 | var descriptor = props[i];
91 | descriptor.enumerable = descriptor.enumerable || false;
92 | descriptor.configurable = true;
93 | if ("value" in descriptor) descriptor.writable = true;
94 | Object.defineProperty(target, descriptor.key, descriptor);
95 | }
96 | }
97 |
98 | return function (Constructor, protoProps, staticProps) {
99 | if (protoProps) defineProperties(Constructor.prototype, protoProps);
100 | if (staticProps) defineProperties(Constructor, staticProps);
101 | return Constructor;
102 | };
103 | }();
104 |
105 | var slicedToArray = function () {
106 | function sliceIterator(arr, i) {
107 | var _arr = [];
108 | var _n = true;
109 | var _d = false;
110 | var _e = undefined;
111 |
112 | try {
113 | for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
114 | _arr.push(_s.value);
115 |
116 | if (i && _arr.length === i) break;
117 | }
118 | } catch (err) {
119 | _d = true;
120 | _e = err;
121 | } finally {
122 | try {
123 | if (!_n && _i["return"]) _i["return"]();
124 | } finally {
125 | if (_d) throw _e;
126 | }
127 | }
128 |
129 | return _arr;
130 | }
131 |
132 | return function (arr, i) {
133 | if (Array.isArray(arr)) {
134 | return arr;
135 | } else if (Symbol.iterator in Object(arr)) {
136 | return sliceIterator(arr, i);
137 | } else {
138 | throw new TypeError("Invalid attempt to destructure non-iterable instance");
139 | }
140 | };
141 | }();
142 |
143 | var noop = function noop() {};
144 |
145 | var Promise$1 = function () {
146 | function Promise(fun) {
147 | classCallCheck(this, Promise);
148 |
149 | if (!(this instanceof Promise)) {
150 | throw TypeError('Calling a Promise constructor without new is forbidden');
151 | }
152 | if (typeof fun !== 'function') {
153 | throw TypeError("Promise constructor's argument must be a function");
154 | }
155 | this._state = 0;
156 | this._value = null;
157 | this._deferreds = null;
158 | if (fun === noop) return;
159 | doResolve(fun, this);
160 | }
161 |
162 | createClass(Promise, [{
163 | key: 'then',
164 | value: function then(onFulfilled, onRejected) {
165 | var p = new Promise(noop);
166 | handle(this, new Handler(p, onFulfilled, onRejected));
167 | return p;
168 | }
169 | }, {
170 | key: 'catch',
171 | value: function _catch(onRejected) {
172 | return this.then(null, onRejected);
173 | }
174 | }, {
175 | key: 'finally',
176 | value: function _finally(fun) {
177 | return this.then(function (value) {
178 | return Promise.resolve(fun()).then(function () {
179 | return value;
180 | });
181 | }, function (reason) {
182 | return Promise.resolve(fun()).then(function () {
183 | throw reason;
184 | });
185 | });
186 | }
187 | }, {
188 | key: 'getValue',
189 | value: function getValue() {
190 | if (this._state === 3) {
191 | return this._value.getValue();
192 | }
193 | return this._value;
194 | }
195 | }, {
196 | key: 'toString',
197 | value: function toString() {
198 | return '[object Promise]';
199 | }
200 | }]);
201 | return Promise;
202 | }();
203 |
204 | Promise$1._noop = noop;
205 | function doResolve(fun, promise) {
206 | var done = false;
207 | function _resolve(value) {
208 | if (done) return;
209 | done = true;
210 | resolve(promise, value);
211 | }
212 | function _reject(reason) {
213 | if (done) return;
214 | done = true;
215 | reject(promise, reason);
216 | }
217 | try {
218 | fun(_resolve, _reject);
219 | } catch (error) {
220 | _reject(error);
221 | }
222 | }
223 | function resolve(promise, newValue) {
224 | if (promise === newValue) {
225 | reject(promise, new TypeError('A promise cannot be resolved with itself'));
226 | return;
227 | }
228 | if (newValue && ((typeof newValue === 'undefined' ? 'undefined' : _typeof(newValue)) === 'object' || typeof newValue === 'function')) {
229 | var _getThen = getThen(newValue),
230 | _getThen2 = slicedToArray(_getThen, 2),
231 | isError = _getThen2[0],
232 | then = _getThen2[1];
233 |
234 | if (isError) {
235 | reject(promise, then);
236 | return;
237 | }
238 | if (then === promise.then && newValue instanceof Promise$1) {
239 | promise._state = 3;
240 | promise._value = newValue;
241 | finale(promise);
242 | return;
243 | } else if (typeof then === 'function') {
244 | doResolve(then.bind(newValue), promise);
245 | return;
246 | }
247 | }
248 | promise._state = 1;
249 | promise._value = newValue;
250 | finale(promise);
251 | }
252 | function reject(promise, reason) {
253 | promise._state = 2;
254 | promise._value = reason;
255 | finale(promise);
256 | }
257 | function finale(promise) {
258 | if (promise._deferreds) {
259 | if (promise._deferreds.length === 1) {
260 | handle(promise, promise._deferreds[0]);
261 | promise._deferreds = null;
262 | return;
263 | }
264 | var _iteratorNormalCompletion = true;
265 | var _didIteratorError = false;
266 | var _iteratorError = undefined;
267 |
268 | try {
269 | for (var _iterator = promise._deferreds[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
270 | var deferred = _step.value;
271 |
272 | handle(promise, deferred);
273 | }
274 | } catch (err) {
275 | _didIteratorError = true;
276 | _iteratorError = err;
277 | } finally {
278 | try {
279 | if (!_iteratorNormalCompletion && _iterator.return) {
280 | _iterator.return();
281 | }
282 | } finally {
283 | if (_didIteratorError) {
284 | throw _iteratorError;
285 | }
286 | }
287 | }
288 |
289 | promise._deferreds = null;
290 | }
291 | }
292 | function handle(promise, deferred) {
293 | while (promise._state === 3) {
294 | promise = promise._value;
295 | }
296 | if (promise._state === 0) {
297 | promise._deferreds ? promise._deferreds.push(deferred) : promise._deferreds = [deferred];
298 | return;
299 | }
300 | handleResolved(promise, deferred);
301 | }
302 | function handleResolved(promise, deferred) {
303 | ascb(function () {
304 | var isResolve = promise._state === 1;
305 | var callback = deferred[isResolve ? 'onFulfilled' : 'onRejected'];
306 | if (callback === null) {
307 | isResolve ? resolve(deferred.promise, promise._value) : reject(deferred.promise, promise._value);
308 | return;
309 | }
310 | try {
311 | var result = callback(promise._value);
312 | resolve(deferred.promise, result);
313 | } catch (error) {
314 | reject(deferred.promise, error);
315 | }
316 | });
317 | }
318 | function getThen(value) {
319 | try {
320 | return [false, value.then];
321 | } catch (error) {
322 | return [true, error];
323 | }
324 | }
325 | function Handler(promise, onFulfilled, onRejected) {
326 | this.promise = promise;
327 | this.onFulfilled = typeof onFulfilled === 'function' ? onFulfilled : null;
328 | this.onRejected = typeof onRejected === 'function' ? onRejected : null;
329 | }
330 |
331 | Promise$1.resolve = function (value) {
332 | if (value instanceof Promise$1) return value;
333 | function valueToPromise(val) {
334 | var p = new Promise$1(Promise$1._noop);
335 | p._state = 1;
336 | p._value = value;
337 | return p;
338 | }
339 | if ((typeof value === 'undefined' ? 'undefined' : _typeof(value)) === 'object' || typeof value === 'function') {
340 | try {
341 | var then = value.then;
342 | if (typeof then === 'function') {
343 | return new Promise$1(then.bind(value));
344 | }
345 | } catch (error) {
346 | return new Promise$1(function (_, reject) {
347 | reject(error);
348 | });
349 | }
350 | }
351 | return valueToPromise(value);
352 | };
353 | Promise$1.reject = function (reason) {
354 | return new Promise$1(function (_, reject) {
355 | reject(reason);
356 | });
357 | };
358 | Promise$1.all = function (array) {
359 | !Array.isArray(array) && (array = Array.from(array));
360 | return new Promise$1(function (resolve, reject) {
361 | if (array.length === 0) return resolve(array);
362 | var remaining = array.length;
363 | for (var i = 0; i < array.length; i++) {
364 | result(array[i], i);
365 | }
366 | function result(val, i) {
367 | if (!val || (typeof val === 'undefined' ? 'undefined' : _typeof(val)) !== 'object' && typeof val !== 'function') {
368 | array[i] = val;
369 | --remaining === 0 && resolve(array);
370 | return;
371 | }
372 | if (val instanceof Promise$1 && val.then === Promise$1.prototype.then) {
373 | while (val._state === 3) {
374 | val = val._value;
375 | }
376 | if (val._state === 1) return result(val._value, i);
377 | if (val._state === 2) reject(val._value);
378 | val.then(function (res) {
379 | return result(res, i);
380 | }, reject);
381 | return;
382 | }
383 | if (typeof val.then === 'function') {
384 | var p = new Promise$1(val.then.bind(val));
385 | p.then(function (res) {
386 | return result(res, i);
387 | }, reject);
388 | return;
389 | }
390 | }
391 | });
392 | };
393 | Promise$1.race = function (array) {
394 | return new Promise$1(function (resolve, reject) {
395 | var _iteratorNormalCompletion = true;
396 | var _didIteratorError = false;
397 | var _iteratorError = undefined;
398 |
399 | try {
400 | for (var _iterator = array[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
401 | var val = _step.value;
402 |
403 | Promise$1.resolve(val).then(resolve, reject);
404 | }
405 | } catch (err) {
406 | _didIteratorError = true;
407 | _iteratorError = err;
408 | } finally {
409 | try {
410 | if (!_iteratorNormalCompletion && _iterator.return) {
411 | _iterator.return();
412 | }
413 | } finally {
414 | if (_didIteratorError) {
415 | throw _iteratorError;
416 | }
417 | }
418 | }
419 | });
420 | };
421 |
422 | module.exports = Promise$1;
423 |
--------------------------------------------------------------------------------
/dist/promise.esm.js:
--------------------------------------------------------------------------------
1 | var capacity = 1024;
2 | var queue = [];
3 | var index = 0;
4 | var flushing = false;
5 | var requestFlush = void 0;
6 | var BrowserMutationObserver = void 0;
7 | var isNode = typeof module !== 'undefined' && module.exports;
8 | function createMutationObserverCallback(callback) {
9 | var toggle = 1;
10 | var observer = new BrowserMutationObserver(callback);
11 | var node = document.createTextNode('');
12 | observer.observe(node, { characterData: true });
13 | return function () {
14 | toggle = -toggle;
15 | node.data = toggle;
16 | };
17 | }
18 | function createTimerCallback(callback) {
19 | return function () {
20 | var t = setTimeout(handleTimer);
21 | var i = setInterval(handleTimer, 50);
22 | function handleTimer() {
23 | clearTimeout(t);
24 | clearInterval(i);
25 | t = null;
26 | i = null;
27 | callback();
28 | }
29 | };
30 | }
31 | function setImmediateOrNexttick(callback) {
32 | return function () {
33 | if (flushing && typeof setImmediate === 'function') {
34 | setImmediate(callback);
35 | } else {
36 | process.nextTick(callback);
37 | }
38 | };
39 | }
40 | if (isNode) {
41 | requestFlush = setImmediateOrNexttick(_requestFlush);
42 | } else {
43 | var scope = typeof global !== 'undefined' ? global : self;
44 | BrowserMutationObserver = scope.MutationObserver || scope.WebKitMutationObserver;
45 | requestFlush = typeof BrowserMutationObserver === 'function' ? createMutationObserverCallback(_requestFlush) : createTimerCallback(_requestFlush);
46 | }
47 | function _requestFlush() {
48 | while (index < queue.length) {
49 | var currentIndex = index;
50 | index++;
51 | queue[currentIndex].call();
52 | if (index > capacity) {
53 | var newLength = queque.length - index;
54 | for (var i = 0; i < newLength; i++) {
55 | queue[i] = queue[index + i];
56 | }
57 | queue.length -= index;
58 | index = 0;
59 | }
60 | }
61 | queue.length = 0;
62 | index = 0;
63 | flushing = false;
64 | }
65 | function ascb(task) {
66 | if (!queue.length) {
67 | requestFlush();
68 | flushing = true;
69 | }
70 | queue[queue.length] = task;
71 | }
72 |
73 | var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) {
74 | return typeof obj;
75 | } : function (obj) {
76 | return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
77 | };
78 |
79 | var classCallCheck = function (instance, Constructor) {
80 | if (!(instance instanceof Constructor)) {
81 | throw new TypeError("Cannot call a class as a function");
82 | }
83 | };
84 |
85 | var createClass = function () {
86 | function defineProperties(target, props) {
87 | for (var i = 0; i < props.length; i++) {
88 | var descriptor = props[i];
89 | descriptor.enumerable = descriptor.enumerable || false;
90 | descriptor.configurable = true;
91 | if ("value" in descriptor) descriptor.writable = true;
92 | Object.defineProperty(target, descriptor.key, descriptor);
93 | }
94 | }
95 |
96 | return function (Constructor, protoProps, staticProps) {
97 | if (protoProps) defineProperties(Constructor.prototype, protoProps);
98 | if (staticProps) defineProperties(Constructor, staticProps);
99 | return Constructor;
100 | };
101 | }();
102 |
103 | var slicedToArray = function () {
104 | function sliceIterator(arr, i) {
105 | var _arr = [];
106 | var _n = true;
107 | var _d = false;
108 | var _e = undefined;
109 |
110 | try {
111 | for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
112 | _arr.push(_s.value);
113 |
114 | if (i && _arr.length === i) break;
115 | }
116 | } catch (err) {
117 | _d = true;
118 | _e = err;
119 | } finally {
120 | try {
121 | if (!_n && _i["return"]) _i["return"]();
122 | } finally {
123 | if (_d) throw _e;
124 | }
125 | }
126 |
127 | return _arr;
128 | }
129 |
130 | return function (arr, i) {
131 | if (Array.isArray(arr)) {
132 | return arr;
133 | } else if (Symbol.iterator in Object(arr)) {
134 | return sliceIterator(arr, i);
135 | } else {
136 | throw new TypeError("Invalid attempt to destructure non-iterable instance");
137 | }
138 | };
139 | }();
140 |
141 | var noop = function noop() {};
142 |
143 | var Promise$1 = function () {
144 | function Promise(fun) {
145 | classCallCheck(this, Promise);
146 |
147 | if (!(this instanceof Promise)) {
148 | throw TypeError('Calling a Promise constructor without new is forbidden');
149 | }
150 | if (typeof fun !== 'function') {
151 | throw TypeError("Promise constructor's argument must be a function");
152 | }
153 | this._state = 0;
154 | this._value = null;
155 | this._deferreds = null;
156 | if (fun === noop) return;
157 | doResolve(fun, this);
158 | }
159 |
160 | createClass(Promise, [{
161 | key: 'then',
162 | value: function then(onFulfilled, onRejected) {
163 | var p = new Promise(noop);
164 | handle(this, new Handler(p, onFulfilled, onRejected));
165 | return p;
166 | }
167 | }, {
168 | key: 'catch',
169 | value: function _catch(onRejected) {
170 | return this.then(null, onRejected);
171 | }
172 | }, {
173 | key: 'finally',
174 | value: function _finally(fun) {
175 | return this.then(function (value) {
176 | return Promise.resolve(fun()).then(function () {
177 | return value;
178 | });
179 | }, function (reason) {
180 | return Promise.resolve(fun()).then(function () {
181 | throw reason;
182 | });
183 | });
184 | }
185 | }, {
186 | key: 'getValue',
187 | value: function getValue() {
188 | if (this._state === 3) {
189 | return this._value.getValue();
190 | }
191 | return this._value;
192 | }
193 | }, {
194 | key: 'toString',
195 | value: function toString() {
196 | return '[object Promise]';
197 | }
198 | }]);
199 | return Promise;
200 | }();
201 |
202 | Promise$1._noop = noop;
203 | function doResolve(fun, promise) {
204 | var done = false;
205 | function _resolve(value) {
206 | if (done) return;
207 | done = true;
208 | resolve(promise, value);
209 | }
210 | function _reject(reason) {
211 | if (done) return;
212 | done = true;
213 | reject(promise, reason);
214 | }
215 | try {
216 | fun(_resolve, _reject);
217 | } catch (error) {
218 | _reject(error);
219 | }
220 | }
221 | function resolve(promise, newValue) {
222 | if (promise === newValue) {
223 | reject(promise, new TypeError('A promise cannot be resolved with itself'));
224 | return;
225 | }
226 | if (newValue && ((typeof newValue === 'undefined' ? 'undefined' : _typeof(newValue)) === 'object' || typeof newValue === 'function')) {
227 | var _getThen = getThen(newValue),
228 | _getThen2 = slicedToArray(_getThen, 2),
229 | isError = _getThen2[0],
230 | then = _getThen2[1];
231 |
232 | if (isError) {
233 | reject(promise, then);
234 | return;
235 | }
236 | if (then === promise.then && newValue instanceof Promise$1) {
237 | promise._state = 3;
238 | promise._value = newValue;
239 | finale(promise);
240 | return;
241 | } else if (typeof then === 'function') {
242 | doResolve(then.bind(newValue), promise);
243 | return;
244 | }
245 | }
246 | promise._state = 1;
247 | promise._value = newValue;
248 | finale(promise);
249 | }
250 | function reject(promise, reason) {
251 | promise._state = 2;
252 | promise._value = reason;
253 | finale(promise);
254 | }
255 | function finale(promise) {
256 | if (promise._deferreds) {
257 | if (promise._deferreds.length === 1) {
258 | handle(promise, promise._deferreds[0]);
259 | promise._deferreds = null;
260 | return;
261 | }
262 | var _iteratorNormalCompletion = true;
263 | var _didIteratorError = false;
264 | var _iteratorError = undefined;
265 |
266 | try {
267 | for (var _iterator = promise._deferreds[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
268 | var deferred = _step.value;
269 |
270 | handle(promise, deferred);
271 | }
272 | } catch (err) {
273 | _didIteratorError = true;
274 | _iteratorError = err;
275 | } finally {
276 | try {
277 | if (!_iteratorNormalCompletion && _iterator.return) {
278 | _iterator.return();
279 | }
280 | } finally {
281 | if (_didIteratorError) {
282 | throw _iteratorError;
283 | }
284 | }
285 | }
286 |
287 | promise._deferreds = null;
288 | }
289 | }
290 | function handle(promise, deferred) {
291 | while (promise._state === 3) {
292 | promise = promise._value;
293 | }
294 | if (promise._state === 0) {
295 | promise._deferreds ? promise._deferreds.push(deferred) : promise._deferreds = [deferred];
296 | return;
297 | }
298 | handleResolved(promise, deferred);
299 | }
300 | function handleResolved(promise, deferred) {
301 | ascb(function () {
302 | var isResolve = promise._state === 1;
303 | var callback = deferred[isResolve ? 'onFulfilled' : 'onRejected'];
304 | if (callback === null) {
305 | isResolve ? resolve(deferred.promise, promise._value) : reject(deferred.promise, promise._value);
306 | return;
307 | }
308 | try {
309 | var result = callback(promise._value);
310 | resolve(deferred.promise, result);
311 | } catch (error) {
312 | reject(deferred.promise, error);
313 | }
314 | });
315 | }
316 | function getThen(value) {
317 | try {
318 | return [false, value.then];
319 | } catch (error) {
320 | return [true, error];
321 | }
322 | }
323 | function Handler(promise, onFulfilled, onRejected) {
324 | this.promise = promise;
325 | this.onFulfilled = typeof onFulfilled === 'function' ? onFulfilled : null;
326 | this.onRejected = typeof onRejected === 'function' ? onRejected : null;
327 | }
328 |
329 | Promise$1.resolve = function (value) {
330 | if (value instanceof Promise$1) return value;
331 | function valueToPromise(val) {
332 | var p = new Promise$1(Promise$1._noop);
333 | p._state = 1;
334 | p._value = value;
335 | return p;
336 | }
337 | if ((typeof value === 'undefined' ? 'undefined' : _typeof(value)) === 'object' || typeof value === 'function') {
338 | try {
339 | var then = value.then;
340 | if (typeof then === 'function') {
341 | return new Promise$1(then.bind(value));
342 | }
343 | } catch (error) {
344 | return new Promise$1(function (_, reject) {
345 | reject(error);
346 | });
347 | }
348 | }
349 | return valueToPromise(value);
350 | };
351 | Promise$1.reject = function (reason) {
352 | return new Promise$1(function (_, reject) {
353 | reject(reason);
354 | });
355 | };
356 | Promise$1.all = function (array) {
357 | !Array.isArray(array) && (array = Array.from(array));
358 | return new Promise$1(function (resolve, reject) {
359 | if (array.length === 0) return resolve(array);
360 | var remaining = array.length;
361 | for (var i = 0; i < array.length; i++) {
362 | result(array[i], i);
363 | }
364 | function result(val, i) {
365 | if (!val || (typeof val === 'undefined' ? 'undefined' : _typeof(val)) !== 'object' && typeof val !== 'function') {
366 | array[i] = val;
367 | --remaining === 0 && resolve(array);
368 | return;
369 | }
370 | if (val instanceof Promise$1 && val.then === Promise$1.prototype.then) {
371 | while (val._state === 3) {
372 | val = val._value;
373 | }
374 | if (val._state === 1) return result(val._value, i);
375 | if (val._state === 2) reject(val._value);
376 | val.then(function (res) {
377 | return result(res, i);
378 | }, reject);
379 | return;
380 | }
381 | if (typeof val.then === 'function') {
382 | var p = new Promise$1(val.then.bind(val));
383 | p.then(function (res) {
384 | return result(res, i);
385 | }, reject);
386 | return;
387 | }
388 | }
389 | });
390 | };
391 | Promise$1.race = function (array) {
392 | return new Promise$1(function (resolve, reject) {
393 | var _iteratorNormalCompletion = true;
394 | var _didIteratorError = false;
395 | var _iteratorError = undefined;
396 |
397 | try {
398 | for (var _iterator = array[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
399 | var val = _step.value;
400 |
401 | Promise$1.resolve(val).then(resolve, reject);
402 | }
403 | } catch (err) {
404 | _didIteratorError = true;
405 | _iteratorError = err;
406 | } finally {
407 | try {
408 | if (!_iteratorNormalCompletion && _iterator.return) {
409 | _iterator.return();
410 | }
411 | } finally {
412 | if (_didIteratorError) {
413 | throw _iteratorError;
414 | }
415 | }
416 | }
417 | });
418 | };
419 |
420 | export default Promise$1;
421 |
--------------------------------------------------------------------------------
/dist/promise.min.js:
--------------------------------------------------------------------------------
1 | (function (global, factory) {
2 | typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
3 | typeof define === 'function' && define.amd ? define(factory) :
4 | (global.Promise = factory());
5 | }(this, (function () { 'use strict';
6 |
7 | var capacity = 1024;
8 | var queue = [];
9 | var index = 0;
10 | var flushing = false;
11 | var requestFlush = void 0;
12 | var BrowserMutationObserver = void 0;
13 | var isNode = typeof module !== 'undefined' && module.exports;
14 | function createMutationObserverCallback(callback) {
15 | var toggle = 1;
16 | var observer = new BrowserMutationObserver(callback);
17 | var node = document.createTextNode('');
18 | observer.observe(node, { characterData: true });
19 | return function () {
20 | toggle = -toggle;
21 | node.data = toggle;
22 | };
23 | }
24 | function createTimerCallback(callback) {
25 | return function () {
26 | var t = setTimeout(handleTimer);
27 | var i = setInterval(handleTimer, 50);
28 | function handleTimer() {
29 | clearTimeout(t);
30 | clearInterval(i);
31 | t = null;
32 | i = null;
33 | callback();
34 | }
35 | };
36 | }
37 | function setImmediateOrNexttick(callback) {
38 | return function () {
39 | if (flushing && typeof setImmediate === 'function') {
40 | setImmediate(callback);
41 | } else {
42 | process.nextTick(callback);
43 | }
44 | };
45 | }
46 | if (isNode) {
47 | requestFlush = setImmediateOrNexttick(_requestFlush);
48 | } else {
49 | var scope = typeof global !== 'undefined' ? global : self;
50 | BrowserMutationObserver = scope.MutationObserver || scope.WebKitMutationObserver;
51 | requestFlush = typeof BrowserMutationObserver === 'function' ? createMutationObserverCallback(_requestFlush) : createTimerCallback(_requestFlush);
52 | }
53 | function _requestFlush() {
54 | while (index < queue.length) {
55 | var currentIndex = index;
56 | index++;
57 | queue[currentIndex].call();
58 | if (index > capacity) {
59 | var newLength = queque.length - index;
60 | for (var i = 0; i < newLength; i++) {
61 | queue[i] = queue[index + i];
62 | }
63 | queue.length -= index;
64 | index = 0;
65 | }
66 | }
67 | queue.length = 0;
68 | index = 0;
69 | flushing = false;
70 | }
71 | function ascb(task) {
72 | if (!queue.length) {
73 | requestFlush();
74 | flushing = true;
75 | }
76 | queue[queue.length] = task;
77 | }
78 |
79 | var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) {
80 | return typeof obj;
81 | } : function (obj) {
82 | return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
83 | };
84 |
85 | var classCallCheck = function (instance, Constructor) {
86 | if (!(instance instanceof Constructor)) {
87 | throw new TypeError("Cannot call a class as a function");
88 | }
89 | };
90 |
91 | var createClass = function () {
92 | function defineProperties(target, props) {
93 | for (var i = 0; i < props.length; i++) {
94 | var descriptor = props[i];
95 | descriptor.enumerable = descriptor.enumerable || false;
96 | descriptor.configurable = true;
97 | if ("value" in descriptor) descriptor.writable = true;
98 | Object.defineProperty(target, descriptor.key, descriptor);
99 | }
100 | }
101 |
102 | return function (Constructor, protoProps, staticProps) {
103 | if (protoProps) defineProperties(Constructor.prototype, protoProps);
104 | if (staticProps) defineProperties(Constructor, staticProps);
105 | return Constructor;
106 | };
107 | }();
108 |
109 | var slicedToArray = function () {
110 | function sliceIterator(arr, i) {
111 | var _arr = [];
112 | var _n = true;
113 | var _d = false;
114 | var _e = undefined;
115 |
116 | try {
117 | for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
118 | _arr.push(_s.value);
119 |
120 | if (i && _arr.length === i) break;
121 | }
122 | } catch (err) {
123 | _d = true;
124 | _e = err;
125 | } finally {
126 | try {
127 | if (!_n && _i["return"]) _i["return"]();
128 | } finally {
129 | if (_d) throw _e;
130 | }
131 | }
132 |
133 | return _arr;
134 | }
135 |
136 | return function (arr, i) {
137 | if (Array.isArray(arr)) {
138 | return arr;
139 | } else if (Symbol.iterator in Object(arr)) {
140 | return sliceIterator(arr, i);
141 | } else {
142 | throw new TypeError("Invalid attempt to destructure non-iterable instance");
143 | }
144 | };
145 | }();
146 |
147 | var noop = function noop() {};
148 |
149 | var Promise$1 = function () {
150 | function Promise(fun) {
151 | classCallCheck(this, Promise);
152 |
153 | if (!(this instanceof Promise)) {
154 | throw TypeError('Calling a Promise constructor without new is forbidden');
155 | }
156 | if (typeof fun !== 'function') {
157 | throw TypeError("Promise constructor's argument must be a function");
158 | }
159 | this._state = 0;
160 | this._value = null;
161 | this._deferreds = null;
162 | if (fun === noop) return;
163 | doResolve(fun, this);
164 | }
165 |
166 | createClass(Promise, [{
167 | key: 'then',
168 | value: function then(onFulfilled, onRejected) {
169 | var p = new Promise(noop);
170 | handle(this, new Handler(p, onFulfilled, onRejected));
171 | return p;
172 | }
173 | }, {
174 | key: 'catch',
175 | value: function _catch(onRejected) {
176 | return this.then(null, onRejected);
177 | }
178 | }, {
179 | key: 'finally',
180 | value: function _finally(fun) {
181 | return this.then(function (value) {
182 | return Promise.resolve(fun()).then(function () {
183 | return value;
184 | });
185 | }, function (reason) {
186 | return Promise.resolve(fun()).then(function () {
187 | throw reason;
188 | });
189 | });
190 | }
191 | }, {
192 | key: 'getValue',
193 | value: function getValue() {
194 | if (this._state === 3) {
195 | return this._value.getValue();
196 | }
197 | return this._value;
198 | }
199 | }, {
200 | key: 'toString',
201 | value: function toString() {
202 | return '[object Promise]';
203 | }
204 | }]);
205 | return Promise;
206 | }();
207 |
208 | Promise$1._noop = noop;
209 | function doResolve(fun, promise) {
210 | var done = false;
211 | function _resolve(value) {
212 | if (done) return;
213 | done = true;
214 | resolve(promise, value);
215 | }
216 | function _reject(reason) {
217 | if (done) return;
218 | done = true;
219 | reject(promise, reason);
220 | }
221 | try {
222 | fun(_resolve, _reject);
223 | } catch (error) {
224 | _reject(error);
225 | }
226 | }
227 | function resolve(promise, newValue) {
228 | if (promise === newValue) {
229 | reject(promise, new TypeError('A promise cannot be resolved with itself'));
230 | return;
231 | }
232 | if (newValue && ((typeof newValue === 'undefined' ? 'undefined' : _typeof(newValue)) === 'object' || typeof newValue === 'function')) {
233 | var _getThen = getThen(newValue),
234 | _getThen2 = slicedToArray(_getThen, 2),
235 | isError = _getThen2[0],
236 | then = _getThen2[1];
237 |
238 | if (isError) {
239 | reject(promise, then);
240 | return;
241 | }
242 | if (then === promise.then && newValue instanceof Promise$1) {
243 | promise._state = 3;
244 | promise._value = newValue;
245 | finale(promise);
246 | return;
247 | } else if (typeof then === 'function') {
248 | doResolve(then.bind(newValue), promise);
249 | return;
250 | }
251 | }
252 | promise._state = 1;
253 | promise._value = newValue;
254 | finale(promise);
255 | }
256 | function reject(promise, reason) {
257 | promise._state = 2;
258 | promise._value = reason;
259 | finale(promise);
260 | }
261 | function finale(promise) {
262 | if (promise._deferreds) {
263 | if (promise._deferreds.length === 1) {
264 | handle(promise, promise._deferreds[0]);
265 | promise._deferreds = null;
266 | return;
267 | }
268 | var _iteratorNormalCompletion = true;
269 | var _didIteratorError = false;
270 | var _iteratorError = undefined;
271 |
272 | try {
273 | for (var _iterator = promise._deferreds[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
274 | var deferred = _step.value;
275 |
276 | handle(promise, deferred);
277 | }
278 | } catch (err) {
279 | _didIteratorError = true;
280 | _iteratorError = err;
281 | } finally {
282 | try {
283 | if (!_iteratorNormalCompletion && _iterator.return) {
284 | _iterator.return();
285 | }
286 | } finally {
287 | if (_didIteratorError) {
288 | throw _iteratorError;
289 | }
290 | }
291 | }
292 |
293 | promise._deferreds = null;
294 | }
295 | }
296 | function handle(promise, deferred) {
297 | while (promise._state === 3) {
298 | promise = promise._value;
299 | }
300 | if (promise._state === 0) {
301 | promise._deferreds ? promise._deferreds.push(deferred) : promise._deferreds = [deferred];
302 | return;
303 | }
304 | handleResolved(promise, deferred);
305 | }
306 | function handleResolved(promise, deferred) {
307 | ascb(function () {
308 | var isResolve = promise._state === 1;
309 | var callback = deferred[isResolve ? 'onFulfilled' : 'onRejected'];
310 | if (callback === null) {
311 | isResolve ? resolve(deferred.promise, promise._value) : reject(deferred.promise, promise._value);
312 | return;
313 | }
314 | try {
315 | var result = callback(promise._value);
316 | resolve(deferred.promise, result);
317 | } catch (error) {
318 | reject(deferred.promise, error);
319 | }
320 | });
321 | }
322 | function getThen(value) {
323 | try {
324 | return [false, value.then];
325 | } catch (error) {
326 | return [true, error];
327 | }
328 | }
329 | function Handler(promise, onFulfilled, onRejected) {
330 | this.promise = promise;
331 | this.onFulfilled = typeof onFulfilled === 'function' ? onFulfilled : null;
332 | this.onRejected = typeof onRejected === 'function' ? onRejected : null;
333 | }
334 |
335 | Promise$1.resolve = function (value) {
336 | if (value instanceof Promise$1) return value;
337 | function valueToPromise(val) {
338 | var p = new Promise$1(Promise$1._noop);
339 | p._state = 1;
340 | p._value = value;
341 | return p;
342 | }
343 | if ((typeof value === 'undefined' ? 'undefined' : _typeof(value)) === 'object' || typeof value === 'function') {
344 | try {
345 | var then = value.then;
346 | if (typeof then === 'function') {
347 | return new Promise$1(then.bind(value));
348 | }
349 | } catch (error) {
350 | return new Promise$1(function (_, reject) {
351 | reject(error);
352 | });
353 | }
354 | }
355 | return valueToPromise(value);
356 | };
357 | Promise$1.reject = function (reason) {
358 | return new Promise$1(function (_, reject) {
359 | reject(reason);
360 | });
361 | };
362 | Promise$1.all = function (array) {
363 | !Array.isArray(array) && (array = Array.from(array));
364 | return new Promise$1(function (resolve, reject) {
365 | if (array.length === 0) return resolve(array);
366 | var remaining = array.length;
367 | for (var i = 0; i < array.length; i++) {
368 | result(array[i], i);
369 | }
370 | function result(val, i) {
371 | if (!val || (typeof val === 'undefined' ? 'undefined' : _typeof(val)) !== 'object' && typeof val !== 'function') {
372 | array[i] = val;
373 | --remaining === 0 && resolve(array);
374 | return;
375 | }
376 | if (val instanceof Promise$1 && val.then === Promise$1.prototype.then) {
377 | while (val._state === 3) {
378 | val = val._value;
379 | }
380 | if (val._state === 1) return result(val._value, i);
381 | if (val._state === 2) reject(val._value);
382 | val.then(function (res) {
383 | return result(res, i);
384 | }, reject);
385 | return;
386 | }
387 | if (typeof val.then === 'function') {
388 | var p = new Promise$1(val.then.bind(val));
389 | p.then(function (res) {
390 | return result(res, i);
391 | }, reject);
392 | return;
393 | }
394 | }
395 | });
396 | };
397 | Promise$1.race = function (array) {
398 | return new Promise$1(function (resolve, reject) {
399 | var _iteratorNormalCompletion = true;
400 | var _didIteratorError = false;
401 | var _iteratorError = undefined;
402 |
403 | try {
404 | for (var _iterator = array[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
405 | var val = _step.value;
406 |
407 | Promise$1.resolve(val).then(resolve, reject);
408 | }
409 | } catch (err) {
410 | _didIteratorError = true;
411 | _iteratorError = err;
412 | } finally {
413 | try {
414 | if (!_iteratorNormalCompletion && _iterator.return) {
415 | _iterator.return();
416 | }
417 | } finally {
418 | if (_didIteratorError) {
419 | throw _iteratorError;
420 | }
421 | }
422 | }
423 | });
424 | };
425 |
426 | return Promise$1;
427 |
428 | })));
429 |
--------------------------------------------------------------------------------
/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |