angularjs-rails 1.4.0 → 1.4.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 3ee721efbee3aea806049cf64fc868356b7d9d7a
4
- data.tar.gz: fee435dfb50624ed360261cc8d8c2b28af9e5f6f
3
+ metadata.gz: 1c924719d1629cab7fd1823f2e859913bd0ad48a
4
+ data.tar.gz: f0380593bbd1beca71ddddad5ffe29288535a4c7
5
5
  SHA512:
6
- metadata.gz: e64d482f45a06799da02e0b512f7b6b1923a5e3989a2e2a198d22b31e27d083b88d937a5a7d724522839f1c5ba347478026db2e84d26d185ce6af930397ae67d
7
- data.tar.gz: cf04d929c1c406f43798732e1d7c4a01ccfa0107869b77df7188078863c58048e85a87d08d3f7705b7c7c84f55d8dc1df8cd46b0d7d5fa2eb48a66b918ef7be0
6
+ metadata.gz: e2ccfb66fb68a67624f7b9f53cddf97f157a0cb3085164883f3a9636b511245f665bbe8d97b12fcf6309cc5e1c01d315bf0f91713b8bea269ef94ad0ea45fce4
7
+ data.tar.gz: f781284c10730d7193f79b5a1498c020ca3ec0afcc08470a6abcbdaad6b9b520a2bbc38e9ffcbd69d1e320c194e9a59796ffabcf6ae1f5e93576c7cb6568496d
@@ -1,6 +1,6 @@
1
1
  module AngularJS
2
2
  module Rails
3
- VERSION = "1.4.0"
4
- UNSTABLE_VERSION = "2.0.0-alpha.25"
3
+ VERSION = "1.4.2"
4
+ UNSTABLE_VERSION = "2.0.0-alpha.28"
5
5
  end
