@angular-wave/angular.ts 0.9.4 → 0.9.6

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.
Files changed (645) hide show
  1. package/@types/index.d.ts +1 -84
  2. package/{src/index.ts → @types/namespace.d.ts} +4 -24
  3. package/@types/router/template-factory.d.ts +2 -2
  4. package/dist/angular-ts.esm.js +3 -3
  5. package/dist/angular-ts.umd.js +3 -3
  6. package/dist/angular-ts.umd.min.js +1 -1
  7. package/package.json +9 -2
  8. package/.github/workflows/ci.yml +0 -104
  9. package/.github/workflows/gh-pages.yml +0 -75
  10. package/.husky/pre-commit +0 -5
  11. package/.prettierignore +0 -9
  12. package/CHANGELOG.md +0 -17667
  13. package/CODE_OF_CONDUCT.md +0 -3
  14. package/CONTRIBUTING.md +0 -247
  15. package/DEVELOPERS.md +0 -499
  16. package/Makefile +0 -60
  17. package/RELEASE.md +0 -86
  18. package/TRIAGING.md +0 -127
  19. package/docs/.cspell.yml +0 -8
  20. package/docs/.github/dependabot.yml +0 -14
  21. package/docs/.nvmrc +0 -1
  22. package/docs/CONTRIBUTING.md +0 -28
  23. package/docs/Dockerfile +0 -4
  24. package/docs/LICENSE +0 -201
  25. package/docs/README.md +0 -217
  26. package/docs/assets/icons/logo.svg +0 -1
  27. package/docs/assets/scss/_variables_project.scss +0 -12
  28. package/docs/assets/scss/_variables_project_after_bs.scss +0 -8
  29. package/docs/assets/scss/index.scss +0 -48
  30. package/docs/config.yaml +0 -15
  31. package/docs/content/_index.md +0 -28
  32. package/docs/content/docs/_index.md +0 -61
  33. package/docs/content/docs/directive/_index.md +0 -4
  34. package/docs/content/docs/directive/app.md +0 -11
  35. package/docs/content/docs/directive/aria.md +0 -0
  36. package/docs/content/docs/directive/bind.md +0 -72
  37. package/docs/content/docs/directive/blur.md +0 -38
  38. package/docs/content/docs/directive/channel.md +0 -37
  39. package/docs/content/docs/directive/class-even.md +0 -47
  40. package/docs/content/docs/directive/class-odd.md +0 -48
  41. package/docs/content/docs/directive/class.md +0 -64
  42. package/docs/content/docs/directive/click.md +0 -41
  43. package/docs/content/docs/directive/cloak.md +0 -74
  44. package/docs/content/docs/directive/copy.md +0 -38
  45. package/docs/content/docs/directive/cut.md +0 -40
  46. package/docs/content/docs/directive/dblclick.md +0 -41
  47. package/docs/content/docs/directive/focus.md +0 -38
  48. package/docs/content/docs/directive/get.md +0 -203
  49. package/docs/content/docs/directive/include.md +0 -7
  50. package/docs/content/docs/directive/keydown.md +0 -38
  51. package/docs/content/docs/directive/keyup.md +0 -38
  52. package/docs/content/docs/directive/load.md +0 -43
  53. package/docs/content/docs/directive/mousedown.md +0 -38
  54. package/docs/content/docs/directive/mouseenter.md +0 -38
  55. package/docs/content/docs/directive/mouseleave.md +0 -38
  56. package/docs/content/docs/directive/mousemove.md +0 -38
  57. package/docs/content/docs/directive/mouseout.md +0 -38
  58. package/docs/content/docs/directive/mouseover.md +0 -38
  59. package/docs/content/docs/directive/mouseup.md +0 -38
  60. package/docs/content/docs/directive/non-bindable.md +0 -28
  61. package/docs/content/docs/filter/_index.md +0 -4
  62. package/docs/content/docs/filter/filter.md +0 -78
  63. package/docs/content/docs/filter/json.md +0 -19
  64. package/docs/content/docs/filter/limit-to.md +0 -30
  65. package/docs/content/docs/filter/order-by.md +0 -123
  66. package/docs/content/docs/provider/_index.md +0 -4
  67. package/docs/content/docs/provider/eventBusProvider.md +0 -35
  68. package/docs/content/docs/provider/locationProvider.md +0 -26
  69. package/docs/content/docs/provider/logProvider.md +0 -59
  70. package/docs/content/docs/provider/sceProvider.md +0 -194
  71. package/docs/content/docs/provider/templateCacheProvider.md +0 -100
  72. package/docs/content/docs/provider/templateRequestProvider.md +0 -5
  73. package/docs/content/docs/service/_index.md +0 -4
  74. package/docs/content/docs/service/compile.md +0 -5
  75. package/docs/content/docs/service/controller.md +0 -5
  76. package/docs/content/docs/service/eventBus.md +0 -56
  77. package/docs/content/docs/service/http.md +0 -161
  78. package/docs/content/docs/service/interpolation.md +0 -5
  79. package/docs/content/docs/service/location.md +0 -57
  80. package/docs/content/docs/service/log.md +0 -113
  81. package/docs/content/docs/service/parse.md +0 -5
  82. package/docs/content/docs/service/rootElement.md +0 -5
  83. package/docs/content/docs/service/rootScope.md +0 -5
  84. package/docs/content/docs/service/sce.md +0 -194
  85. package/docs/content/docs/service/templateCache.md +0 -64
  86. package/docs/content/docs/service/templateRequest.md +0 -5
  87. package/docs/content/docs/service/url.md +0 -5
  88. package/docs/content/docs/values/_index.md +0 -4
  89. package/docs/content/docs/values/document.md +0 -29
  90. package/docs/content/docs/values/window.md +0 -29
  91. package/docs/docker-compose.yaml +0 -12
  92. package/docs/docsy.work +0 -5
  93. package/docs/docsy.work.sum +0 -0
  94. package/docs/go.mod +0 -5
  95. package/docs/go.sum +0 -6
  96. package/docs/hugo-disabled.toml +0 -220
  97. package/docs/hugo.yaml +0 -200
  98. package/docs/layouts/404.html +0 -13
  99. package/docs/layouts/_markup/render-heading.html +0 -1
  100. package/docs/layouts/partials/hooks/head-end.html +0 -3
  101. package/docs/layouts/shortcodes/showcss.html +0 -2
  102. package/docs/layouts/shortcodes/showhtml.html +0 -2
  103. package/docs/layouts/shortcodes/showjs.html +0 -2
  104. package/docs/layouts/shortcodes/showraw.html +0 -1
  105. package/docs/layouts/shortcodes/version.html +0 -1
  106. package/docs/package-lock.json +0 -2293
  107. package/docs/package.json +0 -53
  108. package/docs/static/examples/counter/counter-test.html +0 -13
  109. package/docs/static/examples/counter/counter.html +0 -5
  110. package/docs/static/examples/counter/counter.test.js +0 -28
  111. package/docs/static/examples/document/document.html +0 -3
  112. package/docs/static/examples/eventbus/eventbus-test.html +0 -15
  113. package/docs/static/examples/eventbus/eventbus.html +0 -13
  114. package/docs/static/examples/eventbus/eventbus.js +0 -15
  115. package/docs/static/examples/eventbus/eventbus.test.js +0 -19
  116. package/docs/static/examples/i18n/i18n.html +0 -77
  117. package/docs/static/examples/ng-bind/ng-bind.html +0 -9
  118. package/docs/static/examples/ng-blur/ng-blur.html +0 -9
  119. package/docs/static/examples/ng-channel/ng-channel-test.html +0 -17
  120. package/docs/static/examples/ng-channel/ng-channel.html +0 -24
  121. package/docs/static/examples/ng-channel/ng-channel.test.js +0 -31
  122. package/docs/static/examples/ng-class/ng-class.html +0 -71
  123. package/docs/static/examples/ng-class-even/ng-class-even.html +0 -8
  124. package/docs/static/examples/ng-class-odd/ng-class-odd.html +0 -8
  125. package/docs/static/examples/ng-click/ng-click.html +0 -6
  126. package/docs/static/examples/ng-copy/ng-copy.html +0 -6
  127. package/docs/static/examples/ng-cut/ng-cut.html +0 -6
  128. package/docs/static/examples/ng-dblclick/ng-dblclick.html +0 -10
  129. package/docs/static/examples/ng-focus/ng-focus.html +0 -9
  130. package/docs/static/examples/ng-keydown/ng-keydown.html +0 -9
  131. package/docs/static/examples/ng-keyup/ng-keyup.html +0 -9
  132. package/docs/static/examples/ng-load/ng-load.html +0 -8
  133. package/docs/static/examples/ng-mousedown/ng-mousedown.html +0 -6
  134. package/docs/static/examples/ng-mouseenter/ng-mouseenter.html +0 -4
  135. package/docs/static/examples/ng-mouseleave/ng-mouseleave.html +0 -4
  136. package/docs/static/examples/ng-mousemove/ng-mousemove.html +0 -4
  137. package/docs/static/examples/ng-mouseout/ng-mouseout.html +0 -4
  138. package/docs/static/examples/ng-mouseover/ng-mouseover.html +0 -4
  139. package/docs/static/examples/ng-mouseup/ng-mouseup.html +0 -4
  140. package/docs/static/examples/ng-non-bindable/ng-non-bindable-test.html +0 -13
  141. package/docs/static/examples/ng-non-bindable/ng-non-bindable.html +0 -3
  142. package/docs/static/examples/ng-non-bindable/ng-non-bindable.test.js +0 -11
  143. package/docs/static/examples/window/window.html +0 -4
  144. package/docs/static/typedoc/.nojekyll +0 -1
  145. package/docs/static/typedoc/assets/hierarchy.js +0 -1
  146. package/docs/static/typedoc/assets/highlight.css +0 -29
  147. package/docs/static/typedoc/assets/icons.js +0 -18
  148. package/docs/static/typedoc/assets/icons.svg +0 -1
  149. package/docs/static/typedoc/assets/main.js +0 -60
  150. package/docs/static/typedoc/assets/navigation.js +0 -1
  151. package/docs/static/typedoc/assets/search.js +0 -1
  152. package/docs/static/typedoc/assets/style.css +0 -1633
  153. package/docs/static/typedoc/classes/Location.html +0 -55
  154. package/docs/static/typedoc/classes/LocationProvider.html +0 -20
  155. package/docs/static/typedoc/classes/LogProvider.html +0 -6
  156. package/docs/static/typedoc/classes/PubSub.html +0 -71
  157. package/docs/static/typedoc/classes/PubSubProvider.html +0 -4
  158. package/docs/static/typedoc/classes/TemplateCacheProvider.html +0 -5
  159. package/docs/static/typedoc/hierarchy.html +0 -1
  160. package/docs/static/typedoc/index.html +0 -1
  161. package/docs/static/typedoc/interfaces/DefaultPorts.html +0 -5
  162. package/docs/static/typedoc/interfaces/Html5Mode.html +0 -23
  163. package/docs/static/typedoc/interfaces/HttpHeadersGetter.html +0 -1
  164. package/docs/static/typedoc/interfaces/HttpProviderDefaults.html +0 -31
  165. package/docs/static/typedoc/interfaces/HttpRequestConfigHeaders.html +0 -6
  166. package/docs/static/typedoc/interfaces/HttpRequestTransformer.html +0 -1
  167. package/docs/static/typedoc/interfaces/HttpResponse.html +0 -7
  168. package/docs/static/typedoc/interfaces/HttpResponseTransformer.html +0 -1
  169. package/docs/static/typedoc/interfaces/HttpService.html +0 -38
  170. package/docs/static/typedoc/interfaces/LogService.html +0 -12
  171. package/docs/static/typedoc/interfaces/RequestConfig.html +0 -48
  172. package/docs/static/typedoc/interfaces/RequestShortcutConfig.html +0 -38
  173. package/docs/static/typedoc/interfaces/ServiceProvider.html +0 -5
  174. package/docs/static/typedoc/interfaces/UrlParts.html +0 -9
  175. package/docs/static/typedoc/types/HttpParamSerializer.html +0 -2
  176. package/docs/static/typedoc/types/HttpParams.html +0 -2
  177. package/docs/static/typedoc/types/HttpPromise.html +0 -1
  178. package/docs/static/typedoc/types/HttpResponseStatus.html +0 -1
  179. package/docs/static/typedoc/types/LogCall.html +0 -2
  180. package/docs/static/typedoc/types/LogServiceFactory.html +0 -2
  181. package/docs/static/typedoc/types/UrlChangeListener.html +0 -5
  182. package/docs/static/typedoc/variables/EventBus.html +0 -1
  183. package/docs/static/version.js +0 -13
  184. package/docs/test-results/.last-run.json +0 -4
  185. package/docs/test-results/static-examples-counter-counter-counter-example/error-context.md +0 -50
  186. package/eslint.config.js +0 -26
  187. package/images/android-chrome-192x192.png +0 -0
  188. package/images/android-chrome-512x512.png +0 -0
  189. package/images/apple-touch-icon.png +0 -0
  190. package/images/favicon-16x16.png +0 -0
  191. package/images/favicon-32x32.png +0 -0
  192. package/images/favicon.ico +0 -0
  193. package/images/site.webmanifest +0 -19
  194. package/index.html +0 -86
  195. package/legacy.d.ts +0 -1678
  196. package/playwright.config.ts +0 -81
  197. package/public/jasmine/boot0.js +0 -66
  198. package/public/jasmine/boot1.js +0 -134
  199. package/public/jasmine/jasmine-html.js +0 -970
  200. package/public/jasmine/jasmine.css +0 -323
  201. package/public/jasmine/jasmine.js +0 -11406
  202. package/public/public/README.md +0 -1
  203. package/public/public/circle.html +0 -1
  204. package/public/public/jasmine-helper.css +0 -9
  205. package/public/public/my_child_directive.html +0 -1
  206. package/public/public/my_directive.html +0 -1
  207. package/public/public/my_other_directive.html +0 -1
  208. package/public/public/test.html +0 -1
  209. package/rollup.config.js +0 -51
  210. package/src/angular.js +0 -286
  211. package/src/angular.spec.js +0 -1191
  212. package/src/animations/animate-cache.js +0 -80
  213. package/src/animations/animate-children-directive.js +0 -32
  214. package/src/animations/animate-children-directive.md +0 -80
  215. package/src/animations/animate-css-driver.js +0 -284
  216. package/src/animations/animate-css.html +0 -58
  217. package/src/animations/animate-css.js +0 -915
  218. package/src/animations/animate-css.md +0 -263
  219. package/src/animations/animate-js-driver.js +0 -60
  220. package/src/animations/animate-js.html +0 -47
  221. package/src/animations/animate-js.js +0 -371
  222. package/src/animations/animate-queue.js +0 -859
  223. package/src/animations/animate-runner.js +0 -193
  224. package/src/animations/animate-swap.js +0 -33
  225. package/src/animations/animate-swap.md +0 -88
  226. package/src/animations/animate.html +0 -19
  227. package/src/animations/animate.js +0 -546
  228. package/src/animations/animate.md +0 -933
  229. package/src/animations/animate.spec.js +0 -490
  230. package/src/animations/animation.js +0 -519
  231. package/src/animations/animations.test.js +0 -10
  232. package/src/animations/interface.ts +0 -19
  233. package/src/animations/raf-scheduler.html +0 -19
  234. package/src/animations/raf-scheduler.js +0 -92
  235. package/src/animations/raf-scheduler.spec.js +0 -98
  236. package/src/animations/shared.js +0 -341
  237. package/src/binding.html +0 -19
  238. package/src/binding.spec.js +0 -474
  239. package/src/binding.test.js +0 -10
  240. package/src/core/compile/attributes.js +0 -337
  241. package/src/core/compile/compile.html +0 -19
  242. package/src/core/compile/compile.js +0 -3271
  243. package/src/core/compile/compile.md +0 -1128
  244. package/src/core/compile/compile.spec.js +0 -15574
  245. package/src/core/compile/compile.test.js +0 -12
  246. package/src/core/controller/controller.html +0 -22
  247. package/src/core/controller/controller.js +0 -193
  248. package/src/core/controller/controller.spec.js +0 -334
  249. package/src/core/controller/controller.test.js +0 -12
  250. package/src/core/controller/interface.ts +0 -6
  251. package/src/core/core.html +0 -20
  252. package/src/core/core.test.js +0 -12
  253. package/src/core/di/injector.html +0 -19
  254. package/src/core/di/injector.js +0 -307
  255. package/src/core/di/injector.md +0 -740
  256. package/src/core/di/injector.spec.js +0 -2310
  257. package/src/core/di/injector.test.js +0 -12
  258. package/src/core/di/internal-injector.js +0 -286
  259. package/src/core/di/ng-module.html +0 -19
  260. package/src/core/di/ng-module.js +0 -229
  261. package/src/core/di/ng-module.spec.js +0 -263
  262. package/src/core/di/ng-module.test.js +0 -12
  263. package/src/core/filter/filter.html +0 -19
  264. package/src/core/filter/filter.js +0 -55
  265. package/src/core/filter/filter.md +0 -132
  266. package/src/core/filter/filter.spec.js +0 -149
  267. package/src/core/filter/filter.test.js +0 -12
  268. package/src/core/interpolate/interface.ts +0 -14
  269. package/src/core/interpolate/interpolate.html +0 -22
  270. package/src/core/interpolate/interpolate.js +0 -410
  271. package/src/core/interpolate/interpolate.spec.js +0 -601
  272. package/src/core/interpolate/interpolate.test.js +0 -12
  273. package/src/core/parse/ast/ast-node.ts +0 -81
  274. package/src/core/parse/ast/ast.html +0 -19
  275. package/src/core/parse/ast/ast.js +0 -574
  276. package/src/core/parse/ast/ast.spec.js +0 -1453
  277. package/src/core/parse/ast/ast.test.js +0 -10
  278. package/src/core/parse/ast-type.js +0 -23
  279. package/src/core/parse/interface.ts +0 -84
  280. package/src/core/parse/interpreter.js +0 -915
  281. package/src/core/parse/lexer/lexer.html +0 -19
  282. package/src/core/parse/lexer/lexer.js +0 -338
  283. package/src/core/parse/lexer/lexer.spec.js +0 -303
  284. package/src/core/parse/lexer/lexer.test.js +0 -10
  285. package/src/core/parse/lexer/token.ts +0 -22
  286. package/src/core/parse/parse.html +0 -19
  287. package/src/core/parse/parse.js +0 -337
  288. package/src/core/parse/parse.md +0 -57
  289. package/src/core/parse/parse.spec.js +0 -2107
  290. package/src/core/parse/parse.test.js +0 -10
  291. package/src/core/parse/parser/parser.html +0 -19
  292. package/src/core/parse/parser/parser.js +0 -64
  293. package/src/core/parse/parser/parser.spec.js +0 -8
  294. package/src/core/parse/parser/parser.test.js +0 -10
  295. package/src/core/prop.spec.js +0 -775
  296. package/src/core/root-element.spec.js +0 -14
  297. package/src/core/sanitize/interface.ts +0 -10
  298. package/src/core/sanitize/sanitize-uri.js +0 -75
  299. package/src/core/sanitize/sanitize-uri.spec.js +0 -249
  300. package/src/core/sanitize/sanitize-uri.test.js +0 -12
  301. package/src/core/sanitize/sanitize.html +0 -22
  302. package/src/core/scope/scope.html +0 -19
  303. package/src/core/scope/scope.js +0 -1252
  304. package/src/core/scope/scope.spec.js +0 -3000
  305. package/src/core/scope/scope.test.js +0 -12
  306. package/src/directive/aria/aria.html +0 -19
  307. package/src/directive/aria/aria.js +0 -382
  308. package/src/directive/aria/aria.md +0 -145
  309. package/src/directive/aria/aria.spec.js +0 -1241
  310. package/src/directive/aria/aria.test.js +0 -12
  311. package/src/directive/attrs/attrs.html +0 -19
  312. package/src/directive/attrs/attrs.js +0 -106
  313. package/src/directive/attrs/attrs.md +0 -224
  314. package/src/directive/attrs/attrs.spec.js +0 -71
  315. package/src/directive/attrs/attrs.test.js +0 -12
  316. package/src/directive/attrs/boolean.html +0 -19
  317. package/src/directive/attrs/boolean.spec.js +0 -137
  318. package/src/directive/attrs/boolean.test.js +0 -12
  319. package/src/directive/attrs/element-style.html +0 -22
  320. package/src/directive/attrs/element-style.spec.js +0 -85
  321. package/src/directive/attrs/element-style.test.js +0 -12
  322. package/src/directive/attrs/src.html +0 -19
  323. package/src/directive/attrs/src.spec.js +0 -163
  324. package/src/directive/attrs/src.test.js +0 -12
  325. package/src/directive/bind/bind-html.spec.js +0 -36
  326. package/src/directive/bind/bind.html +0 -20
  327. package/src/directive/bind/bind.js +0 -78
  328. package/src/directive/bind/bind.md +0 -142
  329. package/src/directive/bind/bind.spec.js +0 -314
  330. package/src/directive/bind/bind.test.js +0 -12
  331. package/src/directive/channel/channel.html +0 -19
  332. package/src/directive/channel/channel.js +0 -30
  333. package/src/directive/channel/channel.spec.js +0 -67
  334. package/src/directive/channel/channel.test.js +0 -10
  335. package/src/directive/class/class-test.html +0 -23
  336. package/src/directive/class/class.html +0 -19
  337. package/src/directive/class/class.js +0 -184
  338. package/src/directive/class/class.spec.js +0 -704
  339. package/src/directive/class/class.test.js +0 -12
  340. package/src/directive/cloak/cloak.html +0 -19
  341. package/src/directive/cloak/cloak.js +0 -11
  342. package/src/directive/cloak/cloak.spec.js +0 -44
  343. package/src/directive/cloak/cloak.test.js +0 -12
  344. package/src/directive/controller/controller.html +0 -22
  345. package/src/directive/controller/controller.js +0 -11
  346. package/src/directive/controller/controller.md +0 -46
  347. package/src/directive/controller/controller.spec.js +0 -175
  348. package/src/directive/controller/controller.test.js +0 -12
  349. package/src/directive/events/click.spec.js +0 -35
  350. package/src/directive/events/event.spec.js +0 -267
  351. package/src/directive/events/events-test.html +0 -36
  352. package/src/directive/events/events.html +0 -20
  353. package/src/directive/events/events.js +0 -65
  354. package/src/directive/events/events.md +0 -125
  355. package/src/directive/events/events.test.js +0 -12
  356. package/src/directive/form/form.html +0 -19
  357. package/src/directive/form/form.js +0 -669
  358. package/src/directive/form/form.spec.js +0 -1515
  359. package/src/directive/form/form.test.js +0 -12
  360. package/src/directive/http/delete.spec.js +0 -23
  361. package/src/directive/http/form-router-test.html +0 -44
  362. package/src/directive/http/form-test.html +0 -18
  363. package/src/directive/http/get.spec.js +0 -488
  364. package/src/directive/http/http.html +0 -22
  365. package/src/directive/http/http.js +0 -342
  366. package/src/directive/http/http.test.js +0 -12
  367. package/src/directive/http/interface.ts +0 -36
  368. package/src/directive/http/post-example.html +0 -30
  369. package/src/directive/http/post.spec.js +0 -521
  370. package/src/directive/http/put.spec.js +0 -23
  371. package/src/directive/if/if-animate-css.html +0 -57
  372. package/src/directive/if/if-animate-svg.html +0 -25
  373. package/src/directive/if/if.html +0 -19
  374. package/src/directive/if/if.js +0 -72
  375. package/src/directive/if/if.md +0 -76
  376. package/src/directive/if/if.spec.js +0 -293
  377. package/src/directive/if/if.test.js +0 -114
  378. package/src/directive/include/include.html +0 -19
  379. package/src/directive/include/include.js +0 -151
  380. package/src/directive/include/include.md +0 -87
  381. package/src/directive/include/include.spec.js +0 -734
  382. package/src/directive/include/include.test.js +0 -12
  383. package/src/directive/init/init.html +0 -19
  384. package/src/directive/init/init.js +0 -22
  385. package/src/directive/init/init.md +0 -41
  386. package/src/directive/init/init.spec.js +0 -68
  387. package/src/directive/init/init.test.js +0 -12
  388. package/src/directive/inject/inject.html +0 -19
  389. package/src/directive/inject/inject.js +0 -35
  390. package/src/directive/inject/inject.spec.js +0 -108
  391. package/src/directive/inject/inject.test.js +0 -12
  392. package/src/directive/input/input-example.html +0 -15
  393. package/src/directive/input/input.html +0 -19
  394. package/src/directive/input/input.js +0 -1078
  395. package/src/directive/input/input.md +0 -706
  396. package/src/directive/input/input.spec.js +0 -3700
  397. package/src/directive/input/input.test.js +0 -12
  398. package/src/directive/messages/messages.html +0 -22
  399. package/src/directive/messages/messages.js +0 -349
  400. package/src/directive/messages/messages.md +0 -543
  401. package/src/directive/messages/messages.spec.js +0 -1083
  402. package/src/directive/messages/messages.test.js +0 -12
  403. package/src/directive/model/change.md +0 -25
  404. package/src/directive/model/model.html +0 -19
  405. package/src/directive/model/model.js +0 -1170
  406. package/src/directive/model/model.spec.js +0 -1976
  407. package/src/directive/model/model.test.js +0 -12
  408. package/src/directive/model-options/model-option.test.js +0 -12
  409. package/src/directive/model-options/model-options.html +0 -22
  410. package/src/directive/model-options/model-options.js +0 -142
  411. package/src/directive/model-options/model-options.md +0 -407
  412. package/src/directive/model-options/model-options.spec.js +0 -1022
  413. package/src/directive/non-bindable/non-bindable.html +0 -22
  414. package/src/directive/non-bindable/non-bindable.js +0 -9
  415. package/src/directive/non-bindable/non-bindable.spec.js +0 -59
  416. package/src/directive/non-bindable/non-bindable.test.js +0 -12
  417. package/src/directive/observe/observe-demo.html +0 -184
  418. package/src/directive/observe/observe.html +0 -19
  419. package/src/directive/observe/observe.js +0 -41
  420. package/src/directive/observe/observe.spec.js +0 -106
  421. package/src/directive/observe/observe.test.js +0 -10
  422. package/src/directive/on/on.html +0 -19
  423. package/src/directive/on/on.spec.js +0 -215
  424. package/src/directive/on/on.test.js +0 -12
  425. package/src/directive/options/options-example.html +0 -17
  426. package/src/directive/options/options.html +0 -22
  427. package/src/directive/options/options.js +0 -542
  428. package/src/directive/options/options.md +0 -179
  429. package/src/directive/options/options.spec.js +0 -3554
  430. package/src/directive/options/options.test.js +0 -12
  431. package/src/directive/ref/href.html +0 -19
  432. package/src/directive/ref/href.spec.js +0 -141
  433. package/src/directive/ref/href.test.js +0 -19
  434. package/src/directive/ref/ref.html +0 -19
  435. package/src/directive/ref/ref.js +0 -89
  436. package/src/directive/ref/ref.spec.js +0 -546
  437. package/src/directive/repeat/repeat.html +0 -19
  438. package/src/directive/repeat/repeat.js +0 -333
  439. package/src/directive/repeat/repeat.md +0 -330
  440. package/src/directive/repeat/repeat.spec.js +0 -1209
  441. package/src/directive/repeat/repeat.test.js +0 -12
  442. package/src/directive/script/script.html +0 -19
  443. package/src/directive/script/script.js +0 -17
  444. package/src/directive/script/script.md +0 -11
  445. package/src/directive/script/script.spec.js +0 -47
  446. package/src/directive/script/script.test.js +0 -12
  447. package/src/directive/select/select.html +0 -19
  448. package/src/directive/select/select.js +0 -594
  449. package/src/directive/select/select.md +0 -74
  450. package/src/directive/select/select.spec.js +0 -2566
  451. package/src/directive/select/select.test.js +0 -12
  452. package/src/directive/setter/setter.html +0 -19
  453. package/src/directive/setter/setter.js +0 -59
  454. package/src/directive/setter/setter.spec.js +0 -100
  455. package/src/directive/setter/setter.test.js +0 -12
  456. package/src/directive/show-hide/show-hide.html +0 -22
  457. package/src/directive/show-hide/show-hide.js +0 -65
  458. package/src/directive/show-hide/show-hide.md +0 -255
  459. package/src/directive/show-hide/show-hide.spec.js +0 -268
  460. package/src/directive/show-hide/show-hide.test.js +0 -12
  461. package/src/directive/style/style.html +0 -19
  462. package/src/directive/style/style.js +0 -27
  463. package/src/directive/style/style.md +0 -23
  464. package/src/directive/style/style.spec.js +0 -183
  465. package/src/directive/style/style.test.js +0 -12
  466. package/src/directive/switch/switch.html +0 -19
  467. package/src/directive/switch/switch.js +0 -133
  468. package/src/directive/switch/switch.md +0 -66
  469. package/src/directive/switch/switch.spec.js +0 -509
  470. package/src/directive/switch/switch.test.js +0 -12
  471. package/src/directive/transclude/transclude.js +0 -122
  472. package/src/directive/validators/validators.html +0 -22
  473. package/src/directive/validators/validators.js +0 -346
  474. package/src/directive/validators/validators.spec.js +0 -740
  475. package/src/directive/validators/validators.test.js +0 -12
  476. package/src/filters/filter.js +0 -213
  477. package/src/filters/filter.spec.js +0 -719
  478. package/src/filters/filters.html +0 -22
  479. package/src/filters/filters.js +0 -239
  480. package/src/filters/filters.spec.js +0 -36
  481. package/src/filters/filters.test.js +0 -12
  482. package/src/filters/interface.ts +0 -9
  483. package/src/filters/limit-to.js +0 -55
  484. package/src/filters/limit-to.spec.js +0 -252
  485. package/src/filters/order-by.js +0 -181
  486. package/src/filters/order-by.spec.js +0 -883
  487. package/src/index.js +0 -6
  488. package/src/index.spec.js +0 -11
  489. package/src/injection-tokens.js +0 -81
  490. package/src/interface.ts +0 -430
  491. package/src/ng.js +0 -291
  492. package/src/ng.spec.js +0 -45
  493. package/src/router/common/trace.js +0 -240
  494. package/src/router/directives/component-example.html +0 -37
  495. package/src/router/directives/state-directives.html +0 -22
  496. package/src/router/directives/state-directives.js +0 -393
  497. package/src/router/directives/state-directives.md +0 -435
  498. package/src/router/directives/state-directives.spec.js +0 -1091
  499. package/src/router/directives/state-directives.test.js +0 -10
  500. package/src/router/directives/view-directive.js +0 -489
  501. package/src/router/directives/view-directive.spec.js +0 -1921
  502. package/src/router/directives/view-directive.test.js +0 -10
  503. package/src/router/directives/view-directives.html +0 -22
  504. package/src/router/glob/glob.html +0 -19
  505. package/src/router/glob/glob.js +0 -102
  506. package/src/router/glob/glob.spec.js +0 -108
  507. package/src/router/glob/glob.test.js +0 -12
  508. package/src/router/hooks/core-resolvables.js +0 -38
  509. package/src/router/hooks/ignored-transition.js +0 -25
  510. package/src/router/hooks/invalid-transition.js +0 -14
  511. package/src/router/hooks/lazy-load.js +0 -104
  512. package/src/router/hooks/on-enter-exit-retain.js +0 -55
  513. package/src/router/hooks/redirect-to.js +0 -38
  514. package/src/router/hooks/resolve.js +0 -57
  515. package/src/router/hooks/update-globals.js +0 -34
  516. package/src/router/hooks/url.js +0 -34
  517. package/src/router/hooks/views.js +0 -41
  518. package/src/router/params/interface.ts +0 -626
  519. package/src/router/params/param-factory.js +0 -23
  520. package/src/router/params/param-type.js +0 -133
  521. package/src/router/params/param-types.js +0 -153
  522. package/src/router/params/param.js +0 -243
  523. package/src/router/params/state-params.js +0 -36
  524. package/src/router/path/path-node.js +0 -78
  525. package/src/router/path/path-utils.js +0 -207
  526. package/src/router/resolve/interface.ts +0 -208
  527. package/src/router/resolve/resolvable.js +0 -123
  528. package/src/router/resolve/resolve-context.js +0 -190
  529. package/src/router/router-test-hashbang.html +0 -45
  530. package/src/router/router-test.html +0 -41
  531. package/src/router/router.html +0 -22
  532. package/src/router/router.js +0 -54
  533. package/src/router/router.test.js +0 -12
  534. package/src/router/services.spec.js +0 -52
  535. package/src/router/state/interface.ts +0 -1007
  536. package/src/router/state/state-builder.js +0 -376
  537. package/src/router/state/state-builder.spec.js +0 -86
  538. package/src/router/state/state-matcher.js +0 -64
  539. package/src/router/state/state-object.js +0 -118
  540. package/src/router/state/state-queue-manager.js +0 -95
  541. package/src/router/state/state-registry.js +0 -262
  542. package/src/router/state/state-service.js +0 -687
  543. package/src/router/state/state.html +0 -23
  544. package/src/router/state/state.spec.js +0 -1002
  545. package/src/router/state/state.test.js +0 -12
  546. package/src/router/state/target-state.js +0 -162
  547. package/src/router/state/views.js +0 -195
  548. package/src/router/state-filter.spec.js +0 -139
  549. package/src/router/state-filters.js +0 -46
  550. package/src/router/template-factory.html +0 -19
  551. package/src/router/template-factory.js +0 -249
  552. package/src/router/template-factory.spec.js +0 -146
  553. package/src/router/template-factory.test.js +0 -12
  554. package/src/router/transition/hook-builder.js +0 -137
  555. package/src/router/transition/hook-registry.js +0 -181
  556. package/src/router/transition/interface.js +0 -18
  557. package/src/router/transition/interface.ts +0 -922
  558. package/src/router/transition/reject-factory.js +0 -122
  559. package/src/router/transition/transition-event-type.js +0 -26
  560. package/src/router/transition/transition-hook.js +0 -199
  561. package/src/router/transition/transition-service.js +0 -297
  562. package/src/router/transition/transition.js +0 -653
  563. package/src/router/url/url-config.js +0 -155
  564. package/src/router/url/url-matcher.js +0 -532
  565. package/src/router/url/url-rule.js +0 -231
  566. package/src/router/url/url-rules.js +0 -350
  567. package/src/router/url/url-service.js +0 -446
  568. package/src/router/url/url-service.spec.js +0 -1288
  569. package/src/router/url/url.html +0 -19
  570. package/src/router/url/url.test.js +0 -12
  571. package/src/router/view/interface.ts +0 -51
  572. package/src/router/view/view.html +0 -19
  573. package/src/router/view/view.js +0 -262
  574. package/src/router/view/view.spec.js +0 -100
  575. package/src/router/view/view.test.js +0 -12
  576. package/src/router/view-hook.spec.js +0 -215
  577. package/src/router/view-scroll.js +0 -33
  578. package/src/router/view-scroll.spec.js +0 -72
  579. package/src/services/anchor-scroll/anchor-scroll.html +0 -76
  580. package/src/services/anchor-scroll/anchor-scroll.js +0 -147
  581. package/src/services/exception/exception-handler.js +0 -75
  582. package/src/services/exception/interface.ts +0 -7
  583. package/src/services/http/http.html +0 -23
  584. package/src/services/http/http.js +0 -1109
  585. package/src/services/http/http.spec.js +0 -4320
  586. package/src/services/http/http.test.js +0 -11
  587. package/src/services/http/interface.ts +0 -256
  588. package/src/services/http/template-request.spec.js +0 -220
  589. package/src/services/location/interface.ts +0 -70
  590. package/src/services/location/location.html +0 -22
  591. package/src/services/location/location.js +0 -1006
  592. package/src/services/location/location.spec.js +0 -3792
  593. package/src/services/location/location.test.js +0 -12
  594. package/src/services/log/interface.ts +0 -39
  595. package/src/services/log/log.html +0 -19
  596. package/src/services/log/log.js +0 -74
  597. package/src/services/log/log.spec.js +0 -64
  598. package/src/services/log/log.test.js +0 -12
  599. package/src/services/pubsub/pubsub.html +0 -19
  600. package/src/services/pubsub/pubsub.js +0 -349
  601. package/src/services/pubsub/pubsub.spec.js +0 -400
  602. package/src/services/pubsub/pubsub.test.js +0 -12
  603. package/src/services/sce/sce.html +0 -19
  604. package/src/services/sce/sce.js +0 -852
  605. package/src/services/sce/sce.spec.js +0 -617
  606. package/src/services/sce/sce.test.js +0 -12
  607. package/src/services/template-cache/template-cache.html +0 -22
  608. package/src/services/template-cache/template-cache.js +0 -15
  609. package/src/services/template-cache/template-cache.spec.js +0 -134
  610. package/src/services/template-cache/template-cache.test.js +0 -12
  611. package/src/services/template-request/interface.ts +0 -23
  612. package/src/services/template-request/template-request.js +0 -142
  613. package/src/shared/cache.js +0 -7
  614. package/src/shared/common.js +0 -365
  615. package/src/shared/common.spec.js +0 -294
  616. package/src/shared/constants.js +0 -21
  617. package/src/shared/dom.js +0 -716
  618. package/src/shared/hof.js +0 -157
  619. package/src/shared/hof.spec.js +0 -60
  620. package/src/shared/interface.ts +0 -21
  621. package/src/shared/min-err.spec.js +0 -178
  622. package/src/shared/noderef.js +0 -225
  623. package/src/shared/predicates.js +0 -34
  624. package/src/shared/queue.js +0 -105
  625. package/src/shared/queue.spec.js +0 -80
  626. package/src/shared/shared.html +0 -24
  627. package/src/shared/shared.test.js +0 -12
  628. package/src/shared/strings.js +0 -142
  629. package/src/shared/strings.spec.js +0 -40
  630. package/src/shared/test-utils.js +0 -47
  631. package/src/shared/url-utils/interface.ts +0 -54
  632. package/src/shared/url-utils/url-utils.html +0 -22
  633. package/src/shared/url-utils/url-utils.js +0 -122
  634. package/src/shared/url-utils/url-utils.spec.js +0 -148
  635. package/src/shared/url-utils/url-utils.test.js +0 -12
  636. package/src/shared/utils.js +0 -1255
  637. package/src/shared/utils.spec.js +0 -178
  638. package/src/src.html +0 -21
  639. package/src/src.test.js +0 -10
  640. package/tsconfig.json +0 -19
  641. package/tsconfig.types.json +0 -14
  642. package/typedoc.json +0 -8
  643. package/utils/express.js +0 -203
  644. package/utils/version.cjs +0 -23
  645. package/vite.config.js +0 -14
