summaryrefslogtreecommitdiffstats
path: root/js/vendor/angular/angular.js
diff options
context:
space:
mode:
Diffstat (limited to 'js/vendor/angular/angular.js')
-rw-r--r--js/vendor/angular/angular.js555
1 files changed, 292 insertions, 263 deletions
diff --git a/js/vendor/angular/angular.js b/js/vendor/angular/angular.js
index 36c17d2ff..57da51b3d 100644
--- a/js/vendor/angular/angular.js
+++ b/js/vendor/angular/angular.js
@@ -1,5 +1,5 @@
/**
- * @license AngularJS v1.3.2
+ * @license AngularJS v1.3.3
* (c) 2010-2014 Google, Inc. http://angularjs.org
* License: MIT
*/
@@ -42,40 +42,23 @@ function minErr(module, ErrorConstructor) {
prefix = '[' + (module ? module + ':' : '') + code + '] ',
template = arguments[1],
templateArgs = arguments,
- stringify = function(obj) {
- if (typeof obj === 'function') {
- return obj.toString().replace(/ \{[\s\S]*$/, '');
- } else if (typeof obj === 'undefined') {
- return 'undefined';
- } else if (typeof obj !== 'string') {
- return JSON.stringify(obj);
- }
- return obj;
- },
+
message, i;
message = prefix + template.replace(/\{\d+\}/g, function(match) {
var index = +match.slice(1, -1), arg;
if (index + 2 < templateArgs.length) {
- arg = templateArgs[index + 2];
- if (typeof arg === 'function') {
- return arg.toString().replace(/ ?\{[\s\S]*$/, '');
- } else if (typeof arg === 'undefined') {
- return 'undefined';
- } else if (typeof arg !== 'string') {
- return toJson(arg);
- }
- return arg;
+ return toDebugString(templateArgs[index + 2]);
}
return match;
});
- message = message + '\nhttp://errors.angularjs.org/1.3.2/' +
+ message = message + '\nhttp://errors.angularjs.org/1.3.3/' +
(module ? module + '/' : '') + code;
for (i = 2; i < arguments.length; i++) {
- message = message + (i == 2 ? '?' : '&') + 'p' + (i-2) + '=' +
- encodeURIComponent(stringify(arguments[i]));
+ message = message + (i == 2 ? '?' : '&') + 'p' + (i - 2) + '=' +
+ encodeURIComponent(toDebugString(arguments[i]));
}
return new ErrorConstructor(message);
};
@@ -715,7 +698,7 @@ function includes(array, obj) {
function arrayRemove(array, value) {
var index = array.indexOf(value);
- if (index >=0)
+ if (index >= 0)
array.splice(index, 1);
return value;
}
@@ -916,7 +899,7 @@ function equals(o1, o2) {
if (isArray(o1)) {
if (!isArray(o2)) return false;
if ((length = o1.length) == o2.length) {
- for (key=0; key<length; key++) {
+ for (key = 0; key < length; key++) {
if (!equals(o1[key], o2[key])) return false;
}
return true;
@@ -1002,7 +985,7 @@ function bind(self, fn) {
return curryArgs.length
? function() {
return arguments.length
- ? fn.apply(self, curryArgs.concat(slice.call(arguments, 0)))
+ ? fn.apply(self, concat(curryArgs, arguments, 0))
: fn.apply(self, curryArgs);
}
: function() {
@@ -1202,7 +1185,7 @@ var ngAttrPrefixes = ['ng-', 'data-ng-', 'ng:', 'x-ng-'];
function getNgAttribute(element, ngAttr) {
var attr, i, ii = ngAttrPrefixes.length;
element = jqLite(element);
- for (i=0; i<ii; ++i) {
+ for (i = 0; i < ii; ++i) {
attr = ngAttrPrefixes[i] + ngAttr;
if (isString(attr = element.attr(attr))) {
return attr;
@@ -1987,6 +1970,34 @@ function setupModuleLoader(window) {
}
+/* global: toDebugString: true */
+
+function serializeObject(obj) {
+ var seen = [];
+
+ return JSON.stringify(obj, function(key, val) {
+ val = toJsonReplacer(key, val);
+ if (isObject(val)) {
+
+ if (seen.indexOf(val) >= 0) return '<<already seen>>';
+
+ seen.push(val);
+ }
+ return val;
+ });
+}
+
+function toDebugString(obj) {
+ if (typeof obj === 'function') {
+ return obj.toString().replace(/ \{[\s\S]*$/, '');
+ } else if (typeof obj === 'undefined') {
+ return 'undefined';
+ } else if (typeof obj !== 'string') {
+ return serializeObject(obj);
+ }
+ return obj;
+}
+
/* global angularModule: true,
version: true,
@@ -2089,11 +2100,11 @@ function setupModuleLoader(window) {
* - `codeName` – `{string}` – Code name of the release, such as "jiggling-armfat".
*/
var version = {
- full: '1.3.2', // all of these placeholder strings will be replaced by grunt's
+ full: '1.3.3', // all of these placeholder strings will be replaced by grunt's
major: 1, // package task
minor: 3,
- dot: 2,
- codeName: 'cardiovasculatory-magnification'
+ dot: 3,
+ codeName: 'undersea-arithmetic'
};
@@ -2826,7 +2837,7 @@ forEach({
}
} else {
return (element[name] ||
- (element.attributes.getNamedItem(name)|| noop).specified)
+ (element.attributes.getNamedItem(name) || noop).specified)
? lowercasedName
: undefined;
}
@@ -4162,7 +4173,7 @@ function $AnchorScrollProvider() {
* @name $anchorScrollProvider#disableAutoScrolling
*
* @description
- * By default, {@link ng.$anchorScroll $anchorScroll()} will automatically will detect changes to
+ * By default, {@link ng.$anchorScroll $anchorScroll()} will automatically detect changes to
* {@link ng.$location#hash $location.hash()} and scroll to the element matching the new hash.<br />
* Use this method to disable automatic scrolling.
*
@@ -4811,8 +4822,7 @@ function $$AsyncCallbackProvider() {
/**
* @param {object} window The global window object.
* @param {object} document jQuery wrapped document.
- * @param {function()} XHR XMLHttpRequest constructor.
- * @param {object} $log console.log or an object with the same interface.
+ * @param {object} $log window.console or an object with the same interface.
* @param {object} $sniffer $sniffer service
*/
function Browser(window, document, $log, $sniffer) {
@@ -5162,8 +5172,8 @@ function Browser(window, document, $log, $sniffer) {
// - 20 cookies per unique domain
// - 4096 bytes per cookie
if (cookieLength > 4096) {
- $log.warn("Cookie '"+ name +
- "' possibly not set or overflowed because it was too large ("+
+ $log.warn("Cookie '" + name +
+ "' possibly not set or overflowed because it was too large (" +
cookieLength + " > 4096 bytes)!");
}
}
@@ -5828,7 +5838,7 @@ function $TemplateCacheProvider() {
*
*
* #### `bindToController`
- * When an isolate scope is used for a component (see above), and `controllerAs` is used, `bindToController` will
+ * When an isolate scope is used for a component (see above), and `controllerAs` is used, `bindToController: true` will
* allow a component to have its properties bound to the controller, rather than to scope. When the controller
* is instantiated, the initial values of the isolate scope bindings are already available.
*
@@ -6677,16 +6687,16 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
// for each tuples
var nbrUrisWith2parts = Math.floor(rawUris.length / 2);
- for (var i=0; i<nbrUrisWith2parts; i++) {
- var innerIdx = i*2;
+ for (var i = 0; i < nbrUrisWith2parts; i++) {
+ var innerIdx = i * 2;
// sanitize the uri
result += $$sanitizeUri(trim(rawUris[innerIdx]), true);
// add the descriptor
- result += (" " + trim(rawUris[innerIdx+1]));
+ result += (" " + trim(rawUris[innerIdx + 1]));
}
// split the last item into uri and descriptor
- var lastTuple = trim(rawUris[i*2]).split(/\s/);
+ var lastTuple = trim(rawUris[i * 2]).split(/\s/);
// sanitize the last uri
result += $$sanitizeUri(trim(lastTuple[0]), true);
@@ -6880,7 +6890,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
if (!node) {
return 'html';
} else {
- return nodeName_(node) !== 'foreignobject' && node.toString().match(/SVG/) ? 'svg': 'html';
+ return nodeName_(node) !== 'foreignobject' && node.toString().match(/SVG/) ? 'svg' : 'html';
}
}
@@ -7693,7 +7703,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
var match = null;
if (hasDirectives.hasOwnProperty(name)) {
for (var directive, directives = $injector.get(name + Suffix),
- i = 0, ii = directives.length; i<ii; i++) {
+ i = 0, ii = directives.length; i < ii; i++) {
try {
directive = directives[i];
if ((maxPriority === undefined || maxPriority > directive.priority) &&
@@ -7722,7 +7732,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
function directiveIsMultiElement(name) {
if (hasDirectives.hasOwnProperty(name)) {
for (var directive, directives = $injector.get(name + Suffix),
- i = 0, ii = directives.length; i<ii; i++) {
+ i = 0, ii = directives.length; i < ii; i++) {
directive = directives[i];
if (directive.multiElement) {
return true;
@@ -7941,7 +7951,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
case 'svg':
case 'math':
var wrapper = document.createElement('div');
- wrapper.innerHTML = '<'+type+'>'+template+'</'+type+'>';
+ wrapper.innerHTML = '<' + type + '>' + template + '</' + type + '>';
return wrapper.childNodes[0].childNodes;
default:
return template;
@@ -8298,6 +8308,10 @@ function $ControllerProvider() {
* * if $controllerProvider#allowGlobals, check `window[constructor]` on the global
* `window` object (not recommended)
*
+ * The string can use the `controller as property` syntax, where the controller instance is published
+ * as the specified property on the `scope`; the `scope` must be injected into `locals` param for this
+ * to work correctly.
+ *
* @param {Object} locals Injection locals for Controller.
* @return {Object} Instance of given controller.
*
@@ -8472,7 +8486,7 @@ function defaultHttpResponseTransform(data, headers) {
// strip json vulnerability protection prefix
data = data.replace(JSON_PROTECTION_PREFIX, '');
var contentType = headers('Content-Type');
- if ((contentType && contentType.indexOf(APPLICATION_JSON) === 0) ||
+ if ((contentType && contentType.indexOf(APPLICATION_JSON) === 0 && data.trim()) ||
(JSON_START.test(data) && JSON_END.test(data))) {
data = fromJson(data);
}
@@ -10043,7 +10057,8 @@ function $InterpolateProvider() {
function parseStringifyInterceptor(value) {
try {
- return stringify(getValue(value));
+ value = getValue(value);
+ return allOrNothing && !isDefined(value) ? value : stringify(value);
} catch (err) {
var newErr = $interpolateMinErr('interr', "Can't interpolate: {0}\n{1}", text,
err.toString());
@@ -10367,8 +10382,8 @@ function encodePath(path) {
return segments.join('/');
}
-function parseAbsoluteUrl(absoluteUrl, locationObj, appBase) {
- var parsedUrl = urlResolve(absoluteUrl, appBase);
+function parseAbsoluteUrl(absoluteUrl, locationObj) {
+ var parsedUrl = urlResolve(absoluteUrl);
locationObj.$$protocol = parsedUrl.protocol;
locationObj.$$host = parsedUrl.hostname;
@@ -10376,12 +10391,12 @@ function parseAbsoluteUrl(absoluteUrl, locationObj, appBase) {
}
-function parseAppUrl(relativeUrl, locationObj, appBase) {
+function parseAppUrl(relativeUrl, locationObj) {
var prefixed = (relativeUrl.charAt(0) !== '/');
if (prefixed) {
relativeUrl = '/' + relativeUrl;
}
- var match = urlResolve(relativeUrl, appBase);
+ var match = urlResolve(relativeUrl);
locationObj.$$path = decodeURIComponent(prefixed && match.pathname.charAt(0) === '/' ?
match.pathname.substring(1) : match.pathname);
locationObj.$$search = parseKeyValue(match.search);
@@ -10436,7 +10451,7 @@ function LocationHtml5Url(appBase, basePrefix) {
this.$$html5 = true;
basePrefix = basePrefix || '';
var appBaseNoFile = stripFile(appBase);
- parseAbsoluteUrl(appBase, this, appBase);
+ parseAbsoluteUrl(appBase, this);
/**
@@ -10451,7 +10466,7 @@ function LocationHtml5Url(appBase, basePrefix) {
appBaseNoFile);
}
- parseAppUrl(pathUrl, this, appBase);
+ parseAppUrl(pathUrl, this);
if (!this.$$path) {
this.$$path = '/';
@@ -10514,7 +10529,7 @@ function LocationHtml5Url(appBase, basePrefix) {
function LocationHashbangUrl(appBase, hashPrefix) {
var appBaseNoFile = stripFile(appBase);
- parseAbsoluteUrl(appBase, this, appBase);
+ parseAbsoluteUrl(appBase, this);
/**
@@ -10534,7 +10549,7 @@ function LocationHashbangUrl(appBase, hashPrefix) {
throw $locationMinErr('ihshprfx', 'Invalid url "{0}", missing hash prefix "{1}".', url,
hashPrefix);
}
- parseAppUrl(withoutHashUrl, this, appBase);
+ parseAppUrl(withoutHashUrl, this);
this.$$path = removeWindowsDriveName(this.$$path, withoutHashUrl, appBase);
@@ -11174,11 +11189,19 @@ function $LocationProvider() {
$rootScope.$evalAsync(function() {
var oldUrl = $location.absUrl();
var oldState = $location.$$state;
+ var defaultPrevented;
$location.$$parse(newUrl);
$location.$$state = newState;
- if ($rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,
- newState, oldState).defaultPrevented) {
+
+ defaultPrevented = $rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,
+ newState, oldState).defaultPrevented;
+
+ // if the location was changed by a `$locationChangeStart` handler then stop
+ // processing this location change
+ if ($location.absUrl() !== newUrl) return;
+
+ if (defaultPrevented) {
$location.$$parse(oldUrl);
$location.$$state = oldState;
setBrowserUrlWithFallback(oldUrl, false, oldState);
@@ -11202,13 +11225,20 @@ function $LocationProvider() {
initializing = false;
$rootScope.$evalAsync(function() {
- if ($rootScope.$broadcast('$locationChangeStart', $location.absUrl(), oldUrl,
- $location.$$state, oldState).defaultPrevented) {
+ var newUrl = $location.absUrl();
+ var defaultPrevented = $rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,
+ $location.$$state, oldState).defaultPrevented;
+
+ // if the location was changed by a `$locationChangeStart` handler then stop
+ // processing this location change
+ if ($location.absUrl() !== newUrl) return;
+
+ if (defaultPrevented) {
$location.$$parse(oldUrl);
$location.$$state = oldState;
} else {
if (urlOrStateChanged) {
- setBrowserUrlWithFallback($location.absUrl(), currentReplace,
+ setBrowserUrlWithFallback(newUrl, currentReplace,
oldState === $location.$$state ? null : $location.$$state);
}
afterLocationChange(oldUrl, oldState);
@@ -11398,7 +11428,7 @@ var $parseMinErr = minErr('$parse');
// Sandboxing Angular Expressions
// ------------------------------
// Angular expressions are generally considered safe because these expressions only have direct
-// access to $scope and locals. However, one can obtain the ability to execute arbitrary JS code by
+// access to `$scope` and locals. However, one can obtain the ability to execute arbitrary JS code by
// obtaining a reference to native JS functions such as the Function constructor.
//
// As an example, consider the following Angular expression:
@@ -11407,7 +11437,7 @@ var $parseMinErr = minErr('$parse');
//
// This sandboxing technique is not perfect and doesn't aim to be. The goal is to prevent exploits
// against the expression language, but not to prevent exploits that were enabled by exposing
-// sensitive JavaScript or browser apis on Scope. Exposing such objects on a Scope is never a good
+// sensitive JavaScript or browser APIs on Scope. Exposing such objects on a Scope is never a good
// practice and therefore we are not even trying to protect against interaction with an object
// explicitly exposed in this way.
//
@@ -11415,6 +11445,8 @@ var $parseMinErr = minErr('$parse');
// window or some DOM object that has a reference to window is published onto a Scope.
// Similarly we prevent invocations of function known to be dangerous, as well as assignments to
// native objects.
+//
+// See https://docs.angularjs.org/guide/security
function ensureSafeMemberName(name, fullExpression) {
@@ -11423,7 +11455,7 @@ function ensureSafeMemberName(name, fullExpression) {
|| name === "__proto__") {
throw $parseMinErr('isecfld',
'Attempting to access a disallowed field in Angular expressions! '
- +'Expression: {0}', fullExpression);
+ + 'Expression: {0}', fullExpression);
}
return name;
}
@@ -11500,24 +11532,24 @@ var OPERATORS = extend(createMap(), {
}
return a;
}
- return isDefined(b)?b:undefined;},
+ return isDefined(b) ? b : undefined;},
'-':function(self, locals, a, b) {
a=a(self, locals); b=b(self, locals);
- return (isDefined(a)?a:0)-(isDefined(b)?b:0);
+ return (isDefined(a) ? a : 0) - (isDefined(b) ? b : 0);
},
- '*':function(self, locals, a, b) {return a(self, locals)*b(self, locals);},
- '/':function(self, locals, a, b) {return a(self, locals)/b(self, locals);},
- '%':function(self, locals, a, b) {return a(self, locals)%b(self, locals);},
- '===':function(self, locals, a, b) {return a(self, locals)===b(self, locals);},
- '!==':function(self, locals, a, b) {return a(self, locals)!==b(self, locals);},
- '==':function(self, locals, a, b) {return a(self, locals)==b(self, locals);},
- '!=':function(self, locals, a, b) {return a(self, locals)!=b(self, locals);},
- '<':function(self, locals, a, b) {return a(self, locals)<b(self, locals);},
- '>':function(self, locals, a, b) {return a(self, locals)>b(self, locals);},
- '<=':function(self, locals, a, b) {return a(self, locals)<=b(self, locals);},
- '>=':function(self, locals, a, b) {return a(self, locals)>=b(self, locals);},
- '&&':function(self, locals, a, b) {return a(self, locals)&&b(self, locals);},
- '||':function(self, locals, a, b) {return a(self, locals)||b(self, locals);},
+ '*':function(self, locals, a, b) {return a(self, locals) * b(self, locals);},
+ '/':function(self, locals, a, b) {return a(self, locals) / b(self, locals);},
+ '%':function(self, locals, a, b) {return a(self, locals) % b(self, locals);},
+ '===':function(self, locals, a, b) {return a(self, locals) === b(self, locals);},
+ '!==':function(self, locals, a, b) {return a(self, locals) !== b(self, locals);},
+ '==':function(self, locals, a, b) {return a(self, locals) == b(self, locals);},
+ '!=':function(self, locals, a, b) {return a(self, locals) != b(self, locals);},
+ '<':function(self, locals, a, b) {return a(self, locals) < b(self, locals);},
+ '>':function(self, locals, a, b) {return a(self, locals) > b(self, locals);},
+ '<=':function(self, locals, a, b) {return a(self, locals) <= b(self, locals);},
+ '>=':function(self, locals, a, b) {return a(self, locals) >= b(self, locals);},
+ '&&':function(self, locals, a, b) {return a(self, locals) && b(self, locals);},
+ '||':function(self, locals, a, b) {return a(self, locals) || b(self, locals);},
'!':function(self, locals, a) {return !a(self, locals);},
//Tokenized as operators but parsed as assignment/filters
@@ -11543,44 +11575,31 @@ Lexer.prototype = {
lex: function(text) {
this.text = text;
this.index = 0;
- this.ch = undefined;
this.tokens = [];
while (this.index < this.text.length) {
- this.ch = this.text.charAt(this.index);
- if (this.is('"\'')) {
- this.readString(this.ch);
- } else if (this.isNumber(this.ch) || this.is('.') && this.isNumber(this.peek())) {
+ var ch = this.text.charAt(this.index);
+ if (ch === '"' || ch === "'") {
+ this.readString(ch);
+ } else if (this.isNumber(ch) || ch === '.' && this.isNumber(this.peek())) {
this.readNumber();
- } else if (this.isIdent(this.ch)) {
+ } else if (this.isIdent(ch)) {
this.readIdent();
- } else if (this.is('(){}[].,;:?')) {
- this.tokens.push({
- index: this.index,
- text: this.ch
- });
+ } else if (this.is(ch, '(){}[].,;:?')) {
+ this.tokens.push({index: this.index, text: ch});
this.index++;
- } else if (this.isWhitespace(this.ch)) {
+ } else if (this.isWhitespace(ch)) {
this.index++;
} else {
- var ch2 = this.ch + this.peek();
+ var ch2 = ch + this.peek();
var ch3 = ch2 + this.peek(2);
- var fn = OPERATORS[this.ch];
- var fn2 = OPERATORS[ch2];
- var fn3 = OPERATORS[ch3];
- if (fn3) {
- this.tokens.push({index: this.index, text: ch3, fn: fn3});
- this.index += 3;
- } else if (fn2) {
- this.tokens.push({index: this.index, text: ch2, fn: fn2});
- this.index += 2;
- } else if (fn) {
- this.tokens.push({
- index: this.index,
- text: this.ch,
- fn: fn
- });
- this.index += 1;
+ var op1 = OPERATORS[ch];
+ var op2 = OPERATORS[ch2];
+ var op3 = OPERATORS[ch3];
+ if (op1 || op2 || op3) {
+ var token = op3 ? ch3 : (op2 ? ch2 : ch);
+ this.tokens.push({index: this.index, text: token, operator: true});
+ this.index += token.length;
} else {
this.throwError('Unexpected next character ', this.index, this.index + 1);
}
@@ -11589,8 +11608,8 @@ Lexer.prototype = {
return this.tokens;
},
- is: function(chars) {
- return chars.indexOf(this.ch) !== -1;
+ is: function(ch, chars) {
+ return chars.indexOf(ch) !== -1;
},
peek: function(i) {
@@ -11599,7 +11618,7 @@ Lexer.prototype = {
},
isNumber: function(ch) {
- return ('0' <= ch && ch <= '9');
+ return ('0' <= ch && ch <= '9') && typeof ch === "string";
},
isWhitespace: function(ch) {
@@ -11652,79 +11671,28 @@ Lexer.prototype = {
}
this.index++;
}
- number = 1 * number;
this.tokens.push({
index: start,
text: number,
constant: true,
- fn: function() { return number; }
+ value: Number(number)
});
},
readIdent: function() {
- var expression = this.text;
-
- var ident = '';
var start = this.index;
-
- var lastDot, peekIndex, methodName, ch;
-
while (this.index < this.text.length) {
- ch = this.text.charAt(this.index);
- if (ch === '.' || this.isIdent(ch) || this.isNumber(ch)) {
- if (ch === '.') lastDot = this.index;
- ident += ch;
- } else {
+ var ch = this.text.charAt(this.index);
+ if (!(this.isIdent(ch) || this.isNumber(ch))) {
break;
}
this.index++;
}
-
- //check if the identifier ends with . and if so move back one char
- if (lastDot && ident[ident.length - 1] === '.') {
- this.index--;
- ident = ident.slice(0, -1);
- lastDot = ident.lastIndexOf('.');
- if (lastDot === -1) {
- lastDot = undefined;
- }
- }
-
- //check if this is not a method invocation and if it is back out to last dot
- if (lastDot) {
- peekIndex = this.index;
- while (peekIndex < this.text.length) {
- ch = this.text.charAt(peekIndex);
- if (ch === '(') {
- methodName = ident.substr(lastDot - start + 1);
- ident = ident.substr(0, lastDot - start);
- this.index = peekIndex;
- break;
- }
- if (this.isWhitespace(ch)) {
- peekIndex++;
- } else {
- break;
- }
- }
- }
-
this.tokens.push({
index: start,
- text: ident,
- fn: CONSTANTS[ident] || getterFn(ident, this.options, expression)
+ text: this.text.slice(start, this.index),
+ identifier: true
});
-
- if (methodName) {
- this.tokens.push({
- index: lastDot,
- text: '.'
- });
- this.tokens.push({
- index: lastDot + 1,
- text: methodName
- });
- }
},
readString: function(quote) {
@@ -11755,9 +11723,8 @@ Lexer.prototype = {
this.tokens.push({
index: start,
text: rawString,
- string: string,
constant: true,
- fn: function() { return string; }
+ value: string
});
return;
} else {
@@ -11818,16 +11785,12 @@ Parser.prototype = {
primary = this.arrayDeclaration();
} else if (this.expect('{')) {
primary = this.object();
+ } else if (this.peek().identifier) {
+ primary = this.identifier();
+ } else if (this.peek().constant) {
+ primary = this.constant();
} else {
- var token = this.expect();
- primary = token.fn;
- if (!primary) {
- this.throwError('not a primary expression', token);
- }
- if (token.constant) {
- primary.constant = true;
- primary.literal = true;
- }
+ this.throwError('not a primary expression', this.peek());
}
var next, context;
@@ -11861,8 +11824,11 @@ Parser.prototype = {
},
peek: function(e1, e2, e3, e4) {
- if (this.tokens.length > 0) {
- var token = this.tokens[0];
+ return this.peekAhead(0, e1, e2, e3, e4);
+ },
+ peekAhead: function(i, e1, e2, e3, e4) {
+ if (this.tokens.length > i) {
+ var token = this.tokens[i];
var t = token.text;
if (t === e1 || t === e2 || t === e3 || t === e4 ||
(!e1 && !e2 && !e3 && !e4)) {
@@ -11882,12 +11848,19 @@ Parser.prototype = {
},
consume: function(e1) {
- if (!this.expect(e1)) {
+ if (this.tokens.length === 0) {
+ throw $parseMinErr('ueoe', 'Unexpected end of expression: {0}', this.text);
+ }
+
+ var token = this.expect(e1);
+ if (!token) {
this.throwError('is unexpected, expecting [' + e1 + ']', this.peek());
}
+ return token;
},
- unaryFn: function(fn, right) {
+ unaryFn: function(op, right) {
+ var fn = OPERATORS[op];
return extend(function $parseUnaryFn(self, locals) {
return fn(self, locals, right);
}, {
@@ -11896,7 +11869,8 @@ Parser.prototype = {
});
},
- binaryFn: function(left, fn, right, isBranching) {
+ binaryFn: function(left, op, right, isBranching) {
+ var fn = OPERATORS[op];
return extend(function $parseBinaryFn(self, locals) {
return fn(self, locals, left, right);
}, {
@@ -11905,6 +11879,28 @@ Parser.prototype = {
});
},
+ identifier: function() {
+ var id = this.consume().text;
+
+ //Continue reading each `.identifier` unless it is a method invocation
+ while (this.peek('.') && this.peekAhead(1).identifier && !this.peekAhead(2, '(')) {
+ id += this.consume().text + this.consume().text;
+ }
+
+ return CONSTANTS[id] || getterFn(id, this.options, this.text);
+ },
+
+ constant: function() {
+ var value = this.consume().value;
+
+ return extend(function $parseConstant() {
+ return value;
+ }, {
+ constant: true,
+ literal: true
+ });
+ },
+
statements: function() {
var statements = [];
while (true) {
@@ -11936,8 +11932,7 @@ Parser.prototype = {
},
filter: function(inputFn) {
- var token = this.expect();
- var fn = this.$filter(token.text);
+ var fn = this.$filter(this.consume().text);
var argsFn;
var args;
@@ -12000,7 +11995,7 @@ Parser.prototype = {
var token;
if ((token = this.expect('?'))) {
middle = this.assignment();
- if ((token = this.expect(':'))) {
+ if (this.consume(':')) {
var right = this.assignment();
return extend(function $parseTernary(self, locals) {
@@ -12008,9 +12003,6 @@ Parser.prototype = {
}, {
constant: left.constant && middle.constant && right.constant
});
-
- } else {
- this.throwError('expected :', token);
}
}
@@ -12021,7 +12013,7 @@ Parser.prototype = {
var left = this.logicalAND();
var token;
while ((token = this.expect('||'))) {
- left = this.binaryFn(left, token.fn, this.logicalAND(), true);
+ left = this.binaryFn(left, token.text, this.logicalAND(), true);
}
return left;
},
@@ -12030,7 +12022,7 @@ Parser.prototype = {
var left = this.equality();
var token;
if ((token = this.expect('&&'))) {
- left = this.binaryFn(left, token.fn, this.logicalAND(), true);
+ left = this.binaryFn(left, token.text, this.logicalAND(), true);
}
return left;
},
@@ -12039,7 +12031,7 @@ Parser.prototype = {
var left = this.relational();
var token;
if ((token = this.expect('==','!=','===','!=='))) {
- left = this.binaryFn(left, token.fn, this.equality());
+ left = this.binaryFn(left, token.text, this.equality());
}
return left;
},
@@ -12048,7 +12040,7 @@ Parser.prototype = {
var left = this.additive();
var token;
if ((token = this.expect('<', '>', '<=', '>='))) {
- left = this.binaryFn(left, token.fn, this.relational());
+ left = this.binaryFn(left, token.text, this.relational());
}
return left;
},
@@ -12057,7 +12049,7 @@ Parser.prototype = {
var left = this.multiplicative();
var token;
while ((token = this.expect('+','-'))) {
- left = this.binaryFn(left, token.fn, this.multiplicative());
+ left = this.binaryFn(left, token.text, this.multiplicative());
}
return left;
},
@@ -12066,7 +12058,7 @@ Parser.prototype = {
var left = this.unary();
var token;
while ((token = this.expect('*','/','%'))) {
- left = this.binaryFn(left, token.fn, this.unary());
+ left = this.binaryFn(left, token.text, this.unary());
}
return left;
},
@@ -12076,9 +12068,9 @@ Parser.prototype = {
if (this.expect('+')) {
return this.primary();
} else if ((token = this.expect('-'))) {
- return this.binaryFn(Parser.ZERO, token.fn, this.unary());
+ return this.binaryFn(Parser.ZERO, token.text, this.unary());
} else if ((token = this.expect('!'))) {
- return this.unaryFn(token.fn, this.unary());
+ return this.unaryFn(token.text, this.unary());
} else {
return this.primary();
}
@@ -12086,7 +12078,7 @@ Parser.prototype = {
fieldAccess: function(object) {
var expression = this.text;
- var field = this.expect().text;
+ var field = this.consume().text;
var getter = getterFn(field, this.options, expression);
return extend(function $parseFieldAccess(scope, locals, self) {
@@ -12171,8 +12163,7 @@ Parser.prototype = {
// Support trailing commas per ES5.1.
break;
}
- var elementFn = this.expression();
- elementFns.push(elementFn);
+ elementFns.push(this.expression());
} while (this.expect(','));
}
this.consume(']');
@@ -12198,11 +12189,16 @@ Parser.prototype = {
// Support trailing commas per ES5.1.
break;
}
- var token = this.expect();
- keys.push(token.string || token.text);
+ var token = this.consume();
+ if (token.constant) {
+ keys.push(token.value);
+ } else if (token.identifier) {
+ keys.push(token.text);
+ } else {
+ this.throwError("invalid key", token);
+ }
this.consume(':');
- var value = this.expression();
- valueFns.push(value);
+ valueFns.push(this.expression());
} while (this.expect(','));
}
this.consume('}');
@@ -12644,13 +12640,21 @@ function $ParseProvider() {
function addInterceptor(parsedExpression, interceptorFn) {
if (!interceptorFn) return parsedExpression;
+ var watchDelegate = parsedExpression.$$watchDelegate;
- var fn = function interceptedExpression(scope, locals) {
+ var regularWatch =
+ watchDelegate !== oneTimeLiteralWatchDelegate &&
+ watchDelegate !== oneTimeWatchDelegate;
+
+ var fn = regularWatch ? function regularInterceptedExpression(scope, locals) {
+ var value = parsedExpression(scope, locals);
+ return interceptorFn(value, scope, locals);
+ } : function oneTimeInterceptedExpression(scope, locals) {
var value = parsedExpression(scope, locals);
var result = interceptorFn(value, scope, locals);
// we only return the interceptor's result if the
// initial value is defined (for bind-once)
- return isDefined(value) || interceptorFn.$stateful ? result : value;
+ return isDefined(value) ? result : value;
};
// Propagate $$watchDelegates other then inputsWatchDelegate
@@ -12675,7 +12679,11 @@ function $ParseProvider() {
* @requires $rootScope
*
* @description
- * A promise/deferred implementation inspired by [Kris Kowal's Q](https://github.com/kriskowal/q).
+ * A service that helps you run functions asynchronously, and use their return values (or exceptions)
+ * when they are done processing.
+ *
+ * This is an implementation of promises/deferred objects inspired by
+ * [Kris Kowal's Q](https://github.com/kriskowal/q).
*
* $q can be used in two fashions --- one which is more similar to Kris Kowal's Q or jQuery's Deferred
* implementations, and the other which resembles ES6 promises to some degree.
@@ -12811,16 +12819,12 @@ function $ParseProvider() {
*
* - `catch(errorCallback)` – shorthand for `promise.then(null, errorCallback)`
*
- * - `finally(callback)` – allows you to observe either the fulfillment or rejection of a promise,
+ * - `finally(callback, notifyCallback)` – allows you to observe either the fulfillment or rejection of a promise,
* but to do so without modifying the final value. This is useful to release resources or do some
* clean-up that needs to be done whether the promise was rejected or resolved. See the [full
* specification](https://github.com/kriskowal/q/wiki/API-Reference#promisefinallycallback) for
* more information.
*
- * Because `finally` is a reserved word in JavaScript and reserved keywords are not supported as
- * property names by ES3, you'll need to invoke the method like `promise['finally'](callback)` to
- * make your code IE8 and Android 2.x compatible.
- *
* # Chaining promises
*
* Because calling the `then` method of a promise returns a new derived promise, it is easily
@@ -14043,11 +14047,11 @@ function $RootScopeProvider() {
if (ttl < 5) {
logIdx = 4 - ttl;
if (!watchLog[logIdx]) watchLog[logIdx] = [];
- logMsg = (isFunction(watch.exp))
- ? 'fn: ' + (watch.exp.name || watch.exp.toString())
- : watch.exp;
- logMsg += '; newVal: ' + toJson(value) + '; oldVal: ' + toJson(last);
- watchLog[logIdx].push(logMsg);
+ watchLog[logIdx].push({
+ msg: isFunction(watch.exp) ? 'fn: ' + (watch.exp.name || watch.exp.toString()) : watch.exp,
+ newVal: value,