6
6
  end
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -504,7 +504,8 @@ var $$AnimateChildrenDirective = [function() {
504
504
  * unless you really need a digest to kick off afterwards.
505
505
  *
506
506
  * Keep in mind that, to make this easier, ngAnimate has tweaked the JS animations API to recognize when a runner instance is returned from $animateCss
507
- * (so there is no need to call `runner.done(doneFn)` inside of your JavaScript animation code). Check the [animation code above](#usage) to see how this works.
507
+ * (so there is no need to call `runner.done(doneFn)` inside of your JavaScript animation code).
508
+ * Check the {@link ngAnimate.$animateCss#usage animation code above} to see how this works.
508
509
  *
509
510
  * @param {DOMElement} element the element that will be animated
510
511
  * @param {object} options the animation-related options that will be applied during the animation
@@ -3020,7 +3021,7 @@ var $$AnimationProvider = ['$animateProvider', function($animateProvider) {
3020
3021
  * opacity:0;
3021
3022
  * }
3022
3023
  *
3023
- * /* The starting CSS styles for the enter animation */
3024
+ * /* The finishing CSS styles for the enter animation */
3024
3025
  * .fade.ng-enter.ng-enter-active {
3025
3026
  * opacity:1;
3026
3027
  * }
@@ -3275,7 +3276,7 @@ var $$AnimationProvider = ['$animateProvider', function($animateProvider) {
3275
3276
  * ## CSS + JS Animations Together
3276
3277
  *
3277
3278
  * AngularJS 1.4 and higher has taken steps to make the amalgamation of CSS and JS animations more flexible. However, unlike earlier versions of Angular,
3278
- * defining CSS and JS animations to work off of the same CSS class will not work anymore. Therefore example below will only result in **JS animations taking
3279
+ * defining CSS and JS animations to work off of the same CSS class will not work anymore. Therefore the example below will only result in **JS animations taking
3279
3280
  * charge of the animation**:
3280
3281
  *
3281
3282
  * ```html
@@ -3304,8 +3305,8 @@ var $$AnimationProvider = ['$animateProvider', function($animateProvider) {
3304
3305
  * }
3305
3306
  * ```
3306
3307
  *
3307
- * Does this mean that CSS and JS animations cannot be used together? Do JS-based animations always have higher priority? We can suppliment for the
3308
- * lack of CSS animations by making use of the `$animateCss` service to trigger our own tweaked-out, CSS-based animations directly from
3308
+ * Does this mean that CSS and JS animations cannot be used together? Do JS-based animations always have higher priority? We can make up for the
3309
+ * lack of CSS animations by using the `$animateCss` service to trigger our own tweaked-out, CSS-based animations directly from
3309
3310
  * our own JS-based animation code:
3310
3311
  *
3311
3312
  * ```js
@@ -3603,7 +3604,7 @@ var $$AnimationProvider = ['$animateProvider', function($animateProvider) {
3603
3604
  * ngModule.directive('greetingBox', ['$animate', function($animate) {
3604
3605
  * return function(scope, element, attrs) {
3605
3606
  * attrs.$observe('active', function(value) {
3606
- * value ? $animate.addClass(element, 'on') ? $animate.removeClass(element, 'on');
3607
+ * value ? $animate.addClass(element, 'on') : $animate.removeClass(element, 'on');
3607
3608
  * });
3608
3609
  * });
3609
3610
  * }]);
@@ -3614,7 +3615,7 @@ var $$AnimationProvider = ['$animateProvider', function($animateProvider) {
3614
3615
  *
3615
3616
  * ```css
3616
3617
  * /* normally we would create a CSS class to reference on the element */
3617
- * [greeting-box].on { transition:0.5s linear all; background:green; color:white; }
3618
+ * greeting-box.on { transition:0.5s linear all; background:green; color:white; }
3618
3619
  * ```
3619
3620
  *
3620
3621
  * The `$animate` service contains a variety of other methods like `enter`, `leave`, `animate` and `setClass`. To learn more about what's
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -19,8 +19,8 @@
19
19
  *
20
20
  * ## Usage
21
21
  *
22
- * For ngAria to do its magic, simply include the module as a dependency. The directives supported
23
- * by ngAria are:
22
+ * For ngAria to do its magic, simply include the module `ngAria` as a dependency. The following
23
+ * directives are supported:
24
24
  * `ngModel`, `ngDisabled`, `ngShow`, `ngHide`, `ngClick`, `ngDblClick`, and `ngMessages`.
25
25
  *
26
26
  * Below is a more detailed breakdown of the attributes handled by ngAria:
@@ -88,7 +88,8 @@ function $AriaProvider() {
88
88
  ariaMultiline: true,
89
89
  ariaValue: true,
90
90
  tabindex: true,
91
- bindKeypress: true
91
+ bindKeypress: true,
92
+ bindRoleForClick: true
92
93
  };
93
94
 
94
95
  /**
@@ -107,6 +108,8 @@ function $AriaProvider() {
107
108
  * - **tabindex** – `{boolean}` – Enables/disables tabindex tags
108
109
  * - **bindKeypress** – `{boolean}` – Enables/disables keypress event binding on `<div>` and
109
110
  * `<li>` elements with ng-click
111
+ * - **bindRoleForClick** – `{boolean}` – Adds role=button to non-interactive elements like `div`
112
+ * using ng-click, making them more accessible to users of assistive technologies
110
113
  *
111
114
  * @description
112
115
  * Enables/disables various ARIA attributes
@@ -120,9 +123,8 @@ function $AriaProvider() {
120
123
  var ariaCamelName = attr.$normalize(ariaAttr);
121
124
  if (config[ariaCamelName] && !attr[ariaCamelName]) {
122
125
  scope.$watch(attr[attrName], function(boolVal) {
123
- if (negate) {
124
- boolVal = !boolVal;
125
- }
126
+ // ensure boolean value
127
+ boolVal = negate ? !boolVal : !!boolVal;
126
128
  elem.attr(ariaAttr, boolVal);
127
129
  });
128
130
  }
@@ -270,13 +272,23 @@ ngAriaModule.directive('ngShow', ['$aria', function($aria) {
270
272
  elem.attr('role', 'slider');
271
273
  }
272
274
  if ($aria.config('ariaValue')) {
273
- if (attr.min && !elem.attr('aria-valuemin')) {
274
- elem.attr('aria-valuemin', attr.min);
275
+ var needsAriaValuemin = !elem.attr('aria-valuemin') &&
276
+ (attr.hasOwnProperty('min') || attr.hasOwnProperty('ngMin'));
277
+ var needsAriaValuemax = !elem.attr('aria-valuemax') &&
278
+ (attr.hasOwnProperty('max') || attr.hasOwnProperty('ngMax'));
279
+ var needsAriaValuenow = !elem.attr('aria-valuenow');
280
+
281
+ if (needsAriaValuemin) {
282
+ attr.$observe('min', function ngAriaValueMinReaction(newVal) {
283
+ elem.attr('aria-valuemin', newVal);
284
+ });
275
285
  }
276
- if (attr.max && !elem.attr('aria-valuemax')) {
277
- elem.attr('aria-valuemax', attr.max);
286
+ if (needsAriaValuemax) {
287
+ attr.$observe('max', function ngAriaValueMinReaction(newVal) {
288
+ elem.attr('aria-valuemax', newVal);
289
+ });
278
290
  }
279
- if (!elem.attr('aria-valuenow')) {
291
+ if (needsAriaValuenow) {
280
292
  scope.$watch(ngAriaWatchModelValue, function ngAriaValueNowReaction(newVal) {
281
293
  elem.attr('aria-valuenow', newVal);
282
294
  });
@@ -342,7 +354,10 @@ ngAriaModule.directive('ngShow', ['$aria', function($aria) {
342
354
  return true;
343
355
  }
344
356
  }
345
- if (!elem.attr('role') && !isNodeOneOf(elem, nodeBlackList)) {
357
+
358
+ if ($aria.config('bindRoleForClick')
359
+ && !elem.attr('role')
360
+ && !isNodeOneOf(elem, nodeBlackList)) {
346
361
  elem.attr('role', 'button');
347
362
  }
348
363
 
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -17,8 +17,7 @@
17
17
  *
18
18
  * <div doc-module-components="ngCookies"></div>
19
19
  *
20
- * See {@link ngCookies.$cookies `$cookies`} and
21
- * {@link ngCookies.$cookieStore `$cookieStore`} for usage.
20
+ * See {@link ngCookies.$cookies `$cookies`} for usage.
22
21
  */
23
22
 
24
23
 
@@ -48,7 +47,7 @@ angular.module('ngCookies', ['ng']).
48
47
  * or a Date object indicating the exact date/time this cookie will expire.
49
48
  * - **secure** - `{boolean}` - The cookie will be available only in secured connection.
50
49
  *
51
- * Note: by default the address that appears in your <base> tag will be used as path.
50
+ * Note: by default the address that appears in your `<base>` tag will be used as path.
52
51
  * This is import so that cookies will be visible for all routes in case html5mode is enabled
53
52
  *
54
53
  **/
@@ -65,9 +64,11 @@ angular.module('ngCookies', ['ng']).
65
64
  * @description
66
65
  * Provides read/write access to browser's cookies.
67
66
  *
68
- * BREAKING CHANGE: `$cookies` no longer exposes properties that represent the
69
- * current browser cookie values. Now you must use the get/put/remove/etc. methods
70
- * as described below.
67
+ * <div class="alert alert-info">
68
+ * Up until Angular 1.3, `$cookies` exposed properties that represented the
69
+ * current browser cookie values. In version 1.4, this behavior has changed, and
70
+ * `$cookies` now provides a standard api of getters, setters etc.
71
+ * </div>
71
72
  *
72
73
  * Requires the {@link ngCookies `ngCookies`} module to be installed.
73
74
  *
@@ -192,7 +193,7 @@ angular.module('ngCookies').
192
193
  * Requires the {@link ngCookies `ngCookies`} module to be installed.
193
194
  *
194
195
  * <div class="alert alert-danger">
195
- * **Note:** The $cookieStore service is deprecated.
196
+ * **Note:** The $cookieStore service is **deprecated**.
196
197
  * Please use the {@link ngCookies.$cookies `$cookies`} service instead.
197
198
  * </div>
198
199
  *
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -58,7 +58,7 @@ function minErr(module, ErrorConstructor) {
58
58
  return match;
59
59
  });
60
60
 
61
- message += '\nhttp://errors.angularjs.org/1.4.0/' +
61
+ message += '\nhttp://errors.angularjs.org/1.4.2/' +
62
62
  (module ? module + '/' : '') + code;
63
63
 
64
64
  for (i = SKIP_INDEXES, paramPrefix = '?'; i < templateArgs.length; i++, paramPrefix = '&') {
@@ -216,7 +216,7 @@ function setupModuleLoader(window) {
216
216
  * @description
217
217
  * See {@link auto.$provide#provider $provide.provider()}.
218
218
  */
219
- provider: invokeLater('$provide', 'provider'),
219
+ provider: invokeLaterAndSetModuleName('$provide', 'provider'),
220
220
 
221
221
  /**
222
222
  * @ngdoc method
@@ -227,7 +227,7 @@ function setupModuleLoader(window) {
227
227
  * @description
228
228
  * See {@link auto.$provide#factory $provide.factory()}.
229
229
  */
230
- factory: invokeLater('$provide', 'factory'),
230
+ factory: invokeLaterAndSetModuleName('$provide', 'factory'),
231
231
 
232
232
  /**
233
233
  * @ngdoc method
@@ -238,7 +238,7 @@ function setupModuleLoader(window) {
238
238
  * @description
239
239
  * See {@link auto.$provide#service $provide.service()}.
240
240
  */
241
- service: invokeLater('$provide', 'service'),
241
+ service: invokeLaterAndSetModuleName('$provide', 'service'),
242
242
 
243
243
  /**
244
244
  * @ngdoc method
@@ -273,7 +273,7 @@ function setupModuleLoader(window) {
273
273
  * @description
274
274
  * See {@link auto.$provide#decorator $provide.decorator()}.
275
275
  */
276
- decorator: invokeLater('$provide', 'decorator'),
276
+ decorator: invokeLaterAndSetModuleName('$provide', 'decorator'),
277
277
 
278
278
  /**
279
279
  * @ngdoc method
@@ -307,7 +307,7 @@ function setupModuleLoader(window) {
307
307
  * See {@link ng.$animateProvider#register $animateProvider.register()} and
308
308
  * {@link ngAnimate ngAnimate module} for more information.
309
309
  */
310
- animation: invokeLater('$animateProvider', 'register'),
310
+ animation: invokeLaterAndSetModuleName('$animateProvider', 'register'),
311
311
 
312
312
  /**
313
313
  * @ngdoc method
@@ -325,7 +325,7 @@ function setupModuleLoader(window) {
325
325
  * (`myapp_subsection_filterx`).
326
326
  * </div>
327
327
  */
328
- filter: invokeLater('$filterProvider', 'register'),
328
+ filter: invokeLaterAndSetModuleName('$filterProvider', 'register'),
329
329
 
330
330
  /**
331
331
  * @ngdoc method
@@ -337,7 +337,7 @@ function setupModuleLoader(window) {
337
337
  * @description
338
338
  * See {@link ng.$controllerProvider#register $controllerProvider.register()}.
339
339
  */
340
- controller: invokeLater('$controllerProvider', 'register'),
340
+ controller: invokeLaterAndSetModuleName('$controllerProvider', 'register'),
341
341
 
342
342
  /**
343
343
  * @ngdoc method
@@ -350,7 +350,7 @@ function setupModuleLoader(window) {
350
350
  * @description
351
351
  * See {@link ng.$compileProvider#directive $compileProvider.directive()}.
352
352
  */
353
- directive: invokeLater('$compileProvider', 'directive'),
353
+ directive: invokeLaterAndSetModuleName('$compileProvider', 'directive'),
354
354
 
355
355
  /**
356
356
  * @ngdoc method
@@ -400,6 +400,19 @@ function setupModuleLoader(window) {
400
400
  return moduleInstance;
401
401
  };
402
402
  }
403
+
404
+ /**
405
+ * @param {string} provider
406
+ * @param {string} method
407
+ * @returns {angular.Module}
408
+ */
409
+ function invokeLaterAndSetModuleName(provider, method) {
410
+ return function(recipeName, factoryFunction) {
411
+ if (factoryFunction && isFunction(factoryFunction)) factoryFunction.$$moduleName = name;
412
+ invokeQueue.push([provider, method, arguments]);
413
+ return moduleInstance;
414
+ };
415
+ }
403
416
  });
404
417
  };
405
418
  });
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -56,7 +56,7 @@ var jqLite = angular.element;
56
56
  *
57
57
  * ```javascript
58
58
  * <!-- keep in mind that ngModel automatically sets these error flags -->
59
- * myField.$error = { minlength : true, required : false };
59
+ * myField.$error = { minlength : true, required : true };
60
60
  * ```
61
61
  *
62
62
  * Then the `required` message will be displayed first. When required is false then the `minlength` message
@@ -256,7 +256,7 @@ angular.module('ngMessages', [])
256
256
  *
257
257
  * @description
258
258
  * `ngMessages` is a directive that is designed to show and hide messages based on the state
259
- * of a key/value object that it listens on. The directive itself compliments error message
259
+ * of a key/value object that it listens on. The directive itself complements error message
260
260
  * reporting with the `ngModel` $error object (which stores a key/value state of validation errors).
261
261
  *
262
262
  * `ngMessages` manages the state of internal messages within its container element. The internal
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -1090,7 +1090,7 @@ angular.mock.dump = function(object) {
1090
1090
  $httpBackend.flush();
1091
1091
 
1092
1092
  $httpBackend.expectPOST('/add-msg.py', undefined, function(headers) {
1093
- // check if the header was send, if it wasn't the expectation won't
1093
+ // check if the header was sent, if it wasn't the expectation won't
1094
1094
  // match the request and the test will fail
1095
1095
  return headers['Authorization'] == 'xxx';
1096
1096
  }).respond(201, '');
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -214,7 +214,8 @@ function shallowClearAndCopy(src, dst) {
214
214
  * - non-GET instance actions: `instance.$action([parameters], [success], [error])`
215
215
  *
216
216
  *
217
- * Success callback is called with (value, responseHeaders) arguments. Error callback is called
217
+ * Success callback is called with (value, responseHeaders) arguments, where the value is
218
+ * the populated resource instance or collection object. The error callback is called
218
219
  * with (httpResponse) argument.
219
220
  *
220
221
  * Class actions return empty instance (with additional properties below).
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -596,9 +596,8 @@ function $RouteProvider() {
596
596
  if (angular.isFunction(templateUrl)) {
597
597
  templateUrl = templateUrl(nextRoute.params);
598
598
  }
599
- templateUrl = $sce.getTrustedResourceUrl(templateUrl);
600
599
  if (angular.isDefined(templateUrl)) {
601
- nextRoute.loadedTemplateUrl = templateUrl;
600
+ nextRoute.loadedTemplateUrl = $sce.valueOf(templateUrl);
602
601
  template = $templateRequest(templateUrl);
603
602
  }
604
603
  }
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.4.0
2
+ * @license AngularJS v1.4.2
3
3
  * (c) 2010-2015 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -233,7 +233,7 @@ var uriAttrs = makeMap("background,cite,href,longdesc,src,usemap,xlink:href");
233
233
  var htmlAttrs = makeMap('abbr,align,alt,axis,bgcolor,border,cellpadding,cellspacing,class,clear,' +
234
234
  'color,cols,colspan,compact,coords,dir,face,headers,height,hreflang,hspace,' +
235
235
  'ismap,lang,language,nohref,nowrap,rel,rev,rows,rowspan,rules,' +
236
- 'scope,scrolling,shape,size,span,start,summary,target,title,type,' +
236
+ 'scope,scrolling,shape,size,span,start,summary,tabindex,target,title,type,' +
237
237
  'valign,value,vspace,width');
238
238
 
239
239
  // SVG attributes (without "id" and "name" attributes)
@@ -631,8 +631,8 @@ angular.module('ngSanitize', []).provider('$sanitize', $SanitizeProvider);
631
631
  */
632
632
  angular.module('ngSanitize').filter('linky', ['$sanitize', function($sanitize) {
633
633
  var LINKY_URL_REGEXP =
634
- /((ftp|https?):\/\/|(www\.)|(mailto:)?[A-Za-z0-9._%+-]+@)\S*[^\s.;,(){}<>"”’]/,
635
- MAILTO_REGEXP = /^mailto:/;
634
+ /((ftp|https?):\/\/|(www\.)|(mailto:)?[A-Za-z0-9._%+-]+@)\S*[^\s.;,(){}<>"”’]/i,
635
+ MAILTO_REGEXP = /^mailto:/i;
636
636
 
637
637
  return function(text, target) {
638
638
  if (!text) return text;
@@ -9190,7 +9190,7 @@ return jQuery;
9190
9190
  }));
9191
9191
 
9192
9192
  /**
9193
- * @license AngularJS v1.4.0
9193
+ * @license AngularJS v1.4.2
9194
9194
  * (c) 2010-2015 Google, Inc. http://angularjs.org
9195
9195
  * License: MIT
9196
9196
  */
@@ -9249,7 +9249,7 @@ function minErr(module, ErrorConstructor) {
9249
9249
  return match;
9250
9250
  });
9251
9251
 
9252
- message += '\nhttp://errors.angularjs.org/1.4.0/' +
9252
+ message += '\nhttp://errors.angularjs.org/1.4.2/' +
9253
9253
  (module ? module + '/' : '') + code;
9254
9254
 
9255
9255
  for (i = SKIP_INDEXES, paramPrefix = '?'; i < templateArgs.length; i++, paramPrefix = '&') {
@@ -9613,8 +9613,12 @@ function baseExtend(dst, objs, deep) {
9613
9613
  var src = obj[key];
9614
9614
 
9615
9615
  if (deep && isObject(src)) {
9616
- if (!isObject(dst[key])) dst[key] = isArray(src) ? [] : {};
9617
- baseExtend(dst[key], [src], true);
9616
+ if (isDate(src)) {
9617
+ dst[key] = new Date(src.valueOf());
9618
+ } else {
9619
+ if (!isObject(dst[key])) dst[key] = isArray(src) ? [] : {};
9620
+ baseExtend(dst[key], [src], true);
9621
+ }
9618
9622
  } else {
9619
9623
  dst[key] = src;
9620
9624
  }
@@ -9725,6 +9729,11 @@ identity.$inject = [];
9725
9729
 
9726
9730
  function valueFn(value) {return function() {return value;};}
9727
9731
 
9732
+ function hasCustomToString(obj) {
9733
+ return isFunction(obj.toString) && obj.toString !== Object.prototype.toString;
9734
+ }
9735
+
9736
+
9728
9737
  /**
9729
9738
  * @ngdoc function
9730
9739
  * @name angular.isUndefined
@@ -10056,9 +10065,18 @@ function copy(source, destination, stackSource, stackDest) {
10056
10065
 
10057
10066
  if (!destination) {
10058
10067
  destination = source;
10059
- if (source) {
10068
+ if (isObject(source)) {
10069
+ var index;
10070
+ if (stackSource && (index = stackSource.indexOf(source)) !== -1) {
10071
+ return stackDest[index];
10072
+ }
10073
+
10074
+ // TypedArray, Date and RegExp have specific copy functionality and must be
10075
+ // pushed onto the stack before returning.
10076
+ // Array and other objects create the base object and recurse to copy child
10077
+ // objects. The array/object will be pushed onto the stack when recursed.
10060
10078
  if (isArray(source)) {
10061
- destination = copy(source, [], stackSource, stackDest);
10079
+ return copy(source, [], stackSource, stackDest);
10062
10080
  } else if (isTypedArray(source)) {
10063
10081
  destination = new source.constructor(source);
10064
10082
  } else if (isDate(source)) {
@@ -10066,9 +10084,14 @@ function copy(source, destination, stackSource, stackDest) {
10066
10084
  } else if (isRegExp(source)) {
10067
10085
  destination = new RegExp(source.source, source.toString().match(/[^\/]*$/)[0]);
10068
10086
  destination.lastIndex = source.lastIndex;
10069
- } else if (isObject(source)) {
10087
+ } else {
10070
10088
  var emptyObject = Object.create(getPrototypeOf(source));
10071
- destination = copy(source, emptyObject, stackSource, stackDest);
10089
+ return copy(source, emptyObject, stackSource, stackDest);
10090
+ }
10091
+
10092
+ if (stackDest) {
10093
+ stackSource.push(source);
10094
+ stackDest.push(destination);
10072
10095
  }
10073
10096
  }
10074
10097
  } else {
@@ -10079,9 +10102,6 @@ function copy(source, destination, stackSource, stackDest) {
10079
10102
  stackDest = stackDest || [];
10080
10103
 
10081
10104
  if (isObject(source)) {
10082
- var index = stackSource.indexOf(source);
10083
- if (index !== -1) return stackDest[index];
10084
-
10085
10105
  stackSource.push(source);
10086
10106
  stackDest.push(destination);
10087
10107
  }
@@ -10090,12 +10110,7 @@ function copy(source, destination, stackSource, stackDest) {
10090
10110
  if (isArray(source)) {
10091
10111
  destination.length = 0;
10092
10112
  for (var i = 0; i < source.length; i++) {
10093
- result = copy(source[i], null, stackSource, stackDest);
10094
- if (isObject(source[i])) {
10095
- stackSource.push(source[i]);
10096
- stackDest.push(result);
10097
- }
10098
- destination.push(result);
10113
+ destination.push(copy(source[i], null, stackSource, stackDest));
10099
10114
  }
10100
10115
  } else {
10101
10116
  var h = destination.$$hashKey;
@@ -10109,20 +10124,20 @@ function copy(source, destination, stackSource, stackDest) {
10109
10124
  if (isBlankObject(source)) {
10110
10125
  // createMap() fast path --- Safe to avoid hasOwnProperty check because prototype chain is empty
10111
10126
  for (key in source) {
10112
- putValue(key, source[key], destination, stackSource, stackDest);
10127
+ destination[key] = copy(source[key], null, stackSource, stackDest);
10113
10128
  }
10114
10129
  } else if (source && typeof source.hasOwnProperty === 'function') {
10115
10130
  // Slow path, which must rely on hasOwnProperty
10116
10131
  for (key in source) {
10117
10132
  if (source.hasOwnProperty(key)) {
10118
- putValue(key, source[key], destination, stackSource, stackDest);
10133
+ destination[key] = copy(source[key], null, stackSource, stackDest);
10119
10134
  }
10120
10135
  }
10121
10136
  } else {
10122
10137
  // Slowest path --- hasOwnProperty can't be called as a method
10123
10138
  for (key in source) {
10124
10139
  if (hasOwnProperty.call(source, key)) {
10125
- putValue(key, source[key], destination, stackSource, stackDest);
10140
+ destination[key] = copy(source[key], null, stackSource, stackDest);
10126
10141
  }
10127
10142
  }
10128
10143
  }
@@ -10130,16 +10145,6 @@ function copy(source, destination, stackSource, stackDest) {
10130
10145
  }
10131
10146
  }
10132
10147
  return destination;
10133
-
10134
- function putValue(key, val, destination, stackSource, stackDest) {
10135
- // No context allocation, trivial outer scope, easily inlined
10136
- var result = copy(val, null, stackSource, stackDest);
10137
- if (isObject(val)) {
10138
- stackSource.push(val);
10139
- stackDest.push(result);
10140
- }
10141
- destination[key] = result;
10142
- }
10143
10148
  }
10144
10149
 
10145
10150
  /**
@@ -11197,7 +11202,7 @@ function setupModuleLoader(window) {
11197
11202
  * @description
11198
11203
  * See {@link auto.$provide#provider $provide.provider()}.
11199
11204
  */
11200
- provider: invokeLater('$provide', 'provider'),
11205
+ provider: invokeLaterAndSetModuleName('$provide', 'provider'),
11201
11206
 
11202
11207
  /**
11203
11208
  * @ngdoc method
@@ -11208,7 +11213,7 @@ function setupModuleLoader(window) {
11208
11213
  * @description
11209
11214
  * See {@link auto.$provide#factory $provide.factory()}.
11210
11215
  */
11211
- factory: invokeLater('$provide', 'factory'),
11216
+ factory: invokeLaterAndSetModuleName('$provide', 'factory'),
11212
11217
 
11213
11218
  /**
11214
11219
  * @ngdoc method
@@ -11219,7 +11224,7 @@ function setupModuleLoader(window) {
11219
11224
  * @description
11220
11225
  * See {@link auto.$provide#service $provide.service()}.
11221
11226
  */
11222
- service: invokeLater('$provide', 'service'),
11227
+ service: invokeLaterAndSetModuleName('$provide', 'service'),
11223
11228
 
11224
11229
  /**
11225
11230
  * @ngdoc method
@@ -11254,7 +11259,7 @@ function setupModuleLoader(window) {
11254
11259
  * @description
11255
11260
  * See {@link auto.$provide#decorator $provide.decorator()}.
11256
11261
  */
11257
- decorator: invokeLater('$provide', 'decorator'),
11262
+ decorator: invokeLaterAndSetModuleName('$provide', 'decorator'),
11258
11263
 
11259
11264
  /**
11260
11265
  * @ngdoc method
@@ -11288,7 +11293,7 @@ function setupModuleLoader(window) {
11288
11293
  * See {@link ng.$animateProvider#register $animateProvider.register()} and
11289
11294
  * {@link ngAnimate ngAnimate module} for more information.
11290
11295
  */
11291
- animation: invokeLater('$animateProvider', 'register'),
11296
+ animation: invokeLaterAndSetModuleName('$animateProvider', 'register'),
11292
11297
 
11293
11298
  /**
11294
11299
  * @ngdoc method
@@ -11306,7 +11311,7 @@ function setupModuleLoader(window) {
11306
11311
  * (`myapp_subsection_filterx`).
11307
11312
  * </div>
11308
11313
  */
11309
- filter: invokeLater('$filterProvider', 'register'),
11314
+ filter: invokeLaterAndSetModuleName('$filterProvider', 'register'),
11310
11315
 
11311
11316
  /**
11312
11317
  * @ngdoc method
@@ -11318,7 +11323,7 @@ function setupModuleLoader(window) {
11318
11323
  * @description
11319
11324
  * See {@link ng.$controllerProvider#register $controllerProvider.register()}.
11320
11325
  */
11321
- controller: invokeLater('$controllerProvider', 'register'),
11326
+ controller: invokeLaterAndSetModuleName('$controllerProvider', 'register'),
11322
11327
 
11323
11328
  /**
11324
11329
  * @ngdoc method
@@ -11331,7 +11336,7 @@ function setupModuleLoader(window) {
11331
11336
  * @description
11332
11337
  * See {@link ng.$compileProvider#directive $compileProvider.directive()}.
11333
11338
  */
11334
- directive: invokeLater('$compileProvider', 'directive'),
11339
+ directive: invokeLaterAndSetModuleName('$compileProvider', 'directive'),
11335
11340
 
11336
11341
  /**
11337
11342
  * @ngdoc method
@@ -11381,6 +11386,19 @@ function setupModuleLoader(window) {
11381
11386
  return moduleInstance;
11382
11387
  };
11383
11388
  }
11389
+
11390
+ /**
11391
+ * @param {string} provider
11392
+ * @param {string} method
11393
+ * @returns {angular.Module}
11394
+ */
11395
+ function invokeLaterAndSetModuleName(provider, method) {
11396
+ return function(recipeName, factoryFunction) {
11397
+ if (factoryFunction && isFunction(factoryFunction)) factoryFunction.$$moduleName = name;
11398
+ invokeQueue.push([provider, method, arguments]);
11399
+ return moduleInstance;
11400
+ };
11401
+ }
11384
11402
  });
11385
11403
  };
11386
11404
  });
@@ -11524,11 +11542,11 @@ function toDebugString(obj) {
11524
11542
  * - `codeName` – `{string}` – Code name of the release, such as "jiggling-armfat".
11525
11543
  */
11526
11544
  var version = {
11527
- full: '1.4.0', // all of these placeholder strings will be replaced by grunt's
11545
+ full: '1.4.2', // all of these placeholder strings will be replaced by grunt's
11528
11546
  major: 1, // package task
11529
11547
  minor: 4,
11530
- dot: 0,
11531
- codeName: 'jaracimrman-existence'
11548
+ dot: 2,
11549
+ codeName: 'nebular-readjustment'
11532
11550
  };
11533
11551
 
11534
11552
 
@@ -11854,6 +11872,13 @@ function jqLiteAcceptsData(node) {
11854
11872
  return nodeType === NODE_TYPE_ELEMENT || !nodeType || nodeType === NODE_TYPE_DOCUMENT;
11855
11873
  }
11856
11874
 
11875
+ function jqLiteHasData(node) {
11876
+ for (var key in jqCache[node.ng339]) {
11877
+ return true;
11878
+ }
11879
+ return false;
11880
+ }
11881
+
11857
11882
  function jqLiteBuildFragment(html, context) {
11858
11883
  var tmp, tag, wrap,
11859
11884
  fragment = context.createDocumentFragment(),
@@ -12228,7 +12253,8 @@ function getAliasedAttrName(element, name) {
12228
12253
 
12229
12254
  forEach({
12230
12255
  data: jqLiteData,
12231
- removeData: jqLiteRemoveData
12256
+ removeData: jqLiteRemoveData,
12257
+ hasData: jqLiteHasData
12232
12258
  }, function(fn, name) {
12233
12259
  JQLite[name] = fn;
12234
12260
  });
@@ -13437,7 +13463,7 @@ function createInjector(modulesToLoad, strictDi) {
13437
13463
  }));
13438
13464
 
13439
13465
 
13440
- forEach(loadModules(modulesToLoad), function(fn) { instanceInjector.invoke(fn || noop); });
13466
+ forEach(loadModules(modulesToLoad), function(fn) { if (fn) instanceInjector.invoke(fn); });
13441
13467
 
13442
13468
  return instanceInjector;
13443
13469
 
@@ -14576,7 +14602,7 @@ function Browser(window, document, $log, $sniffer) {
14576
14602
 
14577
14603
  function getHash(url) {
14578
14604
  var index = url.indexOf('#');
14579
- return index === -1 ? '' : url.substr(index + 1);
14605
+ return index === -1 ? '' : url.substr(index);
14580
14606
  }
14581
14607
 
14582
14608
  /**
@@ -14660,7 +14686,7 @@ function Browser(window, document, $log, $sniffer) {
14660
14686
  // Do the assignment again so that those two variables are referentially identical.
14661
14687
  lastHistoryState = cachedState;
14662
14688
  } else {
14663
- if (!sameBase) {
14689
+ if (!sameBase || reloadLocation) {
14664
14690
  reloadLocation = url;
14665
14691
  }
14666
14692
  if (replace) {
@@ -15666,13 +15692,16 @@ function $TemplateCacheProvider() {
15666
15692
  * * `controller` - the directive's required controller instance(s) - Instances are shared
15667
15693
  * among all directives, which allows the directives to use the controllers as a communication
15668
15694
  * channel. The exact value depends on the directive's `require` property:
15695
+ * * no controller(s) required: the directive's own controller, or `undefined` if it doesn't have one
15669
15696
  * * `string`: the controller instance
15670
15697
  * * `array`: array of controller instances
15671
- * * no controller(s) required: `undefined`
15672
15698
  *
15673
15699
  * If a required controller cannot be found, and it is optional, the instance is `null`,
15674
15700
  * otherwise the {@link error:$compile:ctreq Missing Required Controller} error is thrown.
15675
15701
  *
15702
+ * Note that you can also require the directive's own controller - it will be made available like
15703
+ * like any other controller.
15704
+ *
15676
15705
  * * `transcludeFn` - A transclude linking function pre-bound to the correct transclusion scope.
15677
15706
  * This is the same as the `$transclude`
15678
15707
  * parameter of directive controllers, see there for details.
@@ -16119,6 +16148,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
16119
16148
  if (isObject(bindings.isolateScope)) {
16120
16149
  directive.$$isolateBindings = bindings.isolateScope;
16121
16150
  }
16151
+ directive.$$moduleName = directiveFactory.$$moduleName;
16122
16152
  directives.push(directive);
16123
16153
  } catch (e) {
16124
16154
  $exceptionHandler(e);
@@ -16690,8 +16720,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
16690
16720
 
16691
16721
  if (nodeLinkFn.transcludeOnThisElement) {
16692
16722
  childBoundTranscludeFn = createBoundTranscludeFn(
16693
- scope, nodeLinkFn.transclude, parentBoundTranscludeFn,
16694
- nodeLinkFn.elementTranscludeOnThisElement);
16723
+ scope, nodeLinkFn.transclude, parentBoundTranscludeFn);
16695
16724
 
16696
16725
  } else if (!nodeLinkFn.templateOnThisElement && parentBoundTranscludeFn) {
16697
16726
  childBoundTranscludeFn = parentBoundTranscludeFn;
@@ -16713,7 +16742,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
16713
16742
  }
16714
16743
  }
16715
16744
 
16716
- function createBoundTranscludeFn(scope, transcludeFn, previousBoundTranscludeFn, elementTransclusion) {
16745
+ function createBoundTranscludeFn(scope, transcludeFn, previousBoundTranscludeFn) {
16717
16746
 
16718
16747
  var boundTranscludeFn = function(transcludedScope, cloneFn, controllers, futureParentElement, containingScope) {
16719
16748
 
@@ -16812,6 +16841,13 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
16812
16841
  }
16813
16842
  break;
16814
16843
  case NODE_TYPE_TEXT: /* Text Node */
16844
+ if (msie === 11) {
16845
+ // Workaround for #11781
16846
+ while (node.parentNode && node.nextSibling && node.nextSibling.nodeType === NODE_TYPE_TEXT) {
16847
+ node.nodeValue = node.nodeValue + node.nextSibling.nodeValue;
16848
+ node.parentNode.removeChild(node.nextSibling);
16849
+ }
16850
+ }
16815
16851
  addTextInterpolateDirective(directives, node.nodeValue);
16816
16852
  break;
16817
16853
  case NODE_TYPE_COMMENT: /* Comment */
@@ -16911,7 +16947,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
16911
16947
  previousCompileContext = previousCompileContext || {};
16912
16948
 
16913
16949
  var terminalPriority = -Number.MAX_VALUE,
16914
- newScopeDirective,
16950
+ newScopeDirective = previousCompileContext.newScopeDirective,
16915
16951
  controllerDirectives = previousCompileContext.controllerDirectives,
16916
16952
  newIsolateScopeDirective = previousCompileContext.newIsolateScopeDirective,
16917
16953
  templateDirective = previousCompileContext.templateDirective,
@@ -17077,6 +17113,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17077
17113
  nodeLinkFn = compileTemplateUrl(directives.splice(i, directives.length - i), $compileNode,
17078
17114
  templateAttrs, jqCollection, hasTranscludeDirective && childTranscludeFn, preLinkFns, postLinkFns, {
17079
17115
  controllerDirectives: controllerDirectives,
17116
+ newScopeDirective: (newScopeDirective !== directive) && newScopeDirective,
17080
17117
  newIsolateScopeDirective: newIsolateScopeDirective,
17081
17118
  templateDirective: templateDirective,
17082
17119
  nonTlbTranscludeDirective: nonTlbTranscludeDirective
@@ -17104,7 +17141,6 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17104
17141
 
17105
17142
  nodeLinkFn.scope = newScopeDirective && newScopeDirective.scope === true;
17106
17143
  nodeLinkFn.transcludeOnThisElement = hasTranscludeDirective;
17107
- nodeLinkFn.elementTranscludeOnThisElement = hasElementTranscludeDirective;
17108
17144
  nodeLinkFn.templateOnThisElement = hasTemplate;
17109
17145
  nodeLinkFn.transclude = childTranscludeFn;
17110
17146
 
@@ -17265,9 +17301,12 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17265
17301
  for (i in elementControllers) {
17266
17302
  controller = elementControllers[i];
17267
17303
  var controllerResult = controller();
17304
+
17268
17305
  if (controllerResult !== controller.instance) {
17306
+ // If the controller constructor has a return value, overwrite the instance
17307
+ // from setupControllers and update the element data
17269
17308
  controller.instance = controllerResult;
17270
- $element.data('$' + directive.name + 'Controller', controllerResult);
17309
+ $element.data('$' + i + 'Controller', controllerResult);
17271
17310
  if (controller === controllerForBindings) {
17272
17311
  // Remove and re-install bindToController bindings
17273
17312
  thisLinkFn.$$destroyBindings();
@@ -17459,7 +17498,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17459
17498
 
17460
17499
  $compileNode.empty();
17461
17500
 
17462
- $templateRequest($sce.getTrustedResourceUrl(templateUrl))
17501
+ $templateRequest(templateUrl)
17463
17502
  .then(function(content) {
17464
17503
  var compileNode, tempTemplateAttrs, $template, childBoundTranscludeFn;
17465
17504
 
@@ -17567,11 +17606,18 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17567
17606
  return a.index - b.index;
17568
17607
  }
17569
17608
 
17570
-
17571
17609
  function assertNoDuplicate(what, previousDirective, directive, element) {
17610
+
17611
+ function wrapModuleNameIfDefined(moduleName) {
17612
+ return moduleName ?
17613
+ (' (module: ' + moduleName + ')') :
17614
+ '';
17615
+ }
17616
+
17572
17617
  if (previousDirective) {
17573
- throw $compileMinErr('multidir', 'Multiple directives [{0}, {1}] asking for {2} on: {3}',
17574
- previousDirective.name, directive.name, what, startingTag(element));
17618
+ throw $compileMinErr('multidir', 'Multiple directives [{0}{1}, {2}{3}] asking for {4} on: {5}',
17619
+ previousDirective.name, wrapModuleNameIfDefined(previousDirective.$$moduleName),
17620
+ directive.name, wrapModuleNameIfDefined(directive.$$moduleName), what, startingTag(element));
17575
17621
  }
17576
17622
  }
17577
17623
 
@@ -17752,26 +17798,28 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17752
17798
  var fragment = document.createDocumentFragment();
17753
17799
  fragment.appendChild(firstElementToRemove);
17754
17800
 
17755
- // Copy over user data (that includes Angular's $scope etc.). Don't copy private
17756
- // data here because there's no public interface in jQuery to do that and copying over
17757
- // event listeners (which is the main use of private data) wouldn't work anyway.
17758
- jqLite(newNode).data(jqLite(firstElementToRemove).data());
17759
-
17760
- // Remove data of the replaced element. We cannot just call .remove()
17761
- // on the element it since that would deallocate scope that is needed
17762
- // for the new node. Instead, remove the data "manually".
17763
- if (!jQuery) {
17764
- delete jqLite.cache[firstElementToRemove[jqLite.expando]];
17765
- } else {
17766
- // jQuery 2.x doesn't expose the data storage. Use jQuery.cleanData to clean up after
17767
- // the replaced element. The cleanData version monkey-patched by Angular would cause
17768
- // the scope to be trashed and we do need the very same scope to work with the new
17769
- // element. However, we cannot just cache the non-patched version and use it here as
17770
- // that would break if another library patches the method after Angular does (one
17771
- // example is jQuery UI). Instead, set a flag indicating scope destroying should be
17772
- // skipped this one time.
17773
- skipDestroyOnNextJQueryCleanData = true;
17774
- jQuery.cleanData([firstElementToRemove]);
17801
+ if (jqLite.hasData(firstElementToRemove)) {
17802
+ // Copy over user data (that includes Angular's $scope etc.). Don't copy private
17803
+ // data here because there's no public interface in jQuery to do that and copying over
17804
+ // event listeners (which is the main use of private data) wouldn't work anyway.
17805
+ jqLite(newNode).data(jqLite(firstElementToRemove).data());
17806
+
17807
+ // Remove data of the replaced element. We cannot just call .remove()
17808
+ // on the element it since that would deallocate scope that is needed
17809
+ // for the new node. Instead, remove the data "manually".
17810
+ if (!jQuery) {
17811
+ delete jqLite.cache[firstElementToRemove[jqLite.expando]];
17812
+ } else {
17813
+ // jQuery 2.x doesn't expose the data storage. Use jQuery.cleanData to clean up after
17814
+ // the replaced element. The cleanData version monkey-patched by Angular would cause
17815
+ // the scope to be trashed and we do need the very same scope to work with the new
17816
+ // element. However, we cannot just cache the non-patched version and use it here as
17817
+ // that would break if another library patches the method after Angular does (one
17818
+ // example is jQuery UI). Instead, set a flag indicating scope destroying should be
17819
+ // skipped this one time.
17820
+ skipDestroyOnNextJQueryCleanData = true;
17821
+ jQuery.cleanData([firstElementToRemove]);
17822
+ }
17775
17823
  }
17776
17824
 
17777
17825
  for (var k = 1, kk = elementsToRemove.length; k < kk; k++) {
@@ -17812,9 +17860,19 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17812
17860
  lastValue,
17813
17861
  parentGet, parentSet, compare;
17814
17862
 
17863
+ if (!hasOwnProperty.call(attrs, attrName)) {
17864
+ // In the case of user defined a binding with the same name as a method in Object.prototype but didn't set
17865
+ // the corresponding attribute. We need to make sure subsequent code won't access to the prototype function
17866
+ attrs[attrName] = undefined;
17867
+ }
17868
+
17815
17869
  switch (mode) {
17816
17870
 
17817
17871
  case '@':
17872
+ if (!attrs[attrName] && !optional) {
17873
+ destination[scopeName] = undefined;
17874
+ }
17875
+
17818
17876
  attrs.$observe(attrName, function(value) {
17819
17877
  destination[scopeName] = value;
17820
17878
  });
@@ -17831,6 +17889,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17831
17889
  return;
17832
17890
  }
17833
17891
  parentGet = $parse(attrs[attrName]);
17892
+
17834
17893
  if (parentGet.literal) {
17835
17894
  compare = equals;
17836
17895
  } else {
@@ -17869,9 +17928,6 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
17869
17928
  break;
17870
17929
 
17871
17930
  case '&':
17872
- // Don't assign Object.prototype method to scope
17873
- if (!attrs.hasOwnProperty(attrName) && optional) break;
17874
-
17875
17931
  parentGet = $parse(attrs[attrName]);
17876
17932
 
17877
17933
  // Don't assign noop to destination if expression is not valid
@@ -18272,13 +18328,17 @@ function $HttpParamSerializerProvider() {
18272
18328
  * @name $httpParamSerializer
18273
18329
  * @description
18274
18330
  *
18275
- * Default $http params serializer that converts objects to a part of a request URL
18331
+ * Default {@link $http `$http`} params serializer that converts objects to strings
18276
18332
  * according to the following rules:
18333
+ *
18277
18334
  * * `{'foo': 'bar'}` results in `foo=bar`
18278
18335
  * * `{'foo': Date.now()}` results in `foo=2015-04-01T09%3A50%3A49.262Z` (`toISOString()` and encoded representation of a Date object)
18279
18336
  * * `{'foo': ['bar', 'baz']}` results in `foo=bar&foo=baz` (repeated key for each array element)
18280
18337
  * * `{'foo': {'bar':'baz'}}` results in `foo=%7B%22bar%22%3A%22baz%22%7D"` (stringified and encoded representation of an object)
18338
+ *
18339
+ * Note that serializer will sort the request parameters alphabetically.
18281
18340
  * */
18341
+
18282
18342
  this.$get = function() {
18283
18343
  return function ngParamSerializer(params) {
18284
18344
  if (!params) return '';
@@ -18305,7 +18365,43 @@ function $HttpParamSerializerJQLikeProvider() {
18305
18365
  * @name $httpParamSerializerJQLike
18306
18366
  * @description
18307
18367
  *
18308
- * Alternative $http params serializer that follows jQuery's [`param()`](http://api.jquery.com/jquery.param/) method logic.
18368
+ * Alternative {@link $http `$http`} params serializer that follows
18369
+ * jQuery's [`param()`](http://api.jquery.com/jquery.param/) method logic.
18370
+ * The serializer will also sort the params alphabetically.
18371
+ *
18372
+ * To use it for serializing `$http` request parameters, set it as the `paramSerializer` property:
18373
+ *
18374
+ * ```js
18375
+ * $http({
18376
+ * url: myUrl,
18377
+ * method: 'GET',
18378
+ * params: myParams,
18379
+ * paramSerializer: '$httpParamSerializerJQLike'
18380
+ * });
18381
+ * ```
18382
+ *
18383
+ * It is also possible to set it as the default `paramSerializer` in the
18384
+ * {@link $httpProvider#defaults `$httpProvider`}.
18385
+ *
18386
+ * Additionally, you can inject the serializer and use it explicitly, for example to serialize
18387
+ * form data for submission:
18388
+ *
18389
+ * ```js
18390
+ * .controller(function($http, $httpParamSerializerJQLike) {
18391
+ * //...
18392
+ *
18393
+ * $http({
18394
+ * url: myUrl,
18395
+ * method: 'POST',
18396
+ * data: $httpParamSerializerJQLike(myData),
18397
+ * headers: {
18398
+ * 'Content-Type': 'application/x-www-form-urlencoded'
18399
+ * }
18400
+ * });
18401
+ *
18402
+ * });
18403
+ * ```
18404
+ *
18309
18405
  * */
18310
18406
  this.$get = function() {
18311
18407
  return function jQueryLikeParamSerializer(params) {
@@ -18462,7 +18558,7 @@ function $HttpProvider() {
18462
18558
  *
18463
18559
  * - **`defaults.cache`** - {Object} - an object built with {@link ng.$cacheFactory `$cacheFactory`}
18464
18560
  * that will provide the cache for all requests who set their `cache` property to `true`.
18465
- * If you set the `default.cache = false` then only requests that specify their own custom
18561
+ * If you set the `defaults.cache = false` then only requests that specify their own custom
18466
18562
  * cache object will be cached. See {@link $http#caching $http Caching} for more information.
18467
18563
  *
18468
18564
  * - **`defaults.xsrfCookieName`** - {string} - Name of cookie containing the XSRF token.
@@ -18479,10 +18575,11 @@ function $HttpProvider() {
18479
18575
  * - **`defaults.headers.put`**
18480
18576
  * - **`defaults.headers.patch`**
18481
18577
  *
18482
- * - **`defaults.paramSerializer`** - {string|function(Object<string,string>):string} - A function used to prepare string representation
18483
- * of request parameters (specified as an object).
18484
- * If specified as string, it is interpreted as a function registered with the {@link auto.$injector $injector}.
18485
- * Defaults to {@link ng.$httpParamSerializer $httpParamSerializer}.
18578
+ *
18579
+ * - **`defaults.paramSerializer`** - `{string|function(Object<string,string>):string}` - A function
18580
+ * used to the prepare string representation of request parameters (specified as an object).
18581
+ * If specified as string, it is interpreted as a function registered with the {@link auto.$injector $injector}.
18582
+ * Defaults to {@link ng.$httpParamSerializer $httpParamSerializer}.
18486
18583
  *
18487
18584
  **/
18488
18585
  var defaults = this.defaults = {
@@ -18948,15 +19045,17 @@ function $HttpProvider() {
18948
19045
  * properties of either $httpProvider.defaults at config-time, $http.defaults at run-time,
18949
19046
  * or the per-request config object.
18950
19047
  *
19048
+ * In order to prevent collisions in environments where multiple Angular apps share the
19049
+ * same domain or subdomain, we recommend that each application uses unique cookie name.
19050
+ *
18951
19051
  *
18952
19052
  * @param {object} config Object describing the request to be made and how it should be
18953
19053
  * processed. The object has following properties:
18954
19054
  *
18955
19055
  * - **method** – `{string}` – HTTP method (e.g. 'GET', 'POST', etc)
18956
19056
  * - **url** – `{string}` – Absolute or relative URL of the resource that is being requested.
18957
- * - **params** – `{Object.<string|Object>}` – Map of strings or objects which will be turned
18958
- * to `?key1=value1&key2=value2` after the url. If the value is not a string, it will be
18959
- * JSONified.
19057
+ * - **params** – `{Object.<string|Object>}` – Map of strings or objects which will be serialized
19058
+ * with the `paramSerializer` and appended as GET parameters.
18960
19059
  * - **data** – `{string|Object}` – Data to be sent as the request message data.
18961
19060
  * - **headers** – `{Object}` – Map of strings or functions which return strings representing
18962
19061
  * HTTP headers to send to the server. If the return value of a function is null, the
@@ -18974,10 +19073,14 @@ function $HttpProvider() {
18974
19073
  * transform function or an array of such functions. The transform function takes the http
18975
19074
  * response body, headers and status and returns its transformed (typically deserialized) version.
18976
19075
  * See {@link ng.$http#overriding-the-default-transformations-per-request
18977
- * Overriding the Default Transformations}
18978
- * - **paramSerializer** - {string|function(Object<string,string>):string} - A function used to prepare string representation
18979
- * of request parameters (specified as an object).
18980
- * Is specified as string, it is interpreted as function registered in with the {$injector}.
19076
+ * Overriding the Default TransformationjqLiks}
19077
+ * - **paramSerializer** - `{string|function(Object<string,string>):string}` - A function used to
19078
+ * prepare the string representation of request parameters (specified as an object).
19079
+ * If specified as string, it is interpreted as function registered with the
19080
+ * {@link $injector $injector}, which means you can create your own serializer
19081
+ * by registering it as a {@link auto.$provide#service service}.
19082
+ * The default serializer is the {@link $httpParamSerializer $httpParamSerializer};
19083
+ * alternatively, you can use the {@link $httpParamSerializerJQLike $httpParamSerializerJQLike}
18981
19084
  * - **cache** – `{boolean|Cache}` – If true, a default $http cache will be used to cache the
18982
19085
  * GET request, otherwise if a cache instance built with
18983
19086
  * {@link ng.$cacheFactory $cacheFactory}, this cache will be used for
@@ -18988,7 +19091,7 @@ function $HttpProvider() {
18988
19091
  * XHR object. See [requests with credentials](https://developer.mozilla.org/docs/Web/HTTP/Access_control_CORS#Requests_with_credentials)
18989
19092
  * for more information.
18990
19093
  * - **responseType** - `{string}` - see
18991
- * [requestType](https://developer.mozilla.org/en-US/docs/DOM/XMLHttpRequest#responseType).
19094
+ * [XMLHttpRequest.responseType](https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest#xmlhttprequest-responsetype).
18992
19095
  *
18993
19096
  * @returns {HttpPromise} Returns a {@link ng.$q promise} object with the
18994
19097
  * standard `then` method and two http specific methods: `success` and `error`. The `then`
@@ -20471,7 +20574,7 @@ function LocationHashbangUrl(appBase, hashPrefix) {
20471
20574
  var withoutBaseUrl = beginsWith(appBase, url) || beginsWith(appBaseNoFile, url);
20472
20575
  var withoutHashUrl;
20473
20576
 
20474
- if (withoutBaseUrl.charAt(0) === '#') {
20577
+ if (!isUndefined(withoutBaseUrl) && withoutBaseUrl.charAt(0) === '#') {
20475
20578
 
20476
20579
  // The rest of the url starts with a hash so we have
20477
20580
  // got either a hashbang path or a plain hash fragment
@@ -20485,7 +20588,15 @@ function LocationHashbangUrl(appBase, hashPrefix) {
20485
20588
  // There was no hashbang path nor hash fragment:
20486
20589
  // If we are in HTML5 mode we use what is left as the path;
20487
20590
  // Otherwise we ignore what is left
20488
- withoutHashUrl = this.$$html5 ? withoutBaseUrl : '';
20591
+ if (this.$$html5) {
20592
+ withoutHashUrl = withoutBaseUrl;
20593
+ } else {
20594
+ withoutHashUrl = '';
20595
+ if (isUndefined(withoutBaseUrl)) {
20596
+ appBase = url;
20597
+ this.replace();
20598
+ }
20599
+ }
20489
20600
  }
20490
20601
 
20491
20602
  parseAppUrl(withoutHashUrl, this);
@@ -22405,8 +22516,10 @@ ASTCompiler.prototype = {
22405
22516
  nameId.name = ast.property.name;
22406
22517
  }
22407
22518
  }
22408
- recursionFn(intoId);
22519
+ }, function() {
22520
+ self.assign(intoId, 'undefined');
22409
22521
  });
22522
+ recursionFn(intoId);
22410
22523
  }, !!create);
22411
22524
  break;
22412
22525
  case AST.CallExpression:
@@ -22444,8 +22557,10 @@ ASTCompiler.prototype = {
22444
22557
  }
22445
22558
  expression = self.ensureSafeObject(expression);
22446
22559
  self.assign(intoId, expression);
22447
- recursionFn(intoId);
22560
+ }, function() {
22561
+ self.assign(intoId, 'undefined');
22448
22562
  });
22563
+ recursionFn(intoId);
22449
22564
  });
22450
22565
  }
22451
22566
  break;
@@ -23826,6 +23941,19 @@ function qFactory(nextTick, exceptionHandler) {
23826
23941
  return result.promise.then(callback, errback, progressBack);
23827
23942
  };
23828
23943
 
23944
+ /**
23945
+ * @ngdoc method
23946
+ * @name $q#resolve
23947
+ * @kind function
23948
+ *
23949
+ * @description
23950
+ * Alias of {@link ng.$q#when when} to maintain naming consistency with ES6.
23951
+ *
23952
+ * @param {*} value Value or a promise
23953
+ * @returns {Promise} Returns a promise of the passed value or promise
23954
+ */
23955
+ var resolve = when;
23956
+
23829
23957
  /**
23830
23958
  * @ngdoc method
23831
23959
  * @name $q#all
@@ -23894,6 +24022,7 @@ function qFactory(nextTick, exceptionHandler) {
23894
24022
  $Q.defer = defer;
23895
24023
  $Q.reject = reject;
23896
24024
  $Q.when = when;
24025
+ $Q.resolve = resolve;
23897
24026
  $Q.all = all;
23898
24027
 
23899
24028
  return $Q;
@@ -26538,12 +26667,14 @@ var $compileMinErr = minErr('$compile');
26538
26667
  * @name $templateRequest
26539
26668
  *
26540
26669
  * @description
26541
- * The `$templateRequest` service downloads the provided template using `$http` and, upon success,
26542
- * stores the contents inside of `$templateCache`. If the HTTP request fails or the response data
26543
- * of the HTTP request is empty, a `$compile` error will be thrown (the exception can be thwarted
26544
- * by setting the 2nd parameter of the function to true).
26545
- *
26546
- * @param {string} tpl The HTTP request template URL
26670
+ * The `$templateRequest` service runs security checks then downloads the provided template using
26671
+ * `$http` and, upon success, stores the contents inside of `$templateCache`. If the HTTP request
26672
+ * fails or the response data of the HTTP request is empty, a `$compile` error will be thrown (the
26673
+ * exception can be thwarted by setting the 2nd parameter of the function to true). Note that the
26674
+ * contents of `$templateCache` are trusted, so the call to `$sce.getTrustedUrl(tpl)` is omitted
26675
+ * when `tpl` is of type string and `$templateCache` has the matching entry.
26676
+ *
26677
+ * @param {string|TrustedResourceUrl} tpl The HTTP request template URL
26547
26678
  * @param {boolean=} ignoreRequestError Whether or not to ignore the exception when the request fails or the template is empty
26548
26679
  *
26549
26680
  * @return {Promise} a promise for the HTTP response data of the given URL.
@@ -26551,10 +26682,19 @@ var $compileMinErr = minErr('$compile');
26551
26682
  * @property {number} totalPendingRequests total amount of pending template requests being downloaded.
26552
26683
  */
26553
26684
  function $TemplateRequestProvider() {
26554
- this.$get = ['$templateCache', '$http', '$q', function($templateCache, $http, $q) {
26685
+ this.$get = ['$templateCache', '$http', '$q', '$sce', function($templateCache, $http, $q, $sce) {
26555
26686
  function handleRequestFn(tpl, ignoreRequestError) {
26556
26687
  handleRequestFn.totalPendingRequests++;
26557
26688
 
26689
+ // We consider the template cache holds only trusted templates, so
26690
+ // there's no need to go through whitelisting again for keys that already
26691
+ // are included in there. This also makes Angular accept any script
26692
+ // directive, no matter its name. However, we still need to unwrap trusted
26693
+ // types.
26694
+ if (!isString(tpl) || !$templateCache.get(tpl)) {
26695
+ tpl = $sce.getTrustedResourceUrl(tpl);
26696
+ }
26697
+
26558
26698
  var transformResponse = $http.defaults && $http.defaults.transformResponse;
26559
26699
 
26560
26700
  if (isArray(transformResponse)) {
@@ -27203,9 +27343,11 @@ function $FilterProvider($provide) {
27203
27343
  * `{name: {first: 'John', last: 'Doe'}}` will **not** be matched by `{name: 'John'}`, but
27204
27344
  * **will** be matched by `{$: 'John'}`.
27205
27345
  *
27206
- * - `function(value, index)`: A predicate function can be used to write arbitrary filters. The
27207
- * function is called for each element of `array`. The final result is an array of those
27208
- * elements that the predicate returned true for.
27346
+ * - `function(value, index, array)`: A predicate function can be used to write arbitrary filters.
27347
+ * The function is called for each element of the array, with the element, its index, and
27348
+ * the entire array itself as arguments.
27349
+ *
27350
+ * The final result is an array of those elements that the predicate returned true for.
27209
27351
  *
27210
27352
  * @param {function(actual, expected)|true|undefined} comparator Comparator which is used in
27211
27353
  * determining if the expected value (from the filter expression) and actual value (from
@@ -27330,10 +27472,6 @@ function filterFilter() {
27330
27472
  };
27331
27473
  }
27332
27474
 
27333
- function hasCustomToString(obj) {
27334
- return isFunction(obj.toString) && obj.toString !== Object.prototype.toString;
27335
- }
27336
-
27337
27475
  // Helper functions for `filterFilter`
27338
27476
  function createPredicateFn(expression, comparator, matchAgainstAnyProp) {
27339
27477
  var shouldMatchPrimitives = isObject(expression) && ('$' in expression);
@@ -27506,9 +27644,10 @@ function currencyFilter($locale) {
27506
27644
  * @description
27507
27645
  * Formats a number as text.
27508
27646
  *
27647
+ * If the input is null or undefined, it will just be returned.
27648
+ * If the input is infinite (Infinity/-Infinity) the Infinity symbol '∞' is returned.
27509
27649
  * If the input is not a number an empty string is returned.
27510
27650
  *
27511
- * If the input is an infinite (Infinity/-Infinity) the Infinity symbol '∞' is returned.
27512
27651
  *
27513
27652
  * @param {number|string} number Number to format.
27514
27653
  * @param {(number|string)=} fractionSize Number of decimal places to round the number to.
@@ -28137,7 +28276,7 @@ function limitToFilter() {
28137
28276
  * @description
28138
28277
  * Orders a specified `array` by the `expression` predicate. It is ordered alphabetically
28139
28278
  * for strings and numerically for numbers. Note: if you notice numbers are not being sorted
28140
- * correctly, make sure they are actually being saved as numbers and not strings.
28279
+ * as expected, make sure they are actually being saved as numbers and not strings.
28141
28280
  *
28142
28281
  * @param {Array} array The array to sort.
28143
28282
  * @param {function(*)|string|Array.<(function(*)|string)>=} expression A predicate to be
@@ -28212,19 +28351,40 @@ function limitToFilter() {
28212
28351
  {name:'Mike', phone:'555-4321', age:21},
28213
28352
  {name:'Adam', phone:'555-5678', age:35},
28214
28353
  {name:'Julie', phone:'555-8765', age:29}];
28215
- $scope.predicate = '-age';
28354
+ $scope.predicate = 'age';
28355
+ $scope.reverse = true;
28356
+ $scope.order = function(predicate) {
28357
+ $scope.reverse = ($scope.predicate === predicate) ? !$scope.reverse : false;
28358
+ $scope.predicate = predicate;
28359
+ };
28216
28360
  }]);
28217
28361
  </script>
28362
+ <style type="text/css">
28363
+ .sortorder:after {
28364
+ content: '\25b2';
28365
+ }
28366
+ .sortorder.reverse:after {
28367
+ content: '\25bc';
28368
+ }
28369
+ </style>
28218
28370
  <div ng-controller="ExampleController">
28219
28371
  <pre>Sorting predicate = {{predicate}}; reverse = {{reverse}}</pre>
28220
28372
  <hr/>
28221
28373
  [ <a href="" ng-click="predicate=''">unsorted</a> ]
28222
28374
  <table class="friend">
28223
28375
  <tr>
28224
- <th><a href="" ng-click="predicate = 'name'; reverse=false">Name</a>
28225
- (<a href="" ng-click="predicate = '-name'; reverse=false">^</a>)</th>
28226
- <th><a href="" ng-click="predicate = 'phone'; reverse=!reverse">Phone Number</a></th>
28227
- <th><a href="" ng-click="predicate = 'age'; reverse=!reverse">Age</a></th>
28376
+ <th>
28377
+ <a href="" ng-click="order('name')">Name</a>
28378
+ <span class="sortorder" ng-show="predicate === 'name'" ng-class="{reverse:reverse}"></span>
28379
+ </th>
28380
+ <th>
28381
+ <a href="" ng-click="order('phone')">Phone Number</a>
28382
+ <span class="sortorder" ng-show="predicate === 'phone'" ng-class="{reverse:reverse}"></span>
28383
+ </th>
28384
+ <th>
28385
+ <a href="" ng-click="order('age')">Age</a>
28386
+ <span class="sortorder" ng-show="predicate === 'age'" ng-class="{reverse:reverse}"></span>
28387
+ </th>
28228
28388
  </tr>
28229
28389
  <tr ng-repeat="friend in friends | orderBy:predicate:reverse">
28230
28390
  <td>{{friend.name}}</td>
@@ -28284,90 +28444,116 @@ function limitToFilter() {
28284
28444
  orderByFilter.$inject = ['$parse'];
28285
28445
  function orderByFilter($parse) {
28286
28446
  return function(array, sortPredicate, reverseOrder) {
28447
+
28287
28448
  if (!(isArrayLike(array))) return array;
28288
- sortPredicate = isArray(sortPredicate) ? sortPredicate : [sortPredicate];
28449
+
28450
+ if (!isArray(sortPredicate)) { sortPredicate = [sortPredicate]; }
28289
28451
  if (sortPredicate.length === 0) { sortPredicate = ['+']; }
28290
- sortPredicate = sortPredicate.map(function(predicate) {
28291
- var descending = false, get = predicate || identity;
28292
- if (isString(predicate)) {
28452
+
28453
+ var predicates = processPredicates(sortPredicate, reverseOrder);
28454
+
28455
+ // The next three lines are a version of a Swartzian Transform idiom from Perl
28456
+ // (sometimes called the Decorate-Sort-Undecorate idiom)
28457
+ // See https://en.wikipedia.org/wiki/Schwartzian_transform
28458
+ var compareValues = Array.prototype.map.call(array, getComparisonObject);
28459
+ compareValues.sort(doComparison);
28460
+ array = compareValues.map(function(item) { return item.value; });
28461
+
28462
+ return array;
28463
+
28464
+ function getComparisonObject(value, index) {
28465
+ return {
28466
+ value: value,
28467
+ predicateValues: predicates.map(function(predicate) {
28468
+ return getPredicateValue(predicate.get(value), index);
28469
+ })
28470
+ };
28471
+ }
28472
+
28473
+ function doComparison(v1, v2) {
28474
+ var result = 0;
28475
+ for (var index=0, length = predicates.length; index < length; ++index) {
28476
+ result = compare(v1.predicateValues[index], v2.predicateValues[index]) * predicates[index].descending;
28477
+ if (result) break;
28478
+ }
28479
+ return result;
28480
+ }
28481
+ };
28482
+
28483
+ function processPredicates(sortPredicate, reverseOrder) {
28484
+ reverseOrder = reverseOrder ? -1 : 1;
28485
+ return sortPredicate.map(function(predicate) {
28486
+ var descending = 1, get = identity;
28487
+
28488
+ if (isFunction(predicate)) {
28489
+ get = predicate;
28490
+ } else if (isString(predicate)) {
28293
28491
  if ((predicate.charAt(0) == '+' || predicate.charAt(0) == '-')) {
28294
- descending = predicate.charAt(0) == '-';
28492
+ descending = predicate.charAt(0) == '-' ? -1 : 1;
28295
28493
  predicate = predicate.substring(1);
28296
28494
  }
28297
- if (predicate === '') {
28298
- // Effectively no predicate was passed so we compare identity
28299
- return reverseComparator(compare, descending);
28300
- }
28301
- get = $parse(predicate);
28302
- if (get.constant) {
28303
- var key = get();
28304
- return reverseComparator(function(a, b) {
28305
- return compare(a[key], b[key]);
28306
- }, descending);
28495
+ if (predicate !== '') {
28496
+ get = $parse(predicate);
28497
+ if (get.constant) {
28498
+ var key = get();
28499
+ get = function(value) { return value[key]; };
28500
+ }
28307
28501
  }
28308
28502
  }
28309
- return reverseComparator(function(a, b) {
28310
- return compare(get(a),get(b));
28311
- }, descending);
28503
+ return { get: get, descending: descending * reverseOrder };
28312
28504
  });
28313
- return slice.call(array).sort(reverseComparator(comparator, reverseOrder));
28505
+ }
28314
28506
 
28315
- function comparator(o1, o2) {
28316
- for (var i = 0; i < sortPredicate.length; i++) {
28317
- var comp = sortPredicate[i](o1, o2);
28318
- if (comp !== 0) return comp;
28319
- }
28320
- return 0;
28321
- }
28322
- function reverseComparator(comp, descending) {
28323
- return descending
28324
- ? function(a, b) {return comp(b,a);}
28325
- : comp;
28507
+ function isPrimitive(value) {
28508
+ switch (typeof value) {
28509
+ case 'number': /* falls through */
28510
+ case 'boolean': /* falls through */
28511
+ case 'string':
28512
+ return true;
28513
+ default:
28514
+ return false;
28326
28515
  }
28516
+ }
28327
28517
 
28328
- function isPrimitive(value) {
28329
- switch (typeof value) {
28330
- case 'number': /* falls through */
28331
- case 'boolean': /* falls through */
28332
- case 'string':
28333
- return true;
28334
- default:
28335
- return false;
28336
- }
28518
+ function objectValue(value, index) {
28519
+ // If `valueOf` is a valid function use that
28520
+ if (typeof value.valueOf === 'function') {
28521
+ value = value.valueOf();
28522
+ if (isPrimitive(value)) return value;
28337
28523
  }
28338
-
28339
- function objectToString(value) {
28340
- if (value === null) return 'null';
28341
- if (typeof value.valueOf === 'function') {
28342
- value = value.valueOf();
28343
- if (isPrimitive(value)) return value;
28344
- }
28345
- if (typeof value.toString === 'function') {
28346
- value = value.toString();
28347
- if (isPrimitive(value)) return value;
28348
- }
28349
- return '';
28524
+ // If `toString` is a valid function and not the one from `Object.prototype` use that
28525
+ if (hasCustomToString(value)) {
28526
+ value = value.toString();
28527
+ if (isPrimitive(value)) return value;
28350
28528
  }
28529
+ // We have a basic object so we use the position of the object in the collection
28530
+ return index;
28531
+ }
28351
28532
 
28352
- function compare(v1, v2) {
28353
- var t1 = typeof v1;
28354
- var t2 = typeof v2;
28355
- if (t1 === t2 && t1 === "object") {
28356
- v1 = objectToString(v1);
28357
- v2 = objectToString(v2);
28358
- }
28359
- if (t1 === t2) {
28360
- if (t1 === "string") {
28361
- v1 = v1.toLowerCase();
28362
- v2 = v2.toLowerCase();
28363
- }
28364
- if (v1 === v2) return 0;
28365
- return v1 < v2 ? -1 : 1;
28366
- } else {
28367
- return t1 < t2 ? -1 : 1;
28533
+ function getPredicateValue(value, index) {
28534
+ var type = typeof value;
28535
+ if (value === null) {
28536
+ type = 'string';
28537
+ value = 'null';
28538
+ } else if (type === 'string') {
28539
+ value = value.toLowerCase();
28540
+ } else if (type === 'object') {
28541
+ value = objectValue(value, index);
28542
+ }
28543
+ return { value: value, type: type };
28544
+ }
28545
+
28546
+ function compare(v1, v2) {
28547
+ var result = 0;
28548
+ if (v1.type === v2.type) {
28549
+ if (v1.value !== v2.value) {
28550
+ result = v1.value < v2.value ? -1 : 1;
28368
28551
  }
28552
+ } else {
28553
+ result = v1.type < v2.type ? -1 : 1;
28369
28554
  }
28370
- };
28555
+ return result;
28556
+ }
28371
28557
  }
28372
28558
 
28373
28559
  function ngDirective(directive) {
@@ -28621,6 +28807,13 @@ var htmlAnchorDirective = valueFn({
28621
28807
  * @priority 100
28622
28808
  *
28623
28809
  * @description
28810
+ * Sets the `checked` attribute on the element, if the expression inside `ngChecked` is truthy.
28811
+ *
28812
+ * Note that this directive should not be used together with {@link ngModel `ngModel`},
28813
+ * as this can lead to unexpected behavior.
28814
+ *
28815
+ * ### Why do we need `ngChecked`?
28816
+ *
28624
28817
  * The HTML specification does not require browsers to preserve the values of boolean attributes
28625
28818
  * such as checked. (Their presence means true and their absence means false.)
28626
28819
  * If we put an Angular interpolation expression into such an attribute then the
@@ -28645,7 +28838,7 @@ var htmlAnchorDirective = valueFn({
28645
28838
  *
28646
28839
  * @element INPUT
28647
28840
  * @param {expression} ngChecked If the {@link guide/expression expression} is truthy,
28648
- * then special attribute "checked" will be set on the element
28841
+ * then the `checked` attribute will be set on the element
28649
28842
  */
28650
28843
 
28651
28844
 
@@ -29387,7 +29580,7 @@ var ngFormDirective = formDirectiveFactory(true);
29387
29580
  var ISO_DATE_REGEXP = /\d{4}-[01]\d-[0-3]\dT[0-2]\d:[0-5]\d:[0-5]\d\.\d+([+-][0-2]\d:[0-5]\d|Z)/;
29388
29581
  var URL_REGEXP = /^(ftp|http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%@!\-\/]))?$/;
29389
29582
  var EMAIL_REGEXP = /^[a-z0-9!#$%&'*+\/=?^_`{|}~.-]+@[a-z0-9]([a-z0-9-]*[a-z0-9])?(\.[a-z0-9]([a-z0-9-]*[a-z0-9])?)*$/i;
29390
- var NUMBER_REGEXP = /^\s*(\-|\+)?(\d+|(\d*(\.\d*)))\s*$/;
29583
+ var NUMBER_REGEXP = /^\s*(\-|\+)?(\d+|(\d*(\.\d*)))([eE][+-]?\d+)?\s*$/;
29391
29584
  var DATE_REGEXP = /^(\d{4})-(\d{2})-(\d{2})$/;
29392
29585
  var DATETIMELOCAL_REGEXP = /^(\d{4})-(\d\d)-(\d\d)T(\d\d):(\d\d)(?::(\d\d)(\.\d{1,3})?)?$/;
29393
29586
  var WEEK_REGEXP = /^(\d{4})-W(\d\d)$/;
@@ -29986,6 +30179,16 @@ var inputType = {
29986
30179
  * error docs for more information and an example of how to convert your model if necessary.
29987
30180
  * </div>
29988
30181
  *
30182
+ * ## Issues with HTML5 constraint validation
30183
+ *
30184
+ * In browsers that follow the
30185
+ * [HTML5 specification](https://html.spec.whatwg.org/multipage/forms.html#number-state-%28type=number%29),
30186
+ * `input[number]` does not work as expected with {@link ngModelOptions `ngModelOptions.allowInvalid`}.
30187
+ * If a non-number is entered in the input, the browser will report the value as an empty string,
30188
+ * which means the view / model values in `ngModel` and subsequently the scope value
30189
+ * will also be an empty string.
30190
+ *
30191
+ *
29989
30192
  * @param {string} ngModel Assignable angular expression to data-bind to.
29990
30193
  * @param {string=} name Property name of the form under which the control is published.
29991
30194
  * @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
@@ -30277,12 +30480,15 @@ var inputType = {
30277
30480
  * HTML radio button.
30278
30481
  *
30279
30482
  * @param {string} ngModel Assignable angular expression to data-bind to.
30280
- * @param {string} value The value to which the expression should be set when selected.
30483
+ * @param {string} value The value to which the `ngModel` expression should be set when selected.
30484
+ * Note that `value` only supports `string` values, i.e. the scope model needs to be a string,
30485
+ * too. Use `ngValue` if you need complex models (`number`, `object`, ...).
30281
30486
  * @param {string=} name Property name of the form under which the control is published.
30282
30487
  * @param {string=} ngChange Angular expression to be executed when input changes due to user
30283
30488
  * interaction with the input element.
30284
- * @param {string} ngValue Angular expression which sets the value to which the expression should
30285
- * be set when selected.
30489
+ * @param {string} ngValue Angular expression to which `ngModel` will be be set when the radio
30490
+ * is selected. Should be used instead of the `value` attribute if you need
30491
+ * a non-string `ngModel` (`boolean`, `array`, ...).
30286
30492
  *
30287
30493
  * @example
30288
30494
  <example name="radio-input-directive" module="radioExample">
@@ -31522,7 +31728,7 @@ function classDirective(name, selector) {
31522
31728
  * @example Example that demonstrates basic bindings via ngClass directive.
31523
31729
  <example>
31524
31730
  <file name="index.html">
31525
- <p ng-class="{strike: deleted, bold: important, red: error}">Map Syntax Example</p>
31731
+ <p ng-class="{strike: deleted, bold: important, 'has-error': error}">Map Syntax Example</p>
31526
31732
  <label>
31527
31733
  <input type="checkbox" ng-model="deleted">
31528
31734
  deleted (apply "strike" class)
@@ -31533,7 +31739,7 @@ function classDirective(name, selector) {
31533
31739
  </label><br>
31534
31740
  <label>
31535
31741
  <input type="checkbox" ng-model="error">
31536
- error (apply "red" class)
31742
+ error (apply "has-error" class)
31537
31743
  </label>
31538
31744
  <hr>
31539
31745
  <p ng-class="style">Using String Syntax</p>
@@ -31562,6 +31768,10 @@ function classDirective(name, selector) {
31562
31768
  .red {
31563
31769
  color: red;
31564
31770
  }
31771
+ .has-error {
31772
+ color: red;
31773
+ background-color: yellow;
31774
+ }
31565
31775
  .orange {
31566
31776
  color: orange;
31567
31777
  }
@@ -31572,13 +31782,13 @@ function classDirective(name, selector) {
31572
31782
  it('should let you toggle the class', function() {
31573
31783
 
31574
31784
  expect(ps.first().getAttribute('class')).not.toMatch(/bold/);
31575
- expect(ps.first().getAttribute('class')).not.toMatch(/red/);
31785
+ expect(ps.first().getAttribute('class')).not.toMatch(/has-error/);
31576
31786
 
31577
31787
  element(by.model('important')).click();
31578
31788
  expect(ps.first().getAttribute('class')).toMatch(/bold/);
31579
31789
 
31580
31790
  element(by.model('error')).click();
31581
- expect(ps.first().getAttribute('class')).toMatch(/red/);
31791
+ expect(ps.first().getAttribute('class')).toMatch(/has-error/);
31582
31792
  });
31583
31793
 
31584
31794
  it('should let you toggle string example', function() {
@@ -32706,6 +32916,7 @@ forEach(
32706
32916
  * @ngdoc directive
32707
32917
  * @name ngIf
32708
32918
  * @restrict A
32919
+ * @multiElement
32709
32920
  *
32710
32921
  * @description
32711
32922
  * The `ngIf` directive removes or recreates a portion of the DOM tree based on an
@@ -33004,8 +33215,8 @@ var ngIfDirective = ['$animate', function($animate) {
33004
33215
  * @param {Object} angularEvent Synthetic event object.
33005
33216
  * @param {String} src URL of content to load.
33006
33217
  */
33007
- var ngIncludeDirective = ['$templateRequest', '$anchorScroll', '$animate', '$sce',
33008
- function($templateRequest, $anchorScroll, $animate, $sce) {
33218
+ var ngIncludeDirective = ['$templateRequest', '$anchorScroll', '$animate',
33219
+ function($templateRequest, $anchorScroll, $animate) {
33009
33220
  return {
33010
33221
  restrict: 'ECA',
33011
33222
  priority: 400,
@@ -33041,7 +33252,7 @@ var ngIncludeDirective = ['$templateRequest', '$anchorScroll', '$animate', '$sce
33041
33252
  }
33042
33253
  };
33043
33254
 
33044
- scope.$watch($sce.parseAsResourceUrl(srcExp), function ngIncludeWatchAction(src) {
33255
+ scope.$watch(srcExp, function ngIncludeWatchAction(src) {
33045
33256
  var afterAnimation = function() {
33046
33257
  if (isDefined(autoScrollExp) && (!autoScrollExp || scope.$eval(autoScrollExp))) {
33047
33258
  $anchorScroll();
@@ -34412,7 +34623,7 @@ var DEFAULT_REGEXP = /(\s+|^)default(\s+|$)/;
34412
34623
  * - `debounce`: integer value which contains the debounce model update value in milliseconds. A
34413
34624
  * value of 0 triggers an immediate update. If an object is supplied instead, you can specify a
34414
34625
  * custom value for each event. For example:
34415
- * `ng-model-options="{ updateOn: 'default blur', debounce: {'default': 500, 'blur': 0} }"`
34626
+ * `ng-model-options="{ updateOn: 'default blur', debounce: { 'default': 500, 'blur': 0 } }"`
34416
34627
  * - `allowInvalid`: boolean value which indicates that the model can be set with values that did
34417
34628
  * not validate correctly instead of the default behavior of setting the model to undefined.
34418
34629
  * - `getterSetter`: boolean value which determines whether or not to treat functions bound to
@@ -34662,7 +34873,9 @@ function addSetValidityMethod(context) {
34662
34873
  function isObjectEmpty(obj) {
34663
34874
  if (obj) {
34664
34875
  for (var prop in obj) {
34665
- return false;
34876
+ if (obj.hasOwnProperty(prop)) {
34877
+ return false;
34878
+ }
34666
34879
  }
34667
34880
  }
34668
34881
  return true;
@@ -34994,19 +35207,41 @@ var ngOptionsDirective = ['$compile', '$parse', function($compile, $parse) {
34994
35207
  this.disabled = disabled;
34995
35208
  }
34996
35209
 
35210
+ function getOptionValuesKeys(optionValues) {
35211
+ var optionValuesKeys;
35212
+
35213
+ if (!keyName && isArrayLike(optionValues)) {
35214
+ optionValuesKeys = optionValues;
35215
+ } else {
35216
+ // if object, extract keys, in enumeration order, unsorted
35217
+ optionValuesKeys = [];
35218
+ for (var itemKey in optionValues) {
35219
+ if (optionValues.hasOwnProperty(itemKey) && itemKey.charAt(0) !== '$') {
35220
+ optionValuesKeys.push(itemKey);
35221
+ }
35222
+ }
35223
+ }
35224
+ return optionValuesKeys;
35225
+ }
35226
+
34997
35227
  return {
34998
35228
  trackBy: trackBy,
34999
35229
  getTrackByValue: getTrackByValue,
35000
- getWatchables: $parse(valuesFn, function(values) {
35230
+ getWatchables: $parse(valuesFn, function(optionValues) {
35001
35231
  // Create a collection of things that we would like to watch (watchedArray)
35002
35232
  // so that they can all be watched using a single $watchCollection
35003
35233
  // that only runs the handler once if anything changes
35004
35234
  var watchedArray = [];
35005
- values = values || [];
35235
+ optionValues = optionValues || [];
35236
+
35237
+ var optionValuesKeys = getOptionValuesKeys(optionValues);
35238
+ var optionValuesLength = optionValuesKeys.length;
35239
+ for (var index = 0; index < optionValuesLength; index++) {
35240
+ var key = (optionValues === optionValuesKeys) ? index : optionValuesKeys[index];
35241
+ var value = optionValues[key];
35006
35242
 
35007
- Object.keys(values).forEach(function getWatchable(key) {
35008
- var locals = getLocals(values[key], key);
35009
- var selectValue = getTrackByValueFn(values[key], locals);
35243
+ var locals = getLocals(optionValues[key], key);
35244
+ var selectValue = getTrackByValueFn(optionValues[key], locals);
35010
35245
  watchedArray.push(selectValue);
35011
35246
 
35012
35247
  // Only need to watch the displayFn if there is a specific label expression
@@ -35020,7 +35255,7 @@ var ngOptionsDirective = ['$compile', '$parse', function($compile, $parse) {
35020
35255
  var disableWhen = disableWhenFn(scope, locals);
35021
35256
  watchedArray.push(disableWhen);
35022
35257
  }
35023
- });
35258
+ }
35024
35259
  return watchedArray;
35025
35260
  }),
35026
35261
 
@@ -35032,21 +35267,7 @@ var ngOptionsDirective = ['$compile', '$parse', function($compile, $parse) {
35032
35267
  // The option values were already computed in the `getWatchables` fn,
35033
35268
  // which must have been called to trigger `getOptions`
35034
35269
  var optionValues = valuesFn(scope) || [];
35035
- var optionValuesKeys;
35036
-
35037
-
35038
- if (!keyName && isArrayLike(optionValues)) {
35039
- optionValuesKeys = optionValues;
35040
- } else {
35041
- // if object, extract keys, in enumeration order, unsorted
35042
- optionValuesKeys = [];
35043
- for (var itemKey in optionValues) {
35044
- if (optionValues.hasOwnProperty(itemKey) && itemKey.charAt(0) !== '$') {
35045
- optionValuesKeys.push(itemKey);
35046
- }
35047
- }
35048
- }
35049
-
35270
+ var optionValuesKeys = getOptionValuesKeys(optionValues);
35050
35271
  var optionValuesLength = optionValuesKeys.length;
35051
35272
 
35052
35273
  for (var index = 0; index < optionValuesLength; index++) {
@@ -35408,8 +35629,7 @@ var ngOptionsDirective = ['$compile', '$parse', function($compile, $parse) {
35408
35629
  // Check to see if the value has changed due to the update to the options
35409
35630
  if (!ngModelCtrl.$isEmpty(previousValue)) {
35410
35631
  var nextValue = selectCtrl.readValue();
35411
- if (ngOptions.trackBy && !equals(previousValue, nextValue) ||
35412
- previousValue !== nextValue) {
35632
+ if (ngOptions.trackBy ? !equals(previousValue, nextValue) : previousValue !== nextValue) {
35413
35633
  ngModelCtrl.$setViewValue(nextValue);
35414
35634
  ngModelCtrl.$render();
35415
35635
  }
@@ -35663,6 +35883,7 @@ var ngPluralizeDirective = ['$locale', '$interpolate', '$log', function($locale,
35663
35883
  /**
35664
35884
  * @ngdoc directive
35665
35885
  * @name ngRepeat
35886
+ * @multiElement
35666
35887
  *
35667
35888
  * @description
35668
35889
  * The `ngRepeat` directive instantiates a template once per item from a collection. Each template
@@ -35757,6 +35978,15 @@ var ngPluralizeDirective = ['$locale', '$interpolate', '$log', function($locale,
35757
35978
  * </div>
35758
35979
  * ```
35759
35980
  *
35981
+ * <div class="alert alert-warning">
35982
+ * **Note:** `track by` must always be the last expression:
35983
+ * </div>
35984
+ * ```
35985
+ * <div ng-repeat="model in collection | orderBy: 'id' as filtered_result track by model.id">
35986
+ * {{model.name}}
35987
+ * </div>
35988
+ * ```
35989
+ *
35760
35990
  * # Special repeat start and end points
35761
35991
  * To repeat a series of elements instead of just one parent element, ngRepeat (as well as other ng directives) supports extending
35762
35992
  * the range of the repeater by defining explicit start and end points by using **ng-repeat-start** and **ng-repeat-end** respectively.
@@ -35828,8 +36058,9 @@ var ngPluralizeDirective = ['$locale', '$interpolate', '$log', function($locale,
35828
36058
  * which can be used to associate the objects in the collection with the DOM elements. If no tracking expression
35829
36059
  * is specified, ng-repeat associates elements by identity. It is an error to have
35830
36060
  * more than one tracking expression value resolve to the same key. (This would mean that two distinct objects are
35831
- * mapped to the same DOM element, which is not possible.) If filters are used in the expression, they should be
35832
- * applied before the tracking expression.
36061
+ * mapped to the same DOM element, which is not possible.)
36062
+ *
36063
+ * Note that the tracking expression must come last, after any filters, and the alias expression.
35833
36064
  *
35834
36065
  * For example: `item in items` is equivalent to `item in items track by $id(item)`. This implies that the DOM elements
35835
36066
  * will be associated by item identity in the array.
@@ -36182,6 +36413,7 @@ var NG_HIDE_IN_PROGRESS_CLASS = 'ng-hide-animate';
36182
36413
  /**
36183
36414
  * @ngdoc directive
36184
36415
  * @name ngShow
36416
+ * @multiElement
36185
36417
  *
36186
36418
  * @description
36187
36419
  * The `ngShow` directive shows or hides the given HTML element based on the expression
@@ -36357,6 +36589,7 @@ var ngShowDirective = ['$animate', function($animate) {
36357
36589
  /**
36358
36590
  * @ngdoc directive
36359
36591
  * @name ngHide
36592
+ * @multiElement
36360
36593
  *
36361
36594
  * @description
36362
36595
  * The `ngHide` directive shows or hides the given HTML element based on the expression