@@ -1,2107 +0,0 @@
1
- import { isFunction, csp } from "../../shared/utils.js";
2
- import { createInjector } from "../di/injector.js";
3
- import { Angular } from "../../angular.js";
4
- import { wait } from "../../shared/test-utils.js";
5
-
6
- describe("parser", () => {
7
- let $rootScope;
8
- let $parse;
9
- let scope;
10
- let logs = [];
11
-
12
- beforeEach(() => {
13
- window.angular = new Angular();
14
- window.angular
15
- .module("myModule", ["ng"])
16
- .decorator("$exceptionHandler", function () {
17
- return (exception, cause) => {
18
- logs.push(exception);
19
- console.error(exception, cause);
20
- };
21
- });
22
- let injector = createInjector(["myModule"]);
23
- $parse = injector.get("$parse");
24
- $rootScope = injector.get("$rootScope");
25
- });
26
-
27
- let filterProvider;
28
-
29
- beforeEach(() => {
30
- createInjector([
31
- "ng",
32
- function ($filterProvider) {
33
- filterProvider = $filterProvider;
34
- },
35
- ]).invoke((_$rootScope_) => {
36
- $rootScope = _$rootScope_;
37
- });
38
- });
39
-
40
- [true, false].forEach((cspEnabled) => {
41
- describe(`csp: ${cspEnabled}`, () => {
42
- beforeEach(() => {
43
- createInjector([
44
- "ng",
45
- function ($filterProvider) {
46
- filterProvider = $filterProvider;
47
- },
48
- ]).invoke((_$rootScope_) => {
49
- scope = _$rootScope_;
50
- });
51
- });
52
-
53
- it("should parse expressions", () => {
54
- expect(scope.$eval("-1")).toEqual(-1);
55
- expect(scope.$eval("1 + 2.5")).toEqual(3.5);
56
- expect(scope.$eval("1 + -2.5")).toEqual(-1.5);
57
- expect(scope.$eval("1+2*3/4")).toEqual(1 + (2 * 3) / 4);
58
- expect(scope.$eval("0--1+1.5")).toEqual(0 - -1 + 1.5);
59
- expect(scope.$eval("-0--1++2*-3/-4")).toEqual(-0 - -1 + (+2 * -3) / -4);
60
- expect(scope.$eval("1/2*3")).toEqual((1 / 2) * 3);
61
- });
62
-
63
- it("should parse unary", () => {
64
- expect(scope.$eval("+1")).toEqual(+1);
65
- expect(scope.$eval("-1")).toEqual(-1);
66
- expect(scope.$eval("+'1'")).toEqual(+"1");
67
- expect(scope.$eval("-'1'")).toEqual(-"1");
68
- expect(scope.$eval("+undefined")).toEqual(0);
69
-
70
- // Note: don't change toEqual to toBe as toBe collapses 0 & -0.
71
- expect(scope.$eval("-undefined")).toEqual(-0);
72
- expect(scope.$eval("+null")).toEqual(+null);
73
- expect(scope.$eval("-null")).toEqual(-null);
74
- expect(scope.$eval("+false")).toEqual(+false);
75
- expect(scope.$eval("-false")).toEqual(-false);
76
- expect(scope.$eval("+true")).toEqual(+true);
77
- expect(scope.$eval("-true")).toEqual(-true);
78
- });
79
-
80
- it("should parse comparison", () => {
81
- expect(scope.$eval("false")).toBeFalsy();
82
- expect(scope.$eval("!true")).toBeFalsy();
83
- expect(scope.$eval("1==1")).toBeTruthy();
84
- expect(scope.$eval("1==true")).toBeTruthy();
85
- expect(scope.$eval("1!=true")).toBeFalsy();
86
- expect(scope.$eval("1===1")).toBeTruthy();
87
- expect(scope.$eval("1==='1'")).toBeFalsy();
88
- expect(scope.$eval("1===true")).toBeFalsy();
89
- expect(scope.$eval("'true'===true")).toBeFalsy();
90
- expect(scope.$eval("1!==2")).toBeTruthy();
91
- expect(scope.$eval("1!=='1'")).toBeTruthy();
92
- expect(scope.$eval("1!=2")).toBeTruthy();
93
- expect(scope.$eval("1<2")).toBeTruthy();
94
- expect(scope.$eval("1<=1")).toBeTruthy();
95
- expect(scope.$eval("1>2")).toEqual(1 > 2);
96
- expect(scope.$eval("2>=1")).toEqual(2 >= 1);
97
- expect(scope.$eval("true==2<3")).toEqual(2 < 3);
98
- expect(scope.$eval("true===2<3")).toEqual(2 < 3);
99
-
100
- expect(scope.$eval("true===3===3")).toEqual((true === 3) === 3);
101
- expect(scope.$eval("3===3===true")).toEqual(true);
102
- expect(scope.$eval("3 >= 3 > 2")).toEqual(3 >= 3 > 2);
103
- });
104
-
105
- it("should parse logical", () => {
106
- expect(scope.$eval("0&&2")).toEqual(0 && 2);
107
- expect(scope.$eval("0||2")).toEqual(0 || 2);
108
- expect(scope.$eval("0||1&&2")).toEqual(0 || (1 && 2));
109
- expect(scope.$eval("true&&a")).toEqual(undefined);
110
- expect(scope.$eval("true&&a()")).toEqual(undefined);
111
- expect(scope.$eval("true&&a()()")).toEqual(undefined);
112
- expect(scope.$eval("true&&a.b")).toEqual(undefined);
113
- expect(scope.$eval("true&&a.b.c")).toEqual(undefined);
114
- expect(scope.$eval("false||a")).toEqual(undefined);
115
- expect(scope.$eval("false||a()")).toEqual(undefined);
116
- expect(scope.$eval("false||a()()")).toEqual(undefined);
117
- expect(scope.$eval("false||a.b")).toEqual(undefined);
118
- expect(scope.$eval("false||a.b.c")).toEqual(undefined);
119
- });
120
-
121
- it("should parse ternary", () => {
122
- const returnTrue = (scope.returnTrue = function () {
123
- return true;
124
- });
125
- const returnFalse = (scope.returnFalse = function () {
126
- return false;
127
- });
128
- const returnString = (scope.returnString = function () {
129
- return "asd";
130
- });
131
- const returnInt = (scope.returnInt = function () {
132
- return 123;
133
- });
134
- const identity = (scope.identity = function (x) {
135
- return x;
136
- });
137
-
138
- // Simple.
139
- expect(scope.$eval("0?0:2")).toEqual(0 ? 0 : 2);
140
- expect(scope.$eval("1?0:2")).toEqual(1 ? 0 : 2);
141
-
142
- // Nested on the left.
143
- expect(scope.$eval("0?0?0:0:2")).toEqual(0 ? (0 ? 0 : 0) : 2);
144
- expect(scope.$eval("1?0?0:0:2")).toEqual(1 ? (0 ? 0 : 0) : 2);
145
- expect(scope.$eval("0?1?0:0:2")).toEqual(0 ? (1 ? 0 : 0) : 2);
146
- expect(scope.$eval("0?0?1:0:2")).toEqual(0 ? (0 ? 1 : 0) : 2);
147
- expect(scope.$eval("0?0?0:2:3")).toEqual(0 ? (0 ? 0 : 2) : 3);
148
- expect(scope.$eval("1?1?0:0:2")).toEqual(1 ? (1 ? 0 : 0) : 2);
149
- expect(scope.$eval("1?1?1:0:2")).toEqual(1 ? (1 ? 1 : 0) : 2);
150
- expect(scope.$eval("1?1?1:2:3")).toEqual(1 ? (1 ? 1 : 2) : 3);
151
- expect(scope.$eval("1?1?1:2:3")).toEqual(1 ? (1 ? 1 : 2) : 3);
152
-
153
- // Nested on the right.
154
- expect(scope.$eval("0?0:0?0:2")).toEqual(0 ? 0 : 0 ? 0 : 2);
155
- expect(scope.$eval("1?0:0?0:2")).toEqual(1 ? 0 : 0 ? 0 : 2);
156
- expect(scope.$eval("0?1:0?0:2")).toEqual(0 ? 1 : 0 ? 0 : 2);
157
- expect(scope.$eval("0?0:1?0:2")).toEqual(0 ? 0 : 1 ? 0 : 2);
158
- expect(scope.$eval("0?0:0?2:3")).toEqual(0 ? 0 : 0 ? 2 : 3);
159
- expect(scope.$eval("1?1:0?0:2")).toEqual(1 ? 1 : 0 ? 0 : 2);
160
- expect(scope.$eval("1?1:1?0:2")).toEqual(1 ? 1 : 1 ? 0 : 2);
161
- expect(scope.$eval("1?1:1?2:3")).toEqual(1 ? 1 : 1 ? 2 : 3);
162
- expect(scope.$eval("1?1:1?2:3")).toEqual(1 ? 1 : 1 ? 2 : 3);
163
-
164
- // Precedence with respect to logical operators.
165
- expect(scope.$eval("0&&1?0:1")).toEqual(0 && 1 ? 0 : 1);
166
- expect(scope.$eval("1||0?0:0")).toEqual(1 || 0 ? 0 : 0);
167
-
168
- expect(scope.$eval("0?0&&1:2")).toEqual(0 ? 0 && 1 : 2);
169
- expect(scope.$eval("0?1&&1:2")).toEqual(0 ? 1 && 1 : 2);
170
- expect(scope.$eval("0?0||0:1")).toEqual(0 ? 0 || 0 : 1);
171
- expect(scope.$eval("0?0||1:2")).toEqual(0 ? 0 || 1 : 2);
172
-
173
- expect(scope.$eval("1?0&&1:2")).toEqual(1 ? 0 && 1 : 2);
174
- expect(scope.$eval("1?1&&1:2")).toEqual(1 ? 1 && 1 : 2);
175
- expect(scope.$eval("1?0||0:1")).toEqual(1 ? 0 || 0 : 1);
176
- expect(scope.$eval("1?0||1:2")).toEqual(1 ? 0 || 1 : 2);
177
-
178
- expect(scope.$eval("0?1:0&&1")).toEqual(0 ? 1 : 0 && 1);
179
- expect(scope.$eval("0?2:1&&1")).toEqual(0 ? 2 : 1 && 1);
180
- expect(scope.$eval("0?1:0||0")).toEqual(0 ? 1 : 0 || 0);
181
- expect(scope.$eval("0?2:0||1")).toEqual(0 ? 2 : 0 || 1);
182
-
183
- expect(scope.$eval("1?1:0&&1")).toEqual(1 ? 1 : 0 && 1);
184
- expect(scope.$eval("1?2:1&&1")).toEqual(1 ? 2 : 1 && 1);
185
- expect(scope.$eval("1?1:0||0")).toEqual(1 ? 1 : 0 || 0);
186
- expect(scope.$eval("1?2:0||1")).toEqual(1 ? 2 : 0 || 1);
187
-
188
- // Function calls.
189
- expect(
190
- scope.$eval("returnTrue() ? returnString() : returnInt()"),
191
- ).toEqual(returnTrue() ? returnString() : returnInt());
192
- expect(
193
- scope.$eval("returnFalse() ? returnString() : returnInt()"),
194
- ).toEqual(returnFalse() ? returnString() : returnInt());
195
- expect(
196
- scope.$eval("returnTrue() ? returnString() : returnInt()"),
197
- ).toEqual(returnTrue() ? returnString() : returnInt());
198
- expect(
199
- scope.$eval("identity(returnFalse() ? returnString() : returnInt())"),
200
- ).toEqual(identity(returnFalse() ? returnString() : returnInt()));
201
- });
202
-
203
- it("should parse string", () => {
204
- expect(scope.$eval("'a' + 'b c'")).toEqual("ab c");
205
- });
206
-
207
- it("should parse filters", () => {
208
- filterProvider.register(
209
- "substring",
210
- () => (input, start, end) => input.substring(start, end),
211
- );
212
-
213
- expect(() => {
214
- scope.$eval("1|nonexistent");
215
- }).toThrowError();
216
-
217
- scope.offset = 3;
218
- expect(scope.$eval("'abcd'|substring:1:offset")).toEqual("bc");
219
- });
220
-
221
- it("should access scope", () => {
222
- scope.a = 123;
223
- scope.b = { c: 456 };
224
- expect(scope.$eval("a", scope)).toEqual(123);
225
- expect(scope.$eval("b.c", scope)).toEqual(456);
226
- expect(scope.$eval("x.y.z", scope)).not.toBeDefined();
227
- });
228
-
229
- it("should handle white-spaces around dots in paths", () => {
230
- scope.a = { b: 4 };
231
- expect(scope.$eval("a . b", scope)).toEqual(4);
232
- expect(scope.$eval("a. b", scope)).toEqual(4);
233
- expect(scope.$eval("a .b", scope)).toEqual(4);
234
- expect(scope.$eval("a . \nb", scope)).toEqual(4);
235
- });
236
-
237
- it("should handle white-spaces around dots in method invocations", () => {
238
- scope.a = {
239
- b() {
240
- return this.c;
241
- },
242
- c: 4,
243
- };
244
- expect(scope.$eval("a . b ()", scope)).toEqual(4);
245
- expect(scope.$eval("a. b ()", scope)).toEqual(4);
246
- expect(scope.$eval("a .b ()", scope)).toEqual(4);
247
- expect(scope.$eval("a \n . \nb \n ()", scope)).toEqual(4);
248
- });
249
-
250
- it("should throw syntax error exception for identifiers ending with a dot", () => {
251
- scope.a = { b: 4 };
252
-
253
- expect(() => {
254
- scope.$eval("a.", scope);
255
- }).toThrowError(/ueoe/);
256
-
257
- expect(() => {
258
- scope.$eval("a .", scope);
259
- }).toThrowError(/ueoe/);
260
- });
261
-
262
- it("should resolve deeply nested paths (important for CSP mode)", () => {
263
- scope.a = {
264
- b: {
265
- c: {
266
- d: {
267
- e: {
268
- f: {
269
- g: { h: { i: { j: { k: { l: { m: { n: "nooo!" } } } } } } },
270
- },
271
- },
272
- },
273
- },
274
- },
275
- };
276
- expect(scope.$eval("a.b.c.d.e.f.g.h.i.j.k.l.m.n", scope)).toBe("nooo!");
277
- });
278
-
279
- [2, 3, 4, 5, 6, 7, 8, 9, 10, 20, 42, 99].forEach((pathLength) => {
280
- it(`should resolve nested paths of length ${pathLength}`, () => {
281
- let i;
282
- // Create a nested object {x2: {x3: {x4: ... {x[n]: 42} ... }}}.
283
- let obj = 42;
284
- const locals = {};
285
- for (i = pathLength; i >= 2; i--) {
286
- const newObj = {};
287
- newObj[`x${i}`] = obj;
288
- obj = newObj;
289
- }
290
- // Assign to x1 and build path 'x1.x2.x3. ... .x[n]' to access the final value.
291
- scope.x1 = obj;
292
- let path = "x1";
293
- for (i = 2; i <= pathLength; i++) {
294
- path += `.x${i}`;
295
- }
296
- expect(scope.$eval(path)).toBe(42);
297
- locals[`x${pathLength}`] = "not 42";
298
- expect(scope.$eval(path, locals)).toBe(42);
299
- });
300
- });
301
-
302
- it("should be forgiving", () => {
303
- scope.a = { b: 23 };
304
- expect(scope.$eval("b")).toBeUndefined();
305
- expect(scope.$eval("a.x")).toBeUndefined();
306
- expect(scope.$eval("a.b.c.d")).toBeUndefined();
307
- scope.a = undefined;
308
- expect(scope.$eval("a - b")).toBe(0);
309
- expect(scope.$eval("a + b")).toBeUndefined();
310
- scope.a = 0;
311
- expect(scope.$eval("a - b")).toBe(0);
312
- expect(scope.$eval("a + b")).toBe(0);
313
- scope.a = undefined;
314
- scope.b = 0;
315
- expect(scope.$eval("a - b")).toBe(0);
316
- expect(scope.$eval("a + b")).toBe(0);
317
- });
318
-
319
- it("should support property names that collide with native object properties", () => {
320
- // regression
321
- scope.watch = 1;
322
- scope.toString = function toString() {
323
- return "custom toString";
324
- };
325
-
326
- expect(scope.$eval("watch", scope)).toBe(1);
327
- expect(scope.$eval("toString()", scope)).toBe("custom toString");
328
- });
329
-
330
- it("should not break if hasOwnProperty is referenced in an expression", () => {
331
- scope.obj = { value: 1 };
332
- // By evaluating an expression that calls hasOwnProperty, the getterFnCache
333
- // will store a property called hasOwnProperty. This is effectively:
334
- // getterFnCache['hasOwnProperty'] = null
335
- scope.$eval('obj.hasOwnProperty("value")');
336
- // If we rely on this property then evaluating any expression will fail
337
- // because it is not able to find out if obj.value is there in the cache
338
- expect(scope.$eval("obj.value")).toBe(1);
339
- });
340
-
341
- it('should not break if the expression is "hasOwnProperty"', () => {
342
- scope.fooExp = "barVal";
343
- // By evaluating hasOwnProperty, the $parse cache will store a getter for
344
- // the scope's own hasOwnProperty function, which will mess up future cache look ups.
345
- // i.e. cache['hasOwnProperty'] = function(scope) { return scope.hasOwnProperty; }
346
- scope.$eval("hasOwnProperty");
347
- expect(scope.$eval("fooExp")).toBe("barVal");
348
- });
349
-
350
- it("should evaluate grouped expressions", () => {
351
- expect(scope.$eval("(1+2)*3")).toEqual((1 + 2) * 3);
352
- });
353
-
354
- it("should evaluate assignments", () => {
355
- expect(scope.$eval("a=12")).toEqual(12);
356
- expect(scope.a).toEqual(12);
357
-
358
- expect(scope.$eval("x.y.z=123;")).toEqual(123);
359
- expect(scope.x.y.z).toEqual(123);
360
-
361
- expect(scope.$eval("a=123; b=234")).toEqual(234);
362
- expect(scope.a).toEqual(123);
363
- expect(scope.b).toEqual(234);
364
- });
365
-
366
- it("should throw with invalid left-val in assignments", () => {
367
- expect(() => {
368
- scope.$eval("1 = 1");
369
- }).toThrowError(/lval/);
370
- expect(() => {
371
- scope.$eval("{} = 1");
372
- }).toThrowError(/lval/);
373
- expect(() => {
374
- scope.$eval("[] = 1");
375
- }).toThrowError(/lval/);
376
- expect(() => {
377
- scope.$eval("true = 1");
378
- }).toThrowError(/lval/);
379
- expect(() => {
380
- scope.$eval("(a=b) = 1");
381
- }).toThrowError(/lval/);
382
- expect(() => {
383
- scope.$eval("(1<2) = 1");
384
- }).toThrowError(/lval/);
385
- expect(() => {
386
- scope.$eval("(1+2) = 1");
387
- }).toThrowError(/lval/);
388
- expect(() => {
389
- scope.$eval("!v = 1");
390
- }).toThrowError(/lval/);
391
- expect(() => {
392
- scope.$eval("this = 1");
393
- }).toThrowError(/lval/);
394
- expect(() => {
395
- scope.$eval("+v = 1");
396
- }).toThrowError(/lval/);
397
- expect(() => {
398
- scope.$eval("(1?v1:v2) = 1");
399
- }).toThrowError(/lval/);
400
- });
401
-
402
- it("should evaluate assignments in ternary operator", () => {
403
- scope.$eval("a = 1 ? 2 : 3");
404
- expect(scope.a).toBe(2);
405
-
406
- scope.$eval("0 ? a = 2 : a = 3");
407
- expect(scope.a).toBe(3);
408
-
409
- scope.$eval("1 ? a = 2 : a = 3");
410
- expect(scope.a).toBe(2);
411
- });
412
-
413
- it("should evaluate function call without arguments", () => {
414
- scope.const = function (a, b) {
415
- return 123;
416
- };
417
- expect(scope.$eval("const()")).toEqual(123);
418
- });
419
-
420
- it("should evaluate function call with arguments", () => {
421
- scope.add = function (a, b) {
422
- return a + b;
423
- };
424
- expect(scope.$eval("add(1,2)")).toEqual(3);
425
- });
426
-
427
- it("should allow filter chains as arguments", () => {
428
- scope.concat = function (a, b) {
429
- return a + b;
430
- };
431
- scope.begin = 1;
432
- scope.limit = 2;
433
- expect(
434
- scope.$eval("concat('abcd'|limitTo:limit:begin,'abcd'|limitTo:2:1)"),
435
- ).toEqual("bcbc");
436
- });
437
-
438
- it("should evaluate function call from a return value", () => {
439
- scope.getter = function () {
440
- return function () {
441
- return 33;
442
- };
443
- };
444
- expect(scope.$eval("getter()()")).toBe(33);
445
- });
446
-
447
- it("should evaluate multiplication and division", () => {
448
- scope.taxRate = 8;
449
- scope.subTotal = 100;
450
- expect(scope.$eval("taxRate / 100 * subTotal")).toEqual(8);
451
- expect(scope.$eval("subTotal * taxRate / 100")).toEqual(8);
452
- });
453
-
454
- it("should evaluate array", () => {
455
- expect(scope.$eval("[]").length).toEqual(0);
456
- expect(scope.$eval("[1, 2]").length).toEqual(2);
457
- expect(scope.$eval("[1, 2]")[0]).toEqual(1);
458
- expect(scope.$eval("[1, 2]")[1]).toEqual(2);
459
- expect(scope.$eval("[1, 2,]")[1]).toEqual(2);
460
- expect(scope.$eval("[1, 2,]").length).toEqual(2);
461
- });
462
-
463
- it("should evaluate array access", () => {
464
- expect(scope.$eval("[1][0]")).toEqual(1);
465
- expect(scope.$eval("[[1]][0][0]")).toEqual(1);
466
- expect(scope.$eval("[].length")).toEqual(0);
467
- expect(scope.$eval("[1, 2].length")).toEqual(2);
468
- });
469
-
470
- it("should evaluate object", () => {
471
- expect(scope.$eval("{}")).toEqual({});
472
- expect(scope.$eval("{a:'b'}")).toEqual({ a: "b" });
473
- expect(scope.$eval("{'a':'b'}")).toEqual({ a: "b" });
474
- expect(scope.$eval("{\"a\":'b'}")).toEqual({ a: "b" });
475
- expect(scope.$eval("{a:'b',}")).toEqual({ a: "b" });
476
- expect(scope.$eval("{'a':'b',}")).toEqual({ a: "b" });
477
- expect(scope.$eval("{\"a\":'b',}")).toEqual({ a: "b" });
478
- expect(scope.$eval("{'0':1}")).toEqual({ 0: 1 });
479
- expect(scope.$eval("{0:1}")).toEqual({ 0: 1 });
480
- expect(scope.$eval("{1:1}")).toEqual({ 1: 1 });
481
- expect(scope.$eval("{null:1}")).toEqual({ null: 1 });
482
- expect(scope.$eval("{'null':1}")).toEqual({ null: 1 });
483
- expect(scope.$eval("{false:1}")).toEqual({ false: 1 });
484
- expect(scope.$eval("{'false':1}")).toEqual({ false: 1 });
485
- expect(scope.$eval("{'':1,}")).toEqual({ "": 1 });
486
-
487
- // ES6 object initializers.
488
- expect(scope.$eval("{x, y}", { x: "foo", y: "bar" })).toEqual({
489
- x: "foo",
490
- y: "bar",
491
- });
492
- expect(scope.$eval("{[x]: x}", { x: "foo" })).toEqual({ foo: "foo" });
493
- expect(scope.$eval('{[x + "z"]: x}', { x: "foo" })).toEqual({
494
- fooz: "foo",
495
- });
496
- expect(
497
- scope.$eval(
498
- "{x, 1: x, [x = x + 1]: x, 3: x + 1, [x = x + 2]: x, 5: x + 1}",
499
- { x: 1 },
500
- ),
501
- ).toEqual({ x: 1, 1: 1, 2: 2, 3: 3, 4: 4, 5: 5 });
502
- });
503
-
504
- it("should throw syntax error exception for non constant/identifier JSON keys", () => {
505
- expect(() => {
506
- scope.$eval("{[:0}");
507
- }).toThrowError(/syntax/);
508
- expect(() => {
509
- scope.$eval("{{:0}");
510
- }).toThrowError(/syntax/);
511
- expect(() => {
512
- scope.$eval("{?:0}");
513
- }).toThrowError(/syntax/);
514
- expect(() => {
515
- scope.$eval("{):0}");
516
- }).toThrowError(/syntax/);
517
- });
518
-
519
- it("should evaluate object access", () => {
520
- expect(scope.$eval("{false:'WC', true:'CC'}[false]")).toEqual("WC");
521
- });
522
-
523
- it("should evaluate JSON", () => {
524
- expect(scope.$eval("[{}]")).toEqual([{}]);
525
- expect(scope.$eval("[{a:[]}, {b:1}]")).toEqual([{ a: [] }, { b: 1 }]);
526
- });
527
-
528
- it("should evaluate multiple statements", () => {
529
- expect(scope.$eval("a=1;b=3;a+b")).toEqual(4);
530
- expect(scope.$eval(";;1;;")).toEqual(1);
531
- });
532
-
533
- it("should evaluate object methods in correct context (this)", () => {
534
- function C() {
535
- this.a = 123;
536
- }
537
- C.prototype.getA = function () {
538
- return this.a;
539
- };
540
-
541
- scope.obj = new C();
542
- expect(scope.$eval("obj.getA()")).toEqual(123);
543
- expect(scope.$eval("obj['getA']()")).toEqual(123);
544
- });
545
-
546
- it("should evaluate methods in correct context (this) in argument", () => {
547
- function C() {
548
- this.a = 123;
549
- }
550
- C.prototype.sum = function (value) {
551
- return this.a + value;
552
- };
553
- C.prototype.getA = function () {
554
- return this.a;
555
- };
556
-
557
- scope.obj = new C();
558
- expect(scope.$eval("obj.sum(obj.getA())")).toEqual(246);
559
- expect(scope.$eval("obj['sum'](obj.getA())")).toEqual(246);
560
- });
561
-
562
- it("should evaluate objects on scope context", () => {
563
- scope.a = "abc";
564
- expect(scope.$eval("{a:a}").a).toEqual("abc");
565
- });
566
-
567
- it("should evaluate field access on function call result", () => {
568
- scope.a = function () {
569
- return { name: "misko" };
570
- };
571
- expect(scope.$eval("a().name")).toEqual("misko");
572
- });
573
-
574
- it("should evaluate field access after array access", () => {
575
- scope.items = [{}, { name: "misko" }];
576
- expect(scope.$eval("items[1].name")).toEqual("misko");
577
- });
578
-
579
- it("should evaluate array assignment", () => {
580
- scope.items = [];
581
-
582
- expect(scope.$eval('items[1] = "abc"')).toEqual("abc");
583
- expect(scope.$eval("items[1]")).toEqual("abc");
584
- });
585
-
586
- it("should evaluate grouped filters", () => {
587
- scope.name = "MISKO";
588
- expect(scope.$eval("n = (name|limitTo:2|limitTo:1)")).toEqual("M");
589
- expect(scope.$eval("n")).toEqual("M");
590
- });
591
-
592
- it("should evaluate remainder", () => {
593
- expect(scope.$eval("1%2")).toEqual(1);
594
- });
595
-
596
- it("should evaluate sum with undefined", () => {
597
- expect(scope.$eval("1+undefined")).toEqual(1);
598
- expect(scope.$eval("undefined+1")).toEqual(1);
599
- });
600
-
601
- it("should throw exception on non-closed bracket", () => {
602
- expect(() => {
603
- scope.$eval("[].count(");
604
- }).toThrowError(/ueoe/);
605
- });
606
-
607
- it("should evaluate double negation", () => {
608
- expect(scope.$eval("true")).toBeTruthy();
609
- expect(scope.$eval("!true")).toBeFalsy();
610
- expect(scope.$eval("!!true")).toBeTruthy();
611
- expect(scope.$eval('{true:"a", false:"b"}[!!true]')).toEqual("a");
612
- });
613
-
614
- it("should evaluate negation", () => {
615
- expect(scope.$eval("!false || true")).toEqual(true);
616
- expect(scope.$eval("!11 == 10")).toEqual(!11 == 10);
617
- expect(scope.$eval("12/6/2")).toEqual(12 / 6 / 2);
618
- });
619
-
620
- it("should evaluate exclamation mark", () => {
621
- expect(scope.$eval('suffix = "!"')).toEqual("!");
622
- });
623
-
624
- it("should evaluate minus", () => {
625
- expect(scope.$eval("{a:'-'}")).toEqual({ a: "-" });
626
- });
627
-
628
- it("should evaluate undefined", () => {
629
- expect(scope.$eval("undefined")).not.toBeDefined();
630
- expect(scope.$eval("a=undefined")).not.toBeDefined();
631
- expect(scope.a).not.toBeDefined();
632
- });
633
-
634
- it("should allow assignment after array dereference", () => {
635
- scope.obj = [{}];
636
- scope.$eval("obj[0].name=1");
637
- expect(scope.obj.name).toBeUndefined();
638
- expect(scope.obj[0].name).toEqual(1);
639
- });
640
-
641
- it("should short-circuit AND operator", () => {
642
- scope.run = function () {
643
- throw new Error("IT SHOULD NOT HAVE RUN");
644
- };
645
- expect(scope.$eval("false && run()")).toBe(false);
646
- expect(scope.$eval("false && true && run()")).toBe(false);
647
- });
648
-
649
- it("should short-circuit OR operator", () => {
650
- scope.run = function () {
651
- throw new Error("IT SHOULD NOT HAVE RUN");
652
- };
653
- expect(scope.$eval("true || run()")).toBe(true);
654
- expect(scope.$eval("true || false || run()")).toBe(true);
655
- });
656
-
657
- it("should throw TypeError on using a 'broken' object as a key to access a property", () => {
658
- scope.object = {};
659
- [
660
- { toString: 2 },
661
- { toString: null },
662
- {
663
- toString() {
664
- return {};
665
- },
666
- },
667
- ].forEach((brokenObject) => {
668
- scope.brokenObject = brokenObject;
669
- expect(() => {
670
- scope.$eval("object[brokenObject]");
671
- }).toThrow();
672
- });
673
- });
674
-
675
- it("should support method calls on primitive types", () => {
676
- scope.empty = "";
677
- scope.zero = 0;
678
- scope.bool = false;
679
-
680
- expect(scope.$eval("empty.substring(0)")).toBe("");
681
- expect(scope.$eval("zero.toString()")).toBe("0");
682
- expect(scope.$eval("bool.toString()")).toBe("false");
683
- });
684
-
685
- it("should evaluate expressions with line terminators", () => {
686
- scope.a = "a";
687
- scope.b = { c: "bc" };
688
- expect(
689
- scope.$eval('a + \n b.c + \r "\td" + \t \r\n\r "\r\n\n"'),
690
- ).toEqual("abc\td\r\n\n");
691
- });
692
-
693
- // https://github.com/angular/angular.js/issues/10968
694
- it("should evaluate arrays literals initializers left-to-right", () => {
695
- const s = {
696
- c() {
697
- return { b: 1 };
698
- },
699
- };
700
- expect($parse("e=1;[a=c(),d=a.b+1]")(s)).toEqual([{ b: 1 }, 2]);
701
- });
702
-
703
- it("should evaluate function arguments left-to-right", () => {
704
- const s = {
705
- c() {
706
- return { b: 1 };
707
- },
708
- i(x, y) {
709
- return [x, y];
710
- },
711
- };
712
- expect($parse("e=1;i(a=c(),d=a.b+1)")(s)).toEqual([{ b: 1 }, 2]);
713
- });
714
-
715
- it("should evaluate object properties expressions left-to-right", () => {
716
- const s = {
717
- c() {
718
- return { b: 1 };
719
- },
720
- };
721
- expect($parse("e=1;{x: a=c(), y: d=a.b+1}")(s)).toEqual({
722
- x: { b: 1 },
723
- y: 2,
724
- });
725
- });
726
-
727
- it("should call the function from the received instance and not from a new one", () => {
728
- let n = 0;
729
- scope.fn = function () {
730
- const c = n++;
731
- return {
732
- c,
733
- anotherFn() {
734
- return this.c === c;
735
- },
736
- };
737
- };
738
- expect(scope.$eval("fn().anotherFn()")).toBe(true);
739
- });
740
-
741
- it("should call the function once when it is part of the context", () => {
742
- let count = 0;
743
- scope.fn = function () {
744
- count++;
745
- return {
746
- anotherFn() {
747
- return "lucas";
748
- },
749
- };
750
- };
751
- expect(scope.$eval("fn().anotherFn()")).toBe("lucas");
752
- expect(count).toBe(1);
753
- });
754
-
755
- it("should call the function once when it is not part of the context", () => {
756
- let count = 0;
757
- scope.fn = function () {
758
- count++;
759
- return function () {
760
- return "lucas";
761
- };
762
- };
763
- expect(scope.$eval("fn()()")).toBe("lucas");
764
- expect(count).toBe(1);
765
- });
766
-
767
- it("should call the function once when it is part of the context on assignments", () => {
768
- let count = 0;
769
- const element = {};
770
- scope.fn = function () {
771
- count++;
772
- return element;
773
- };
774
- expect(scope.$eval('fn().name = "lucas"')).toBe("lucas");
775
- expect(element.name).toBe("lucas");
776
- expect(count).toBe(1);
777
- });
778
-
779
- it("should call the function once when it is part of the context on array lookups", () => {
780
- let count = 0;
781
- const element = [];
782
- scope.fn = function () {
783
- count++;
784
- return element;
785
- };
786
- expect(scope.$eval('fn()[0] = "lucas"')).toBe("lucas");
787
- expect(element[0]).toBe("lucas");
788
- expect(count).toBe(1);
789
- });
790
-
791
- it("should call the function once when it is part of the context on array lookup function", () => {
792
- let count = 0;
793
- const element = [
794
- {
795
- anotherFn() {
796
- return "lucas";
797
- },
798
- },
799
- ];
800
- scope.fn = function () {
801
- count++;
802
- return element;
803
- };
804
- expect(scope.$eval("fn()[0].anotherFn()")).toBe("lucas");
805
- expect(count).toBe(1);
806
- });
807
-
808
- it("should call the function once when it is part of the context on property lookup function", () => {
809
- let count = 0;
810
- const element = {
811
- name: {
812
- anotherFn() {
813
- return "lucas";
814
- },
815
- },
816
- };
817
- scope.fn = function () {
818
- count++;
819
- return element;
820
- };
821
- expect(scope.$eval("fn().name.anotherFn()")).toBe("lucas");
822
- expect(count).toBe(1);
823
- });
824
-
825
- it("should call the function once when it is part of a sub-expression", () => {
826
- let count = 0;
827
- scope.element = [{}];
828
- scope.fn = function () {
829
- count++;
830
- return 0;
831
- };
832
- expect(scope.$eval('element[fn()].name = "lucas"')).toBe("lucas");
833
- expect(scope.element.$target[0].name).toBe("lucas");
834
- expect(count).toBe(1);
835
- });
836
- });
837
- });
838
-
839
- describe("assignable", () => {
840
- beforeEach(() => {
841
- createInjector([
842
- "ng",
843
- function ($filterProvider) {
844
- filterProvider = $filterProvider;
845
- },
846
- ]);
847
- });
848
-
849
- it("should expose assignment function", () => {
850
- const fn = $parse("a");
851
- expect(fn.assign).toBeTruthy();
852
- const scope = {};
853
- fn.assign(scope, 123);
854
- expect(scope).toEqual({ a: 123 });
855
- });
856
-
857
- it("should return the assigned value", () => {
858
- const fn = $parse("a");
859
- const scope = {};
860
- expect(fn.assign(scope, 123)).toBe(123);
861
- const someObject = {};
862
- expect(fn.assign(scope, someObject)).toBe(someObject);
863
- });
864
-
865
- it("should expose working assignment function for expressions ending with brackets", () => {
866
- const fn = $parse('a.b["c"]');
867
- expect(fn.assign).toBeTruthy();
868
- const scope = {};
869
- fn.assign(scope, 123);
870
- expect(scope.a.b.c).toEqual(123);
871
- });
872
-
873
- it("should expose working assignment function for expressions with brackets in the middle", () => {
874
- const fn = $parse('a["b"].c');
875
- expect(fn.assign).toBeTruthy();
876
- const scope = {};
877
- fn.assign(scope, 123);
878
- expect(scope.a.b.c).toEqual(123);
879
- });
880
-
881
- it("should create objects when finding a null", () => {
882
- const fn = $parse("foo.bar");
883
- const scope = { foo: null };
884
- fn.assign(scope, 123);
885
- expect(scope.foo.bar).toEqual(123);
886
- });
887
-
888
- it("should create objects when finding a null", () => {
889
- const fn = $parse('foo["bar"]');
890
- const scope = { foo: null };
891
- fn.assign(scope, 123);
892
- expect(scope.foo.bar).toEqual(123);
893
- });
894
-
895
- it("should create objects when finding a null", () => {
896
- const fn = $parse("foo.bar.baz");
897
- const scope = { foo: null };
898
- fn.assign(scope, 123);
899
- expect(scope.foo.bar.baz).toEqual(123);
900
- });
901
- });
902
-
903
- describe("watched $parse expressions", () => {
904
- beforeEach(() => {
905
- createInjector(["ng"]).invoke((_$rootScope_) => {
906
- scope = _$rootScope_;
907
- });
908
- });
909
-
910
- it("should respect short-circuiting AND if it could have side effects", async () => {
911
- let bCalled = 0;
912
- let called = false;
913
- scope.b = function () {
914
- bCalled++;
915
- return true;
916
- };
917
-
918
- scope.$watch("a && b()", () => {
919
- called = true;
920
- });
921
- await wait();
922
- expect(bCalled).toBe(0);
923
- expect(called).toBe(false);
924
-
925
- scope.a = true;
926
- await wait();
927
- expect(called).toBe(true);
928
- expect(bCalled).toBe(1);
929
-
930
- scope.a = false;
931
- scope.a = true;
932
- await wait();
933
- expect(bCalled).toBe(3);
934
- });
935
-
936
- it("should respect short-circuiting OR if it could have side effects", async () => {
937
- let bCalled = false;
938
- scope.b = function () {
939
- bCalled = true;
940
- return true;
941
- };
942
-
943
- scope.$watch("a || b()", () => {});
944
- await wait();
945
- expect(bCalled).toBe(false);
946
-
947
- scope.a = true;
948
- await wait();
949
- expect(bCalled).toBe(false);
950
-
951
- scope.a = false;
952
- await wait();
953
- expect(bCalled).toBe(true);
954
- });
955
-
956
- it("should respect the branching ternary operator if it could have side effects", async () => {
957
- let bCalled = false;
958
- scope.b = function () {
959
- bCalled = true;
960
- };
961
-
962
- scope.$watch("a ? b() : 1", () => {});
963
- await wait();
964
- expect(bCalled).toBe(false);
965
-
966
- scope.a = true;
967
- await wait();
968
- expect(bCalled).toBe(true);
969
- });
970
- });
971
-
972
- describe("filters", () => {
973
- beforeEach(() => {
974
- createInjector([
975
- "ng",
976
- function ($filterProvider) {
977
- filterProvider = $filterProvider;
978
- },
979
- ]).invoke((_$rootScope_, _$parse_) => {
980
- scope = _$rootScope_;
981
- $parse = _$parse_;
982
- });
983
- logs = [];
984
- });
985
-
986
- it("should be invoked when the input/arguments change", async () => {
987
- let filterCalled = false;
988
- filterProvider.register("foo", () => (input) => {
989
- filterCalled = true;
990
- return input;
991
- });
992
-
993
- scope.$watch("a | foo:b:1", () => {});
994
- await wait();
995
- expect(filterCalled).toBe(true);
996
-
997
- filterCalled = false;
998
-
999
- scope.a = 0;
1000
- await wait();
1001
- expect(filterCalled).toBe(true);
1002
-
1003
- filterCalled = false;
1004
-
1005
- scope.a++;
1006
- await wait();
1007
- expect(filterCalled).toBe(true);
1008
- });
1009
-
1010
- it("should not be invoked unless the input/arguments change within literals", async () => {
1011
- const filterCalls = [];
1012
- filterProvider.register("foo", () => (input) => {
1013
- filterCalls.push(input);
1014
- return input;
1015
- });
1016
-
1017
- scope.$watch("[(a | foo:b:1), undefined]", () => {});
1018
-
1019
- scope.a = 0;
1020
- await wait();
1021
- expect(filterCalls).toEqual([0, 0]);
1022
-
1023
- scope.a++;
1024
- await wait();
1025
- expect(filterCalls).toEqual([0, 0, 1]);
1026
- });
1027
-
1028
- it("should be treated as constant when input are constant", async () => {
1029
- let filterCalls = 0;
1030
- filterProvider.register("foo", () => (input) => {
1031
- filterCalls++;
1032
- return input;
1033
- });
1034
-
1035
- const parsed = $parse("{x: 1} | foo:1");
1036
- expect(parsed.constant).toBe(true);
1037
-
1038
- let watcherCalls = 0;
1039
- scope.$watch("{x: 1} | foo:1", (input) => {
1040
- expect(input).toEqual({ x: 1 });
1041
- watcherCalls++;
1042
- });
1043
-
1044
- // await wait();
1045
- // expect(filterCalls).toBe(1);
1046
- // expect(watcherCalls).toBe(1);
1047
-
1048
- // await wait();
1049
- // expect(filterCalls).toBe(1);
1050
- // expect(watcherCalls).toBe(1);
1051
- });
1052
-
1053
- it("should ignore changes within nested objects", async () => {
1054
- const watchCalls = [];
1055
- scope.$watch("[a]", (a) => {
1056
- watchCalls.push(a[0]);
1057
- });
1058
- scope.a = 0;
1059
- await wait();
1060
- expect(watchCalls).toEqual([0, 0]);
1061
-
1062
- scope.a++;
1063
- await wait();
1064
- expect(watchCalls).toEqual([0, 0, 1]);
1065
-
1066
- scope.a = {};
1067
- await wait();
1068
- expect(watchCalls).toEqual([0, 0, 1, {}]);
1069
-
1070
- scope.a.foo = 42;
1071
- await wait();
1072
- expect(watchCalls).toEqual([0, 0, 1, { foo: 42 }]);
1073
- });
1074
- });
1075
-
1076
- describe("with non-primitive input", () => {
1077
- beforeEach(() => {
1078
- createInjector([
1079
- "ng",
1080
- function ($filterProvider) {
1081
- filterProvider = $filterProvider;
1082
- },
1083
- ]).invoke((_$rootScope_, _$parse_) => {
1084
- scope = _$rootScope_;
1085
- $parse = _$parse_;
1086
- });
1087
- logs = [];
1088
- });
1089
-
1090
- describe("that does NOT support valueOf()", () => {
1091
- it("should always be reevaluated", async () => {
1092
- let filterCalls = 0;
1093
- filterProvider.register("foo", () => (input) => {
1094
- filterCalls++;
1095
- return input;
1096
- });
1097
-
1098
- scope.obj = {};
1099
-
1100
- let watcherCalls = 0;
1101
- scope.$watch("obj | foo", (input) => {
1102
- watcherCalls++;
1103
- });
1104
-
1105
- await wait();
1106
- expect(filterCalls).toBe(1);
1107
- expect(watcherCalls).toBe(1);
1108
- });
1109
-
1110
- it("should always be reevaluated in literals", async () => {
1111
- filterProvider.register("foo", () => (input) => input.b > 0);
1112
-
1113
- scope.$watch("[(a | foo)]", () => {});
1114
- scope.$apply("a = {b: 1}");
1115
- await wait();
1116
- // Would be great if filter-output was checked for changes and this didn't throw...
1117
- expect(async () => {
1118
- scope.$apply("a = {b: 1}");
1119
- await wait();
1120
- }).not.toThrow();
1121
- });
1122
-
1123
- it("should always be reevaluated when passed literals", () => {
1124
- scope.$watch("[a] | filter", () => {});
1125
-
1126
- scope.$apply("a = 1");
1127
-
1128
- // Would be great if filter-output was checked for changes and this didn't throw...
1129
- expect(async () => {
1130
- scope.$apply("a = {}");
1131
- await wait();
1132
- }).not.toThrow();
1133
- });
1134
- });
1135
-
1136
- describe("that does support valueOf()", () => {
1137
- it("should not be reevaluated", async () => {
1138
- let filterCalls = 0;
1139
- filterProvider.register("foo", () => (input) => {
1140
- filterCalls++;
1141
- expect(input instanceof Date).toBe(true);
1142
- return input;
1143
- });
1144
-
1145
- const date = (scope.date = new Date());
1146
-
1147
- let watcherCalls = 0;
1148
- scope.$watch("date | foo:a", (input) => {
1149
- watcherCalls++;
1150
- });
1151
-
1152
- await wait();
1153
- expect(filterCalls).toBe(2);
1154
- expect(watcherCalls).toBe(2);
1155
- });
1156
-
1157
- it("should not be reevaluated in literals", async () => {
1158
- let filterCalls = 0;
1159
- filterProvider.register("foo", () => (input) => {
1160
- filterCalls++;
1161
- return input;
1162
- });
1163
-
1164
- let watcherCalls = 0;
1165
- scope.$watch("[(date | foo)]", (input) => {
1166
- watcherCalls++;
1167
- });
1168
-
1169
- scope.date = new Date(1234567890123);
1170
-
1171
- await wait();
1172
-
1173
- expect(filterCalls).toBe(2);
1174
- expect(watcherCalls).toBe(2);
1175
-
1176
- scope.date = new Date(1234567890124);
1177
-
1178
- await wait();
1179
- expect(filterCalls).toBe(3);
1180
- expect(watcherCalls).toBe(3);
1181
- });
1182
-
1183
- it("should be reevaluated when valueOf() changes", async () => {
1184
- let filterCalls = 0;
1185
- filterProvider.register("foo", () => (input) => {
1186
- filterCalls++;
1187
- return input;
1188
- });
1189
-
1190
- let watcherCalls = 0;
1191
-
1192
- scope.date = new Date();
1193
- scope.$watch("date | foo:a", (input) => {
1194
- watcherCalls++;
1195
- });
1196
-
1197
- await wait();
1198
- expect(filterCalls).toBe(2);
1199
- expect(watcherCalls).toBe(2);
1200
-
1201
- scope.date = new Date();
1202
-
1203
- await wait();
1204
- expect(filterCalls).toBe(3);
1205
- expect(watcherCalls).toBe(3);
1206
- });
1207
-
1208
- it("should be reevaluated in literals when valueOf() changes", async () => {
1209
- let filterCalls = 0;
1210
- filterProvider.register("foo", () => (input) => {
1211
- filterCalls++;
1212
- return input;
1213
- });
1214
-
1215
- scope.date = new Date(1234567890123);
1216
-
1217
- let watcherCalls = 0;
1218
- scope.$watch("[(date | foo)]", (input) => {
1219
- watcherCalls++;
1220
- });
1221
-
1222
- await wait();
1223
- expect(filterCalls).toBe(1);
1224
- expect(watcherCalls).toBe(1);
1225
-
1226
- scope.date = new Date(1234567890133);
1227
-
1228
- await wait();
1229
- expect(filterCalls).toBe(2);
1230
- expect(watcherCalls).toBe(2);
1231
- });
1232
-
1233
- it("should not be reevaluated when the instance changes but valueOf() does not", async () => {
1234
- let filterCalls = 0;
1235
- filterProvider.register("foo", () => (input) => {
1236
- filterCalls++;
1237
- return input;
1238
- });
1239
-
1240
- scope.date = new Date(1234567890123);
1241
-
1242
- let watcherCalls = 0;
1243
- scope.$watch("[(date | foo)]", (input) => {
1244
- watcherCalls++;
1245
- });
1246
-
1247
- await wait();
1248
- expect(watcherCalls).toBe(1);
1249
- expect(filterCalls).toBe(1);
1250
-
1251
- scope.date = new Date(1234567890123);
1252
- await wait();
1253
- expect(watcherCalls).toBe(2);
1254
- expect(filterCalls).toBe(2);
1255
- });
1256
- });
1257
-
1258
- it("should not be reevaluated when input is simplified via unary operators", async () => {
1259
- let filterCalls = 0;
1260
- filterProvider.register("foo", () => (input) => {
1261
- filterCalls++;
1262
- return input;
1263
- });
1264
-
1265
- scope.obj = {};
1266
-
1267
- let watcherCalls = 0;
1268
- scope.$watch("!obj | foo:!obj", (input) => {
1269
- watcherCalls++;
1270
- });
1271
-
1272
- await wait();
1273
- expect(filterCalls).toBe(2);
1274
- expect(watcherCalls).toBe(2);
1275
-
1276
- await wait();
1277
- expect(filterCalls).toBe(2);
1278
- expect(watcherCalls).toBe(2);
1279
- });
1280
-
1281
- it("should not be reevaluated when input is simplified via non-plus/concat binary operators", async () => {
1282
- let filterCalls = 0;
1283
- filterProvider.register("foo", () => (input) => {
1284
- filterCalls++;
1285
- return input;
1286
- });
1287
-
1288
- scope.obj = {};
1289
-
1290
- let watcherCalls = 0;
1291
- scope.$watch("1 - obj | foo:(1 * obj)", (input) => {
1292
- watcherCalls++;
1293
- });
1294
-
1295
- await wait();
1296
- expect(filterCalls).toBe(2);
1297
- expect(watcherCalls).toBe(2);
1298
-
1299
- await wait();
1300
- expect(filterCalls).toBe(2);
1301
- expect(watcherCalls).toBe(2);
1302
- });
1303
-
1304
- it("should be reevaluated when input is simplified via plus/concat", async () => {
1305
- let filterCalls = 0;
1306
- filterProvider.register("foo", () => (input) => {
1307
- filterCalls++;
1308
- return input;
1309
- });
1310
-
1311
- scope.obj = {};
1312
-
1313
- let watcherCalls = 0;
1314
- scope.$watch("1 + obj | foo", (input) => {
1315
- watcherCalls++;
1316
- });
1317
-
1318
- await wait();
1319
- expect(filterCalls).toBe(1);
1320
- expect(watcherCalls).toBe(1);
1321
-
1322
- await wait();
1323
- expect(filterCalls).toBe(1);
1324
- expect(watcherCalls).toBe(1);
1325
- });
1326
- });
1327
-
1328
- describe("with primitive input", () => {
1329
- beforeEach(() => {
1330
- createInjector([
1331
- "ng",
1332
- function ($filterProvider) {
1333
- filterProvider = $filterProvider;
1334
- },
1335
- ]).invoke((_$rootScope_, _$parse_) => {
1336
- scope = _$rootScope_;
1337
- $parse = _$parse_;
1338
- });
1339
- logs = [];
1340
- });
1341
-
1342
- it("should not be reevaluated when passed literals", async () => {
1343
- let filterCalls = 0;
1344
- filterProvider.register("foo", () => (input) => {
1345
- filterCalls++;
1346
- return input;
1347
- });
1348
-
1349
- let watcherCalls = 0;
1350
- scope.$watch("[a] | foo", (input) => {
1351
- watcherCalls++;
1352
- });
1353
-
1354
- scope.$apply("a = 1");
1355
- await wait();
1356
- expect(filterCalls).toBe(2);
1357
- expect(watcherCalls).toBe(2);
1358
-
1359
- scope.$apply("a = 2");
1360
- await wait();
1361
- expect(filterCalls).toBe(3);
1362
- expect(watcherCalls).toBe(3);
1363
- });
1364
-
1365
- it("should not be reevaluated in literals", async () => {
1366
- let filterCalls = 0;
1367
- filterProvider.register("foo", () => (input) => {
1368
- filterCalls++;
1369
- return input;
1370
- });
1371
-
1372
- scope.prim = 1234567890123;
1373
-
1374
- let watcherCalls = 0;
1375
- scope.$watch("[(prim | foo)]", (input) => {
1376
- watcherCalls++;
1377
- });
1378
-
1379
- await wait();
1380
- expect(filterCalls).toBe(1);
1381
- expect(watcherCalls).toBe(1);
1382
-
1383
- await wait();
1384
- expect(filterCalls).toBe(1);
1385
- expect(watcherCalls).toBe(1);
1386
- });
1387
- });
1388
-
1389
- describe("literals", () => {
1390
- beforeEach(() => {
1391
- createInjector([
1392
- "ng",
1393
- function ($filterProvider) {
1394
- filterProvider = $filterProvider;
1395
- },
1396
- ]).invoke((_$rootScope_, _$parse_) => {
1397
- scope = _$rootScope_;
1398
- $parse = _$parse_;
1399
- });
1400
- logs = [];
1401
- });
1402
-
1403
- it("should mark an empty expressions as literal", () => {
1404
- expect($parse("").literal).toBe(true);
1405
- expect($parse(" ").literal).toBe(true);
1406
- });
1407
-
1408
- it("should support watching", async () => {
1409
- let lastVal = NaN;
1410
- let callCount = 0;
1411
- const listener = function (val) {
1412
- callCount++;
1413
- lastVal = val;
1414
- };
1415
-
1416
- scope.$watch("{val: val}", listener);
1417
- await wait();
1418
- expect(callCount).toBe(1);
1419
-
1420
- scope.$apply("val = 1");
1421
- await wait();
1422
- expect(callCount).toBe(2);
1423
- expect(lastVal).toEqual({ val: 1 });
1424
-
1425
- scope.$apply("val = []");
1426
- await wait();
1427
- expect(callCount).toBe(3);
1428
- expect(lastVal).toEqual({ val: [] });
1429
-
1430
- scope.$apply("val = []");
1431
- await wait();
1432
- expect(callCount).toBe(4);
1433
- expect(lastVal).toEqual({ val: [] });
1434
-
1435
- scope.$apply("val = {}");
1436
- await wait();
1437
- expect(callCount).toBe(5);
1438
- expect(lastVal).toEqual({ val: {} });
1439
- });
1440
-
1441
- it("should only watch the direct inputs", async () => {
1442
- let lastVal = NaN;
1443
- let callCount = 0;
1444
- const listener = function (val) {
1445
- callCount++;
1446
- lastVal = val;
1447
- };
1448
-
1449
- scope.$watch("{val: val}", listener);
1450
- scope.$apply("val = 1");
1451
- await wait();
1452
- expect(callCount).toBe(2);
1453
- expect(lastVal).toEqual({ val: 1 });
1454
-
1455
- scope.$apply("val = [2]");
1456
- await wait();
1457
- expect(callCount).toBe(3);
1458
- expect(lastVal).toEqual({ val: [2] });
1459
-
1460
- scope.$apply("val.push(3)");
1461
- await wait();
1462
- expect(callCount).toBe(3);
1463
-
1464
- scope.$apply("val.length = 0");
1465
- await wait();
1466
- expect(callCount).toBe(3);
1467
- });
1468
-
1469
- it("should only watch the direct inputs when nested", async () => {
1470
- let callCount = 0;
1471
- const listener = function (val) {
1472
- callCount++;
1473
- };
1474
-
1475
- scope.$watch("[{val: [val]}]", listener);
1476
- scope.$apply("val = 1");
1477
- await wait();
1478
- expect(callCount).toBe(2);
1479
-
1480
- scope.$apply("val = [2]");
1481
- await wait();
1482
- expect(callCount).toBe(3);
1483
-
1484
- scope.$apply("val.push(3)");
1485
- await wait();
1486
- expect(callCount).toBe(3);
1487
-
1488
- scope.$apply("val.length = 0");
1489
- await wait();
1490
- expect(callCount).toBe(3);
1491
- });
1492
- });
1493
-
1494
- describe("with non-primative input", () => {
1495
- beforeEach(() => {
1496
- createInjector([
1497
- "ng",
1498
- function ($filterProvider) {
1499
- filterProvider = $filterProvider;
1500
- },
1501
- ]).invoke((_$rootScope_, _$parse_) => {
1502
- scope = _$rootScope_;
1503
- $parse = _$parse_;
1504
- });
1505
- logs = [];
1506
- });
1507
-
1508
- describe("that does NOT support valueOf()", () => {
1509
- it("should not be reevaluated", async () => {
1510
- const obj = (scope.obj = {});
1511
- let watcherCalls = 0;
1512
- scope.$watch("[obj]", (input) => {
1513
- watcherCalls++;
1514
- });
1515
-
1516
- await wait();
1517
- expect(watcherCalls).toBe(1);
1518
-
1519
- await wait();
1520
- expect(watcherCalls).toBe(1);
1521
- });
1522
- });
1523
-
1524
- describe("that does support valueOf()", () => {
1525
- it("should not be reevaluated", async () => {
1526
- const date = (scope.date = new Date());
1527
- let watcherCalls = 0;
1528
- scope.$watch("[date]", () => {
1529
- watcherCalls++;
1530
- });
1531
-
1532
- await wait();
1533
- expect(watcherCalls).toBe(1);
1534
-
1535
- await wait();
1536
- expect(watcherCalls).toBe(1);
1537
- });
1538
-
1539
- it("should be reevaluated even when valueOf() changes", async () => {
1540
- scope.date = new Date();
1541
- let watcherCalls = 0;
1542
- scope.$watch("[date]", () => {
1543
- watcherCalls++;
1544
- });
1545
-
1546
- await wait();
1547
- expect(watcherCalls).toBe(1);
1548
-
1549
- scope.date = new Date();
1550
-
1551
- await wait();
1552
- expect(watcherCalls).toBe(2);
1553
- });
1554
-
1555
- xit("should be reevaluated when the instance changes but valueOf() does not", async () => {
1556
- scope.date = new Date(1234567890123);
1557
- let watcherCalls = 0;
1558
- scope.$watch("[date]", (input) => {
1559
- watcherCalls++;
1560
- });
1561
-
1562
- await wait();
1563
- expect(watcherCalls).toBe(1);
1564
-
1565
- scope.date = new Date(1234567890123);
1566
- await wait();
1567
- expect(watcherCalls).toBe(1);
1568
- });
1569
-
1570
- xit("should be reevaluated when the instance does not change but valueOf() does", async () => {
1571
- scope.date = new Date(1234567890123);
1572
- let watcherCalls = 0;
1573
- scope.$watch("[date]", () => {
1574
- watcherCalls++;
1575
- });
1576
-
1577
- await wait();
1578
- expect(watcherCalls).toBe(1);
1579
-
1580
- scope.date.setTime(scope.date.getTime() + 1);
1581
- await wait();
1582
- expect(watcherCalls).toBe(2);
1583
- });
1584
- });
1585
-
1586
- xit("should invoke all statements in multi-statement expressions", async () => {
1587
- let lastVal = NaN;
1588
- const listener = function (val) {
1589
- lastVal = val;
1590
- };
1591
-
1592
- scope.setBarToOne = false;
1593
- scope.bar = 0;
1594
- scope.two = 2;
1595
- scope.foo = function () {
1596
- if (scope.setBarToOne) scope.bar = 1;
1597
- };
1598
-
1599
- scope.$watch("foo(); bar + two", listener);
1600
-
1601
- await wait();
1602
- expect(lastVal).toBe(2);
1603
-
1604
- scope.bar = 2;
1605
- await wait();
1606
- expect(lastVal).toBe(4);
1607
-
1608
- scope.setBarToOne = true;
1609
- await wait();
1610
- expect(lastVal).toBe(3);
1611
- });
1612
-
1613
- xit("should watch the left side of assignments", async () => {
1614
- let lastVal = NaN;
1615
- const listener = function (val) {
1616
- lastVal = val;
1617
- };
1618
-
1619
- const objA = {};
1620
- const objB = {};
1621
-
1622
- scope.$watch("curObj.value = input", () => {});
1623
-
1624
- scope.curObj = objA;
1625
- scope.input = 1;
1626
- await wait();
1627
- expect(objA.value).toBe(scope.input);
1628
-
1629
- scope.curObj = objB;
1630
- await wait();
1631
- expect(objB.value).toBe(scope.input);
1632
-
1633
- scope.input = 2;
1634
- await wait();
1635
- expect(objB.value).toBe(scope.input);
1636
- });
1637
-
1638
- it("should watch ES6 object computed property changes", async () => {
1639
- let count = 0;
1640
- let lastValue;
1641
-
1642
- scope.$watch("{[a]: true}", (val) => {
1643
- count++;
1644
- lastValue = val;
1645
- });
1646
-
1647
- await wait();
1648
- expect(count).toBe(1);
1649
- expect(lastValue).toEqual({ undefined: true });
1650
-
1651
- await wait();
1652
- expect(count).toBe(1);
1653
- expect(lastValue).toEqual({ undefined: true });
1654
-
1655
- scope.a = true;
1656
- await wait();
1657
- expect(count).toBe(2);
1658
- expect(lastValue).toEqual({ true: true });
1659
-
1660
- scope.a = "abc";
1661
- await wait();
1662
- expect(count).toBe(3);
1663
- expect(lastValue).toEqual({ abc: true });
1664
-
1665
- scope.a = undefined;
1666
- await wait();
1667
- expect(count).toBe(4);
1668
- expect(lastValue).toEqual({ undefined: true });
1669
- });
1670
-
1671
- it("should not shallow-watch ES6 object computed properties in case of stateful toString", async () => {
1672
- let count = 0;
1673
- let lastValue;
1674
-
1675
- scope.$watch("{[a]: true}", (val) => {
1676
- count++;
1677
- lastValue = val;
1678
- });
1679
-
1680
- scope.a = {
1681
- toString() {
1682
- return this.b;
1683
- },
1684
- };
1685
- scope.a.b = 1;
1686
- await wait();
1687
-
1688
- expect(lastValue).toEqual({ 1: true });
1689
- scope.$apply("a.b = 2");
1690
- await wait();
1691
- expect(lastValue).toEqual({ 2: true });
1692
- });
1693
-
1694
- describe("locals", () => {
1695
- it("should expose local variables", () => {
1696
- expect($parse("a")({ a: 0 }, { a: 1 })).toEqual(1);
1697
- expect(
1698
- $parse("add(a,b)")(
1699
- {
1700
- b: 1,
1701
- add(a, b) {
1702
- return a + b;
1703
- },
1704
- },
1705
- { a: 2 },
1706
- ),
1707
- ).toEqual(3);
1708
- });
1709
-
1710
- it("should expose traverse locals", () => {
1711
- expect($parse("a.b")({ a: { b: 0 } }, { a: { b: 1 } })).toEqual(1);
1712
- expect($parse("a.b")({ a: null }, { a: { b: 1 } })).toEqual(1);
1713
- expect($parse("a.b")({ a: { b: 0 } }, { a: null })).toEqual(undefined);
1714
- expect($parse("a.b.c")({ a: null }, { a: { b: { c: 1 } } })).toEqual(1);
1715
- });
1716
-
1717
- it("should not use locals to resolve object properties", () => {
1718
- expect($parse("a[0].b")({ a: [{ b: "scope" }] }, { b: "locals" })).toBe(
1719
- "scope",
1720
- );
1721
- expect(
1722
- $parse('a[0]["b"]')({ a: [{ b: "scope" }] }, { b: "locals" }),
1723
- ).toBe("scope");
1724
- expect(
1725
- $parse("a[0][0].b")({ a: [[{ b: "scope" }]] }, { b: "locals" }),
1726
- ).toBe("scope");
1727
- expect(
1728
- $parse("a[0].b.c")(
1729
- { a: [{ b: { c: "scope" } }] },
1730
- { b: { c: "locals" } },
1731
- ),
1732
- ).toBe("scope");
1733
- });
1734
-
1735
- it("should assign directly to locals when the local property exists", () => {
1736
- const s = {};
1737
- const l = {};
1738
-
1739
- $parse("a = 1")(s, l);
1740
- expect(s.a).toBe(1);
1741
- expect(l.a).toBeUndefined();
1742
-
1743
- l.a = 2;
1744
- $parse("a = 0")(s, l);
1745
- expect(s.a).toBe(1);
1746
- expect(l.a).toBe(0);
1747
-
1748
- $parse("toString = 1")(s, l);
1749
- expect(isFunction(s.toString)).toBe(true);
1750
- expect(l.toString).toBe(1);
1751
- });
1752
-
1753
- it("should overwrite undefined / null scope properties when assigning", () => {
1754
- let scope;
1755
-
1756
- scope = {};
1757
- $parse("a.b = 1")(scope);
1758
- $parse('c["d"] = 2')(scope);
1759
- expect(scope).toEqual({ a: { b: 1 }, c: { d: 2 } });
1760
-
1761
- scope = { a: {} };
1762
- $parse("a.b.c = 1")(scope);
1763
- $parse('a.c["d"] = 2')(scope);
1764
- expect(scope).toEqual({ a: { b: { c: 1 }, c: { d: 2 } } });
1765
-
1766
- scope = { a: undefined, c: undefined };
1767
- $parse("a.b = 1")(scope);
1768
- $parse('c["d"] = 2')(scope);
1769
- expect(scope).toEqual({ a: { b: 1 }, c: { d: 2 } });
1770
-
1771
- scope = { a: { b: undefined, c: undefined } };
1772
- $parse("a.b.c = 1")(scope);
1773
- $parse('a.c["d"] = 2')(scope);
1774
- expect(scope).toEqual({ a: { b: { c: 1 }, c: { d: 2 } } });
1775
-
1776
- scope = { a: null, c: null };
1777
- $parse("a.b = 1")(scope);
1778
- $parse('c["d"] = 2')(scope);
1779
- expect(scope).toEqual({ a: { b: 1 }, c: { d: 2 } });
1780
-
1781
- scope = { a: { b: null, c: null } };
1782
- $parse("a.b.c = 1")(scope);
1783
- $parse('a.c["d"] = 2')(scope);
1784
- expect(scope).toEqual({ a: { b: { c: 1 }, c: { d: 2 } } });
1785
- });
1786
-
1787
- [0, false, "", NaN].forEach((falsyValue) => {
1788
- it("should not overwrite $prop scope properties when assigning", () => {
1789
- let scope;
1790
-
1791
- scope = { a: falsyValue, c: falsyValue };
1792
- tryParseAndIgnoreException("a.b = 1");
1793
- tryParseAndIgnoreException('c["d"] = 2');
1794
- expect(scope).toEqual({ a: falsyValue, c: falsyValue });
1795
-
1796
- scope = { a: { b: falsyValue, c: falsyValue } };
1797
- tryParseAndIgnoreException("a.b.c = 1");
1798
- tryParseAndIgnoreException('a.c["d"] = 2');
1799
- expect(scope).toEqual({ a: { b: falsyValue, c: falsyValue } });
1800
-
1801
- // Helpers
1802
- //
1803
- // Normally assigning property on a primitive should throw exception in strict mode
1804
- // and silently fail in non-strict mode, IE seems to always have the non-strict-mode behavior,
1805
- // so if we try to use 'expect(() => {$parse('a.b=1')({a:false});).toThrow()' for testing
1806
- // the test will fail in case of IE because it will not throw exception, and if we just use
1807
- // '$parse('a.b=1')({a:false})' the test will fail because it will throw exception in case of Chrome
1808
- // so we use tryParseAndIgnoreException helper to catch the exception silently for all cases.
1809
- //
1810
- function tryParseAndIgnoreException(expression) {
1811
- try {
1812
- $parse(expression)(scope);
1813
- } catch (error) {
1814
- /* ignore exception */
1815
- }
1816
- }
1817
- });
1818
- });
1819
- });
1820
-
1821
- describe("literal", () => {
1822
- it("should mark scalar value expressions as literal", () => {
1823
- expect($parse("0").literal).toBe(true);
1824
- expect($parse('"hello"').literal).toBe(true);
1825
- expect($parse("true").literal).toBe(true);
1826
- expect($parse("false").literal).toBe(true);
1827
- expect($parse("null").literal).toBe(true);
1828
- expect($parse("undefined").literal).toBe(true);
1829
- });
1830
-
1831
- it("should mark array expressions as literal", () => {
1832
- expect($parse("[]").literal).toBe(true);
1833
- expect($parse("[1, 2, 3]").literal).toBe(true);
1834
- expect($parse("[1, identifier]").literal).toBe(true);
1835
- });
1836
-
1837
- it("should mark object expressions as literal", () => {
1838
- expect($parse("{}").literal).toBe(true);
1839
- expect($parse("{x: 1}").literal).toBe(true);
1840
- expect($parse("{foo: bar}").literal).toBe(true);
1841
- });
1842
-
1843
- it("should not mark function calls or operator expressions as literal", () => {
1844
- expect($parse("1 + 1").literal).toBe(false);
1845
- expect($parse("call()").literal).toBe(false);
1846
- expect($parse("[].length").literal).toBe(false);
1847
- });
1848
- });
1849
-
1850
- describe("constant", () => {
1851
- it("should mark an empty expressions as constant", () => {
1852
- expect($parse("").constant).toBe(true);
1853
- expect($parse(" ").constant).toBe(true);
1854
- });
1855
-
1856
- it("should mark scalar value expressions as constant", () => {
1857
- expect($parse("12.3").constant).toBe(true);
1858
- expect($parse('"string"').constant).toBe(true);
1859
- expect($parse("true").constant).toBe(true);
1860
- expect($parse("false").constant).toBe(true);
1861
- expect($parse("null").constant).toBe(true);
1862
- expect($parse("undefined").constant).toBe(true);
1863
- });
1864
-
1865
- it("should mark arrays as constant if they only contain constant elements", () => {
1866
- expect($parse("[]").constant).toBe(true);
1867
- expect($parse("[1, 2, 3]").constant).toBe(true);
1868
- expect($parse('["string", null]').constant).toBe(true);
1869
- expect($parse("[[]]").constant).toBe(true);
1870
- expect($parse("[1, [2, 3], {4: 5}]").constant).toBe(true);
1871
- });
1872
-
1873
- it("should not mark arrays as constant if they contain any non-constant elements", () => {
1874
- expect($parse("[foo]").constant).toBe(false);
1875
- expect($parse("[x + 1]").constant).toBe(false);
1876
- expect($parse("[bar[0]]").constant).toBe(false);
1877
- });
1878
-
1879
- it("should mark complex expressions involving constant values as constant", () => {
1880
- expect($parse("!true").constant).toBe(true);
1881
- expect($parse("-42").constant).toBe(true);
1882
- expect($parse("1 - 1").constant).toBe(true);
1883
- expect($parse('"foo" + "bar"').constant).toBe(true);
1884
- expect($parse("5 != null").constant).toBe(true);
1885
- expect($parse("{standard: 4/3, wide: 16/9}").constant).toBe(true);
1886
- expect($parse("{[standard]: 4/3, wide: 16/9}").constant).toBe(false);
1887
- expect($parse('{["key"]: 1}').constant).toBe(true);
1888
- expect($parse("[0].length").constant).toBe(true);
1889
- expect($parse("[0][0]").constant).toBe(true);
1890
- expect($parse("{x: 1}.x").constant).toBe(true);
1891
- expect($parse('{x: 1}["x"]').constant).toBe(true);
1892
- });
1893
-
1894
- it("should not mark any expression involving variables or function calls as constant", () => {
1895
- expect($parse("true.toString()").constant).toBe(false);
1896
- expect($parse("foo(1, 2, 3)").constant).toBe(false);
1897
- expect($parse('"name" + id').constant).toBe(false);
1898
- });
1899
- });
1900
-
1901
- describe("null/undefined in expressions", () => {
1902
- // simpleGetterFn1
1903
- it("should return null for `a` where `a` is null", () => {
1904
- $rootScope.a = null;
1905
- expect($rootScope.$eval("a")).toBe(null);
1906
- });
1907
-
1908
- it("should return undefined for `a` where `a` is undefined", () => {
1909
- expect($rootScope.$eval("a")).toBeUndefined();
1910
- });
1911
-
1912
- // simpleGetterFn2
1913
- it("should return undefined for properties of `null` constant", () => {
1914
- expect($rootScope.$eval("null.a")).toBeUndefined();
1915
- });
1916
-
1917
- it("should return undefined for properties of `null` values", () => {
1918
- $rootScope.a = null;
1919
- expect($rootScope.$eval("a.b")).toBeUndefined();
1920
- });
1921
-
1922
- it("should return null for `a.b` where `b` is null", () => {
1923
- $rootScope.a = { b: null };
1924
- expect($rootScope.$eval("a.b")).toBe(null);
1925
- });
1926
-
1927
- // cspSafeGetter && pathKeys.length < 6 || pathKeys.length > 2
1928
- it("should return null for `a.b.c.d.e` where `e` is null", () => {
1929
- $rootScope.a = { b: { c: { d: { e: null } } } };
1930
- expect($rootScope.$eval("a.b.c.d.e")).toBe(null);
1931
- });
1932
-
1933
- it("should return undefined for `a.b.c.d.e` where `d` is null", () => {
1934
- $rootScope.a = { b: { c: { d: null } } };
1935
- expect($rootScope.$eval("a.b.c.d.e")).toBeUndefined();
1936
- });
1937
-
1938
- // cspSafeGetter || pathKeys.length > 6
1939
- it("should return null for `a.b.c.d.e.f.g` where `g` is null", () => {
1940
- $rootScope.a = { b: { c: { d: { e: { f: { g: null } } } } } };
1941
- expect($rootScope.$eval("a.b.c.d.e.f.g")).toBe(null);
1942
- });
1943
-
1944
- it("should return undefined for `a.b.c.d.e.f.g` where `f` is null", () => {
1945
- $rootScope.a = { b: { c: { d: { e: { f: null } } } } };
1946
- expect($rootScope.$eval("a.b.c.d.e.f.g")).toBeUndefined();
1947
- });
1948
-
1949
- it("should return undefined if the return value of a function invocation is undefined", () => {
1950
- $rootScope.fn = function () {};
1951
- expect($rootScope.$eval("fn()")).toBeUndefined();
1952
- });
1953
-
1954
- it("should ignore undefined values when doing addition/concatenation", () => {
1955
- $rootScope.fn = function () {};
1956
- expect($rootScope.$eval('foo + "bar" + fn()')).toBe("bar");
1957
- });
1958
-
1959
- it("should treat properties named null/undefined as normal properties", () => {
1960
- expect(
1961
- $rootScope.$eval("a.null.undefined.b", {
1962
- a: { null: { undefined: { b: 1 } } },
1963
- }),
1964
- ).toBe(1);
1965
- });
1966
-
1967
- it("should not allow overriding null/undefined keywords", () => {
1968
- expect($rootScope.$eval("null.a", { null: { a: 42 } })).toBeUndefined();
1969
- });
1970
-
1971
- it("should allow accessing null/undefined properties on `this`", () => {
1972
- $rootScope.null = { a: 42 };
1973
- expect($rootScope.$eval("this.null.a")).toBe(42);
1974
- });
1975
-
1976
- it("should allow accessing $locals", () => {
1977
- $rootScope.foo = "foo";
1978
- $rootScope.bar = "bar";
1979
- $rootScope.$locals = "foo";
1980
- const locals = { foo: 42 };
1981
- expect($rootScope.$eval("$locals")).toBeUndefined();
1982
- expect($rootScope.$eval("$locals.foo")).toBeUndefined();
1983
- expect($rootScope.$eval("this.$locals")).toBe("foo");
1984
- expect(() => {
1985
- $rootScope.$eval("$locals = {}");
1986
- }).toThrow();
1987
- expect(() => {
1988
- $rootScope.$eval("$locals.bar = 23");
1989
- }).toThrow();
1990
- expect($rootScope.$eval("$locals", locals)).toBe(locals);
1991
- expect($rootScope.$eval("$locals.foo", locals)).toBe(42);
1992
- expect($rootScope.$eval("this.$locals", locals)).toBe("foo");
1993
- expect(() => {
1994
- $rootScope.$eval("$locals = {}", locals);
1995
- }).toThrow();
1996
- expect($rootScope.$eval("$locals.bar = 23", locals)).toEqual(23);
1997
- expect(locals.bar).toBe(23);
1998
- });
1999
- });
2000
-
2001
- [true, false].forEach((cspEnabled) => {
2002
- describe(`custom identifiers (csp: ${cspEnabled})`, () => {
2003
- const isIdentifierStartRe = /[#a-z]/;
2004
- const isIdentifierContinueRe = /[-a-z]/;
2005
- let isIdentifierStartFn;
2006
- let isIdentifierContinueFn;
2007
- let scope;
2008
-
2009
- beforeEach(() => {
2010
- createInjector([
2011
- "ng",
2012
- function ($parseProvider) {
2013
- isIdentifierStartFn = jasmine
2014
- .createSpy("isIdentifierStart")
2015
- .and.callFake((ch, cp) => isIdentifierStartRe.test(ch));
2016
- isIdentifierContinueFn = jasmine
2017
- .createSpy("isIdentifierContinue")
2018
- .and.callFake((ch, cp) => isIdentifierContinueRe.test(ch));
2019
-
2020
- $parseProvider.setIdentifierFns(
2021
- isIdentifierStartFn,
2022
- isIdentifierContinueFn,
2023
- );
2024
- csp().noUnsafeEval = cspEnabled;
2025
- },
2026
- ]).invoke((_$rootScope_) => {
2027
- scope = _$rootScope_;
2028
- });
2029
- });
2030
-
2031
- it("should allow specifying a custom `isIdentifierStart/Continue` functions", () => {
2032
- scope.x = {};
2033
-
2034
- scope["#foo"] = "foo";
2035
- scope.x["#foo"] = "foo";
2036
- expect(scope.$eval("#foo")).toBe("foo");
2037
- expect(scope.$eval("x.#foo")).toBe("foo");
2038
-
2039
- scope["bar--"] = 42;
2040
- scope.x["bar--"] = 42;
2041
- expect(scope.$eval("bar--")).toBe(42);
2042
- expect(scope.$eval("x.bar--")).toBe(42);
2043
- expect(scope["bar--"]).toBe(42);
2044
- expect(scope.x["bar--"]).toBe(42);
2045
-
2046
- scope["#-"] = "baz";
2047
- scope.x["#-"] = "baz";
2048
- expect(scope.$eval("#-")).toBe("baz");
2049
- expect(scope.$eval("x.#-")).toBe("baz");
2050
-
2051
- expect(() => {
2052
- scope.$eval("##");
2053
- }).toThrow();
2054
- expect(() => {
2055
- scope.$eval("x.##");
2056
- }).toThrow();
2057
-
2058
- expect(() => {
2059
- scope.$eval("--");
2060
- }).toThrow();
2061
- expect(() => {
2062
- scope.$eval("x.--");
2063
- }).toThrow();
2064
- });
2065
-
2066
- it("should pass the character and codepoint to the custom functions", () => {
2067
- scope.$eval("#-");
2068
- expect(isIdentifierStartFn).toHaveBeenCalledOnceWith(
2069
- "#",
2070
- "#".charCodeAt(0),
2071
- );
2072
- expect(isIdentifierContinueFn).toHaveBeenCalledOnceWith(
2073
- "-",
2074
- "-".charCodeAt(0),
2075
- );
2076
-
2077
- isIdentifierStartFn.calls.reset();
2078
- isIdentifierContinueFn.calls.reset();
2079
-
2080
- scope.$eval("#.foo.#-.bar-");
2081
- expect(isIdentifierStartFn).toHaveBeenCalledTimes(7);
2082
- expect(isIdentifierStartFn.calls.allArgs()).toEqual([
2083
- ["#", "#".charCodeAt(0)],
2084
- [".", ".".charCodeAt(0)],
2085
- ["f", "f".charCodeAt(0)],
2086
- [".", ".".charCodeAt(0)],
2087
- ["#", "#".charCodeAt(0)],
2088
- [".", ".".charCodeAt(0)],
2089
- ["b", "b".charCodeAt(0)],
2090
- ]);
2091
- expect(isIdentifierContinueFn).toHaveBeenCalledTimes(9);
2092
- expect(isIdentifierContinueFn.calls.allArgs()).toEqual([
2093
- [".", ".".charCodeAt(0)],
2094
- ["o", "o".charCodeAt(0)],
2095
- ["o", "o".charCodeAt(0)],
2096
- [".", ".".charCodeAt(0)],
2097
- ["-", "-".charCodeAt(0)],
2098
- [".", ".".charCodeAt(0)],
2099
- ["a", "a".charCodeAt(0)],
2100
- ["r", "r".charCodeAt(0)],
2101
- ["-", "-".charCodeAt(0)],
2102
- ]);
2103
- });
2104
- });
2105
- });
2106
- });
2107
- });