mirror of
https://github.com/Hopiu/angular.js.git
synced 2026-03-17 07:40:22 +00:00
style(q): reorganize the file + drop fallback dependencies
This commit is contained in:
parent
174952e443
commit
bb3be87606
1 changed files with 137 additions and 123 deletions
260
src/Deferred.js
260
src/Deferred.js
|
|
@ -1,28 +1,149 @@
|
|||
'use strict';
|
||||
|
||||
/**
|
||||
* @ngdoc service
|
||||
* @name angular.module.ng.$q
|
||||
* @requires $rootScope
|
||||
*
|
||||
* @description
|
||||
* A promise/deferred implementation inspired by [Kris Kowal's Q](https://github.com/kriskowal/q).
|
||||
*
|
||||
* [The CommonJS Promise proposal](http://wiki.commonjs.org/wiki/Promises) describes a promise as an
|
||||
* interface for interacting with an object that represents the result of an action that is
|
||||
* performed asynchronously, and may or may not be finished at any given point in time.
|
||||
*
|
||||
* From the perspective of dealing with error handling, deferred and promise apis are to
|
||||
* asynchronous programing what `try`, `catch` and `throw` keywords are to synchronous programing.
|
||||
*
|
||||
* <pre>
|
||||
* // for the purpose of this example let's assume that variables `$q` and `scope` are
|
||||
* // available in the current lexical scope (they could have been injected or passed in).
|
||||
*
|
||||
* function asyncGreet(name) {
|
||||
* var deferred = $q.defer();
|
||||
*
|
||||
* setTimeout(function() {
|
||||
* // since this fn executes async in a future turn of the event loop, we need to wrap
|
||||
* // our code into an $apply call so that the model changes are properly observed.
|
||||
* scope.$apply(function() {
|
||||
* if (okToGreet(name)) {
|
||||
* deferred.resolve('Hello, ' + name + '!');
|
||||
* } else {
|
||||
* deferred.reject('Greeting ' + name + ' is not allowed.');
|
||||
* }
|
||||
* });
|
||||
* }, 1000);
|
||||
*
|
||||
* return deferred.promise;
|
||||
* }
|
||||
*
|
||||
* var promise = asyncGreet('Robin Hood');
|
||||
* promise.then(function(greeting) {
|
||||
* alert('Success: ' + greeting);
|
||||
* }, function(reason) {
|
||||
* alert('Failed: ' + reason);
|
||||
* );
|
||||
* </pre>
|
||||
*
|
||||
* At first it might not be obvious why this extra complexity is worth the trouble. The payoff
|
||||
* comes in the way of
|
||||
* [guarantees that promise and deferred apis make](https://github.com/kriskowal/uncommonjs/blob/master/promises/specification.md).
|
||||
*
|
||||
* Additionally the promise api allows for composition that is very hard to do with the
|
||||
* traditional callback ([CPS](http://en.wikipedia.org/wiki/Continuation-passing_style)) approach.
|
||||
* For more on this please see the [Q documentation](https://github.com/kriskowal/q) especially the
|
||||
* section on serial or parallel joining of promises.
|
||||
*
|
||||
*
|
||||
* # The Deferred API
|
||||
*
|
||||
* A new instance of deferred is constructed by calling `$q.defer()`.
|
||||
*
|
||||
* The purpose of the deferred object is to expose the associated Promise instance as well as apis
|
||||
* that can be used for signaling the successful or unsuccessful completion of the task.
|
||||
*
|
||||
* **Methods**
|
||||
*
|
||||
* - `resolve(value)` – resolves the derived promise with the `value`. If the value is a rejection
|
||||
* constructed via `$q.reject`, the promise will be rejected instead.
|
||||
* - `reject(reason)` – rejects the derived promise with the `reason`. This is equivalent to
|
||||
* resolving it with a rejection constructed via `$q.reject`.
|
||||
*
|
||||
* **Properties**
|
||||
*
|
||||
* - promise – `{Promise}` – promise object associated with this deferred.
|
||||
*
|
||||
*
|
||||
* # The Promise API
|
||||
*
|
||||
* A new promise instance is created when a deferred instance is created and can be retrieved by
|
||||
* calling `deferred.promise`.
|
||||
*
|
||||
* The purpose of the promise object is to allow for interested parties to get access to the result
|
||||
* of the deferred task when it completes.
|
||||
*
|
||||
* **Methods**
|
||||
*
|
||||
* - `then(successCallback, errorCallback)` – regardless of when the promise was or will be resolved
|
||||
* or rejected calls one of the success or error callbacks asynchronously as soon as the result
|
||||
* is available. The callbacks are called with a single argument the result or rejection reason.
|
||||
*
|
||||
* This method *returns a new promise* which is resolved or rejected via the return value of the
|
||||
* `successCallback` or `errorCallback`.
|
||||
*
|
||||
*
|
||||
* # Chaining promises
|
||||
*
|
||||
* Because calling `then` api of a promise returns a new derived promise, it is easily possible
|
||||
* to create a chain of promises:
|
||||
*
|
||||
* <pre>
|
||||
* promiseB = promiseA.then(function(result) {
|
||||
* return result + 1;
|
||||
* });
|
||||
*
|
||||
* // promiseB will be resolved immediately after promiseA is resolved and it's value will be
|
||||
* // the result of promiseA incremented by 1
|
||||
* </pre>
|
||||
*
|
||||
* It is possible to create chains of any length and since a promise can be resolved with another
|
||||
* promise (which will defer its resolution further), it is possible to pause/defer resolution of
|
||||
* the promises at any point in the chain. This makes it possible to implement powerful apis like
|
||||
* $http's response interceptors.
|
||||
*
|
||||
*
|
||||
* # Differences between Kris Kowal's Q and $q
|
||||
*
|
||||
* There are three main differences:
|
||||
*
|
||||
* - $q is integrated with the {@link angular.module.ng.$rootScope.Scope} Scope model observation
|
||||
* mechanism in angular, which means faster propagation of resolution or rejection into your
|
||||
* models and avoiding unnecessary browser repaints, which would result in flickering UI.
|
||||
* - $q promises are recognized by the templating engine in angular, which means that in templates
|
||||
* you can treat promises attached to a scope as if they were the resulting values.
|
||||
* - Q has many more features that $q, but that comes at a cost of bytes. $q is tiny, but contains
|
||||
* all the important functionality needed for common async tasks.
|
||||
*/
|
||||
function $QProvider() {
|
||||
|
||||
this.$get = ['$rootScope', '$exceptionHandler', function($rootScope, $exceptionHandler) {
|
||||
return qFactory(function(callback) {
|
||||
$rootScope.$evalAsync(callback);
|
||||
}, $exceptionHandler);
|
||||
}];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Constructs a promise manager.
|
||||
*
|
||||
* @param {function(function)=} nextTick Function for executing functions in the next turn. Falls
|
||||
* back to `setTimeout` if undefined.
|
||||
* @param {function(...*)=} exceptionHandler Function into which unexpected exceptions are passed for
|
||||
* debugging purposes. Falls back to `console.error` if undefined,
|
||||
* @param {function(function)} nextTick Function for executing functions in the next turn.
|
||||
* @param {function(...*)} exceptionHandler Function into which unexpected exceptions are passed for
|
||||
* debugging purposes.
|
||||
* @returns {object} Promise manager.
|
||||
*/
|
||||
function qFactory(nextTick, exceptionHandler) {
|
||||
|
||||
nextTick = nextTick || function(callback) {
|
||||
setTimeout(callback, 0); // very rare since most of queueing will be handled within $apply
|
||||
};
|
||||
|
||||
exceptionHandler = exceptionHandler || function(e) {
|
||||
// TODO(i): console.error is somehow reset to function(a) {}, it might be a JSTD bug
|
||||
if (console && console.log) {
|
||||
console.log(e);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @ngdoc
|
||||
* @name angular.module.ng.$q#defer
|
||||
|
|
@ -264,110 +385,3 @@ function qFactory(nextTick, exceptionHandler) {
|
|||
all: all
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* @ngdoc service
|
||||
* @name angular.module.ng.$q
|
||||
* @requires $rootScope
|
||||
*
|
||||
* @description
|
||||
* A promise/deferred implementation inspired by [Kris Kowal's Q](https://github.com/kriskowal/q).
|
||||
*
|
||||
* [The CommonJS Promise proposal](http://wiki.commonjs.org/wiki/Promises) describes a promise as an
|
||||
* interface for interacting with an object that represents the result of an action that is
|
||||
* performed asynchronously, and may or may not be finished at any given point in time.
|
||||
*
|
||||
* When it comes to error handling, deferred and promise apis are to asynchronous programing what
|
||||
* `try`, `catch` and `throw` keywords are to synchronous programing.
|
||||
*
|
||||
* <pre>
|
||||
* function asyncGreet(name) {
|
||||
* var deferred = $q.defer();
|
||||
*
|
||||
* setTimeout(function() {
|
||||
* if (okToGreet(name)) {
|
||||
* deferred.resolve('Hello, ' + name + '!');
|
||||
* } else {
|
||||
* deferred.reject('Greeting ' + name + ' is not allowed.');
|
||||
* }
|
||||
* }, 1000);
|
||||
*
|
||||
* return deferred.promise;
|
||||
* }
|
||||
*
|
||||
* var promise = asyncGreet('Robin Hood');
|
||||
* promise.then(function(greeting) {
|
||||
* alert('Success: ' + greeting);
|
||||
* }, function(reason) {
|
||||
* alert('Failed: ' + reason);
|
||||
* );
|
||||
* </pre>
|
||||
*
|
||||
* At first it might not be obvious why this extra complexity is worth the trouble. The payoff
|
||||
* comes in the way of
|
||||
* [guarantees that promise and deferred apis make](https://github.com/kriskowal/uncommonjs/blob/master/promises/specification.md).
|
||||
*
|
||||
* Additionally the promise api allows for composition that is very hard to do with the
|
||||
* traditional callback ([CPS](http://en.wikipedia.org/wiki/Continuation-passing_style)) approach.
|
||||
* For more on this please see the [Q documentation](https://github.com/kriskowal/q) especially the
|
||||
* section on serial or paralel joining of promises.
|
||||
*
|
||||
*
|
||||
* # The Deferred API
|
||||
*
|
||||
* A new instance of deferred is constructed by calling `$q.defer()`.
|
||||
*
|
||||
* The purpose of the deferred object is to expose the associated Promise instance as well as api's
|
||||
* that can be used for singnaling the successful or unsucessful completion of the task.
|
||||
*
|
||||
* **Methods**
|
||||
*
|
||||
* - `resolve(value)` – resolves the derived promise with the `value`. If the value is a rejection
|
||||
* constructed via `$q.reject`, the promise will be rejected instead.
|
||||
* - `reject(reason)` – rejects the derived promise with the `reason`. This is equivalent to
|
||||
* resolving it with a rejection constructed via `$q.reject`.
|
||||
*
|
||||
* **Properties**
|
||||
*
|
||||
* - promise – `{Promise}` – promise object associated with this deferred.
|
||||
*
|
||||
*
|
||||
* # The Promise API
|
||||
*
|
||||
* A new promise instance is created when a deferred instance is created and can be retrieved by
|
||||
* calling `deferred.promise`.
|
||||
*
|
||||
* The purpose of the promise object is to allow for interested parties to get access to the result
|
||||
* of the deferred task when it completes.
|
||||
*
|
||||
* **Methods**
|
||||
*
|
||||
* - `then(successCallback, errorCallback)` – regardless of when the promise was or will be resolved
|
||||
* or rejected calls one of the success or error callbacks asynchronously as soon as the result
|
||||
* is available.
|
||||
*
|
||||
* This method *returns a new promise* which is resolved or rejected via the return value of the
|
||||
* `successCallback` or `errorCallback`.
|
||||
*
|
||||
*
|
||||
* # Differences betweeb Kris Kowal's Q and $q
|
||||
*
|
||||
* There are three main differences:
|
||||
*
|
||||
* - $q is integrated with the {@link angular.module.ng.$rootScope.Scope} Scope model observation
|
||||
* mechanism in angular, which means faster propagation of resolution or rejection into your
|
||||
* models and avoiding unnecessary browser redraws, which would result in flickering UI.
|
||||
* - $q promises are reconginized by the templating engine in angular, which means that in templates
|
||||
* you can treat promises attached to a scope as if they were the resulting values.
|
||||
* - Q has many more features that $q, but that comes at a cost of bytes. $q is tiny, but contains
|
||||
* all the important functionality needed for common async tasks.
|
||||
*/
|
||||
// TODO(i): move elsewhere
|
||||
function $QProvider() {
|
||||
|
||||
this.$get = ['$rootScope', '$exceptionHandler', function($rootScope, $exceptionHandler) {
|
||||
return qFactory(function(callback) {
|
||||
$rootScope.$evalAsync(callback);
|
||||
}, $exceptionHandler);
|
||||
}];
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue