@angular-wave/angular.ts 0.9.3 → 0.9.5

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 (703) hide show
  1. package/@types/angular.d.ts +4 -19
  2. package/@types/animations/animate.d.ts +2 -2
  3. package/@types/animations/animation.d.ts +1 -1
  4. package/@types/core/compile/attributes.d.ts +1 -1
  5. package/@types/core/compile/compile.d.ts +2 -2
  6. package/@types/core/controller/controller.d.ts +1 -1
  7. package/@types/core/controller/interface.d.ts +6 -0
  8. package/@types/core/di/ng-module.d.ts +27 -26
  9. package/@types/core/filter/filter.d.ts +5 -5
  10. package/@types/core/interpolate/interface.d.ts +13 -0
  11. package/@types/core/interpolate/interpolate.d.ts +1 -13
  12. package/@types/core/scope/scope.d.ts +4 -1
  13. package/@types/directive/http/http.d.ts +16 -16
  14. package/@types/directive/http/interface.d.ts +27 -0
  15. package/@types/directive/include/include.d.ts +4 -4
  16. package/@types/directive/inject/inject.d.ts +12 -0
  17. package/@types/directive/model/model.d.ts +1 -1
  18. package/@types/directive/script/script.d.ts +2 -2
  19. package/@types/directive/setter/setter.d.ts +4 -4
  20. package/@types/filters/filter.d.ts +2 -2
  21. package/@types/filters/filters.d.ts +2 -2
  22. package/@types/filters/interface.d.ts +8 -0
  23. package/@types/filters/limit-to.d.ts +2 -2
  24. package/@types/filters/order-by.d.ts +2 -2
  25. package/@types/interface.d.ts +105 -82
  26. package/@types/namespace.d.ts +76 -0
  27. package/@types/router/state/interface.d.ts +8 -8
  28. package/@types/router/state-filters.d.ts +4 -4
  29. package/@types/router/template-factory.d.ts +8 -8
  30. package/@types/router/transition/hook-builder.d.ts +5 -2
  31. package/@types/router/transition/hook-registry.d.ts +11 -2
  32. package/@types/router/transition/transition-service.d.ts +6 -2
  33. package/@types/router/transition/transition.d.ts +2 -2
  34. package/@types/router/view/view.d.ts +1 -8
  35. package/@types/router/view-scroll.d.ts +4 -2
  36. package/@types/services/{anchor-scroll.d.ts → anchor-scroll/anchor-scroll.d.ts} +2 -2
  37. package/@types/services/exception/exception-handler.d.ts +2 -2
  38. package/@types/services/exception/interface.d.ts +1 -1
  39. package/@types/services/http/http.d.ts +40 -2
  40. package/@types/services/http/interface.d.ts +11 -0
  41. package/@types/services/location/location.d.ts +1 -4
  42. package/@types/services/sce/sce.d.ts +3 -4
  43. package/@types/services/template-cache/template-cache.d.ts +4 -4
  44. package/@types/services/template-request/interface.d.ts +22 -0
  45. package/@types/services/{template-request.d.ts → template-request/template-request.d.ts} +4 -7
  46. package/@types/shared/common.d.ts +8 -69
  47. package/@types/shared/hof.d.ts +7 -7
  48. package/dist/angular-ts.esm.js +510 -570
  49. package/dist/angular-ts.umd.js +510 -570
  50. package/dist/angular-ts.umd.min.js +1 -1
  51. package/package.json +8 -1
  52. package/.github/workflows/ci.yml +0 -104
  53. package/.github/workflows/gh-pages.yml +0 -75
  54. package/.husky/pre-commit +0 -5
  55. package/.prettierignore +0 -9
  56. package/@types/services/cookie-reader.d.ts +0 -4
  57. package/@types/services/http-backend/http-backend.d.ts +0 -58
  58. package/@types/services/template-cache/interface.d.ts +0 -10
  59. package/CHANGELOG.md +0 -17667
  60. package/CODE_OF_CONDUCT.md +0 -3
  61. package/CONTRIBUTING.md +0 -247
  62. package/DEVELOPERS.md +0 -499
  63. package/Makefile +0 -60
  64. package/RELEASE.md +0 -86
  65. package/TRIAGING.md +0 -127
  66. package/docs/.cspell.yml +0 -8
  67. package/docs/.github/dependabot.yml +0 -14
  68. package/docs/.nvmrc +0 -1
  69. package/docs/CONTRIBUTING.md +0 -28
  70. package/docs/Dockerfile +0 -4
  71. package/docs/LICENSE +0 -201
  72. package/docs/README.md +0 -217
  73. package/docs/assets/icons/logo.svg +0 -1
  74. package/docs/assets/scss/_variables_project.scss +0 -12
  75. package/docs/assets/scss/_variables_project_after_bs.scss +0 -8
  76. package/docs/assets/scss/index.scss +0 -48
  77. package/docs/config.yaml +0 -15
  78. package/docs/content/_index.md +0 -28
  79. package/docs/content/docs/_index.md +0 -61
  80. package/docs/content/docs/directive/_index.md +0 -4
  81. package/docs/content/docs/directive/app.md +0 -11
  82. package/docs/content/docs/directive/aria.md +0 -0
  83. package/docs/content/docs/directive/bind.md +0 -72
  84. package/docs/content/docs/directive/blur.md +0 -38
  85. package/docs/content/docs/directive/channel.md +0 -37
  86. package/docs/content/docs/directive/class-even.md +0 -47
  87. package/docs/content/docs/directive/class-odd.md +0 -48
  88. package/docs/content/docs/directive/class.md +0 -64
  89. package/docs/content/docs/directive/click.md +0 -41
  90. package/docs/content/docs/directive/cloak.md +0 -74
  91. package/docs/content/docs/directive/copy.md +0 -38
  92. package/docs/content/docs/directive/cut.md +0 -40
  93. package/docs/content/docs/directive/dblclick.md +0 -41
  94. package/docs/content/docs/directive/focus.md +0 -38
  95. package/docs/content/docs/directive/get.md +0 -203
  96. package/docs/content/docs/directive/include.md +0 -7
  97. package/docs/content/docs/directive/keydown.md +0 -38
  98. package/docs/content/docs/directive/keyup.md +0 -38
  99. package/docs/content/docs/directive/load.md +0 -43
  100. package/docs/content/docs/directive/mousedown.md +0 -38
  101. package/docs/content/docs/directive/mouseenter.md +0 -38
  102. package/docs/content/docs/directive/mouseleave.md +0 -38
  103. package/docs/content/docs/directive/mousemove.md +0 -38
  104. package/docs/content/docs/directive/mouseout.md +0 -38
  105. package/docs/content/docs/directive/mouseover.md +0 -38
  106. package/docs/content/docs/directive/mouseup.md +0 -38
  107. package/docs/content/docs/directive/non-bindable.md +0 -28
  108. package/docs/content/docs/filter/_index.md +0 -4
  109. package/docs/content/docs/provider/_index.md +0 -4
  110. package/docs/content/docs/provider/eventBusProvider.md +0 -35
  111. package/docs/content/docs/provider/locationProvider.md +0 -26
  112. package/docs/content/docs/provider/logProvider.md +0 -59
  113. package/docs/content/docs/provider/templateCacheProvider.md +0 -100
  114. package/docs/content/docs/service/_index.md +0 -4
  115. package/docs/content/docs/service/eventBus.md +0 -56
  116. package/docs/content/docs/service/location.md +0 -57
  117. package/docs/content/docs/service/log.md +0 -113
  118. package/docs/content/docs/service/templateCache.md +0 -64
  119. package/docs/content/docs/service/url.md +0 -5
  120. package/docs/docker-compose.yaml +0 -12
  121. package/docs/docsy.work +0 -5
  122. package/docs/docsy.work.sum +0 -0
  123. package/docs/go.mod +0 -5
  124. package/docs/go.sum +0 -6
  125. package/docs/hugo-disabled.toml +0 -220
  126. package/docs/hugo.yaml +0 -200
  127. package/docs/layouts/404.html +0 -13
  128. package/docs/layouts/_markup/render-heading.html +0 -1
  129. package/docs/layouts/partials/hooks/head-end.html +0 -3
  130. package/docs/layouts/shortcodes/showcss.html +0 -2
  131. package/docs/layouts/shortcodes/showhtml.html +0 -2
  132. package/docs/layouts/shortcodes/showjs.html +0 -2
  133. package/docs/layouts/shortcodes/showraw.html +0 -1
  134. package/docs/layouts/shortcodes/version.html +0 -1
  135. package/docs/package-lock.json +0 -2293
  136. package/docs/package.json +0 -53
  137. package/docs/static/examples/counter/counter-test.html +0 -13
  138. package/docs/static/examples/counter/counter.html +0 -5
  139. package/docs/static/examples/counter/counter.test.js +0 -28
  140. package/docs/static/examples/eventbus/eventbus-test.html +0 -15
  141. package/docs/static/examples/eventbus/eventbus.html +0 -13
  142. package/docs/static/examples/eventbus/eventbus.js +0 -15
  143. package/docs/static/examples/eventbus/eventbus.test.js +0 -19
  144. package/docs/static/examples/ng-bind/ng-bind.html +0 -9
  145. package/docs/static/examples/ng-blur/ng-blur.html +0 -9
  146. package/docs/static/examples/ng-channel/ng-channel-test.html +0 -17
  147. package/docs/static/examples/ng-channel/ng-channel.html +0 -24
  148. package/docs/static/examples/ng-channel/ng-channel.test.js +0 -31
  149. package/docs/static/examples/ng-class/ng-class.html +0 -71
  150. package/docs/static/examples/ng-class-even/ng-class-even.html +0 -8
  151. package/docs/static/examples/ng-class-odd/ng-class-odd.html +0 -8
  152. package/docs/static/examples/ng-click/ng-click.html +0 -6
  153. package/docs/static/examples/ng-copy/ng-copy.html +0 -6
  154. package/docs/static/examples/ng-cut/ng-cut.html +0 -6
  155. package/docs/static/examples/ng-dblclick/ng-dblclick.html +0 -10
  156. package/docs/static/examples/ng-focus/ng-focus.html +0 -9
  157. package/docs/static/examples/ng-keydown/ng-keydown.html +0 -9
  158. package/docs/static/examples/ng-keyup/ng-keyup.html +0 -9
  159. package/docs/static/examples/ng-load/ng-load.html +0 -8
  160. package/docs/static/examples/ng-mousedown/ng-mousedown.html +0 -6
  161. package/docs/static/examples/ng-mouseenter/ng-mouseenter.html +0 -4
  162. package/docs/static/examples/ng-mouseleave/ng-mouseleave.html +0 -4
  163. package/docs/static/examples/ng-mousemove/ng-mousemove.html +0 -4
  164. package/docs/static/examples/ng-mouseout/ng-mouseout.html +0 -4
  165. package/docs/static/examples/ng-mouseover/ng-mouseover.html +0 -4
  166. package/docs/static/examples/ng-mouseup/ng-mouseup.html +0 -4
  167. package/docs/static/examples/ng-non-bindable/ng-non-bindable-test.html +0 -13
  168. package/docs/static/examples/ng-non-bindable/ng-non-bindable.html +0 -3
  169. package/docs/static/examples/ng-non-bindable/ng-non-bindable.test.js +0 -11
  170. package/docs/static/typedoc/.nojekyll +0 -1
  171. package/docs/static/typedoc/assets/hierarchy.js +0 -1
  172. package/docs/static/typedoc/assets/highlight.css +0 -78
  173. package/docs/static/typedoc/assets/icons.js +0 -18
  174. package/docs/static/typedoc/assets/icons.svg +0 -1
  175. package/docs/static/typedoc/assets/main.js +0 -60
  176. package/docs/static/typedoc/assets/navigation.js +0 -1
  177. package/docs/static/typedoc/assets/search.js +0 -1
  178. package/docs/static/typedoc/assets/style.css +0 -1633
  179. package/docs/static/typedoc/classes/Location.html +0 -55
  180. package/docs/static/typedoc/classes/LocationProvider.html +0 -20
  181. package/docs/static/typedoc/classes/LogProvider.html +0 -6
  182. package/docs/static/typedoc/classes/PubSub.html +0 -71
  183. package/docs/static/typedoc/classes/PubSubProvider.html +0 -3
  184. package/docs/static/typedoc/classes/TemplateCacheProvider.html +0 -5
  185. package/docs/static/typedoc/hierarchy.html +0 -1
  186. package/docs/static/typedoc/index.html +0 -1
  187. package/docs/static/typedoc/interfaces/ChangesObject.html +0 -6
  188. package/docs/static/typedoc/interfaces/ComponentOptions.html +0 -16
  189. package/docs/static/typedoc/interfaces/Controller.html +0 -12
  190. package/docs/static/typedoc/interfaces/DefaultPorts.html +0 -5
  191. package/docs/static/typedoc/interfaces/Directive.html +0 -37
  192. package/docs/static/typedoc/interfaces/DirectivePrePost.html +0 -4
  193. package/docs/static/typedoc/interfaces/Html5Mode.html +0 -23
  194. package/docs/static/typedoc/interfaces/HttpHeadersGetter.html +0 -1
  195. package/docs/static/typedoc/interfaces/HttpProviderDefaults.html +0 -31
  196. package/docs/static/typedoc/interfaces/HttpRequestConfigHeaders.html +0 -6
  197. package/docs/static/typedoc/interfaces/HttpRequestTransformer.html +0 -1
  198. package/docs/static/typedoc/interfaces/HttpResponse.html +0 -7
  199. package/docs/static/typedoc/interfaces/HttpResponseTransformer.html +0 -1
  200. package/docs/static/typedoc/interfaces/HttpService.html +0 -38
  201. package/docs/static/typedoc/interfaces/LogService.html +0 -12
  202. package/docs/static/typedoc/interfaces/NgModelController.html +0 -30
  203. package/docs/static/typedoc/interfaces/NgModelOptions.html +0 -16
  204. package/docs/static/typedoc/interfaces/Provider.html +0 -34
  205. package/docs/static/typedoc/interfaces/RequestConfig.html +0 -48
  206. package/docs/static/typedoc/interfaces/RequestShortcutConfig.html +0 -38
  207. package/docs/static/typedoc/interfaces/ServiceProvider.html +0 -5
  208. package/docs/static/typedoc/interfaces/TemplateCache.html +0 -7
  209. package/docs/static/typedoc/interfaces/TranscludeFunctionObject.html +0 -8
  210. package/docs/static/typedoc/interfaces/UrlParts.html +0 -9
  211. package/docs/static/typedoc/types/AnnotatedDirectiveFactory.html +0 -1
  212. package/docs/static/typedoc/types/AnnotatedFactory.html +0 -8
  213. package/docs/static/typedoc/types/CloneAttachFunction.html +0 -2
  214. package/docs/static/typedoc/types/ControllerConstructor.html +0 -2
  215. package/docs/static/typedoc/types/DirectiveCompileFn.html +0 -2
  216. package/docs/static/typedoc/types/DirectiveController.html +0 -2
  217. package/docs/static/typedoc/types/DirectiveFactory.html +0 -1
  218. package/docs/static/typedoc/types/DirectiveFactoryFn.html +0 -1
  219. package/docs/static/typedoc/types/DirectiveLinkFn.html +0 -2
  220. package/docs/static/typedoc/types/ExpandoStore.html +0 -2
  221. package/docs/static/typedoc/types/Expression.html +0 -6
  222. package/docs/static/typedoc/types/FilterFactory.html +0 -2
  223. package/docs/static/typedoc/types/FilterFn.html +0 -2
  224. package/docs/static/typedoc/types/HttpPromise.html +0 -1
  225. package/docs/static/typedoc/types/HttpResponseStatus.html +0 -1
  226. package/docs/static/typedoc/types/Injectable.html +0 -4
  227. package/docs/static/typedoc/types/InjectableClass.html +0 -1
  228. package/docs/static/typedoc/types/InjectableFactory.html +0 -1
  229. package/docs/static/typedoc/types/LogCall.html +0 -2
  230. package/docs/static/typedoc/types/LogServiceFactory.html +0 -2
  231. package/docs/static/typedoc/types/OnChangesObject.html +0 -2
  232. package/docs/static/typedoc/types/SwapModeType.html +0 -2
  233. package/docs/static/typedoc/types/TController.html +0 -2
  234. package/docs/static/typedoc/types/UrlChangeListener.html +0 -5
  235. package/docs/static/typedoc/variables/EventBus.html +0 -1
  236. package/docs/static/typedoc/variables/SwapMode.html +0 -11
  237. package/docs/static/version.js +0 -13
  238. package/docs/test-results/.last-run.json +0 -4
  239. package/docs/test-results/static-examples-counter-counter-counter-example/error-context.md +0 -50
  240. package/eslint.config.js +0 -26
  241. package/images/android-chrome-192x192.png +0 -0
  242. package/images/android-chrome-512x512.png +0 -0
  243. package/images/apple-touch-icon.png +0 -0
  244. package/images/favicon-16x16.png +0 -0
  245. package/images/favicon-32x32.png +0 -0
  246. package/images/favicon.ico +0 -0
  247. package/images/site.webmanifest +0 -19
  248. package/index.html +0 -86
  249. package/legacy.d.ts +0 -2599
  250. package/playwright.config.ts +0 -81
  251. package/public/jasmine/boot0.js +0 -66
  252. package/public/jasmine/boot1.js +0 -134
  253. package/public/jasmine/jasmine-html.js +0 -970
  254. package/public/jasmine/jasmine.css +0 -323
  255. package/public/jasmine/jasmine.js +0 -11406
  256. package/public/public/README.md +0 -1
  257. package/public/public/circle.html +0 -1
  258. package/public/public/jasmine-helper.css +0 -9
  259. package/public/public/my_child_directive.html +0 -1
  260. package/public/public/my_directive.html +0 -1
  261. package/public/public/my_other_directive.html +0 -1
  262. package/public/public/test.html +0 -1
  263. package/rollup.config.js +0 -51
  264. package/src/angular.js +0 -293
  265. package/src/angular.spec.js +0 -1191
  266. package/src/animations/animate-cache.js +0 -80
  267. package/src/animations/animate-children-directive.js +0 -32
  268. package/src/animations/animate-children-directive.md +0 -80
  269. package/src/animations/animate-css-driver.js +0 -284
  270. package/src/animations/animate-css.html +0 -58
  271. package/src/animations/animate-css.js +0 -915
  272. package/src/animations/animate-css.md +0 -263
  273. package/src/animations/animate-js-driver.js +0 -60
  274. package/src/animations/animate-js.html +0 -47
  275. package/src/animations/animate-js.js +0 -371
  276. package/src/animations/animate-queue.js +0 -859
  277. package/src/animations/animate-runner.js +0 -193
  278. package/src/animations/animate-swap.js +0 -33
  279. package/src/animations/animate-swap.md +0 -88
  280. package/src/animations/animate.html +0 -19
  281. package/src/animations/animate.js +0 -546
  282. package/src/animations/animate.md +0 -933
  283. package/src/animations/animate.spec.js +0 -490
  284. package/src/animations/animation.js +0 -519
  285. package/src/animations/animations.test.js +0 -10
  286. package/src/animations/interface.ts +0 -19
  287. package/src/animations/raf-scheduler.html +0 -19
  288. package/src/animations/raf-scheduler.js +0 -92
  289. package/src/animations/raf-scheduler.spec.js +0 -98
  290. package/src/animations/shared.js +0 -341
  291. package/src/binding.html +0 -19
  292. package/src/binding.spec.js +0 -474
  293. package/src/binding.test.js +0 -10
  294. package/src/core/compile/attributes.js +0 -337
  295. package/src/core/compile/compile.html +0 -19
  296. package/src/core/compile/compile.js +0 -3270
  297. package/src/core/compile/compile.md +0 -1128
  298. package/src/core/compile/compile.spec.js +0 -15574
  299. package/src/core/compile/compile.test.js +0 -12
  300. package/src/core/controller/controller.html +0 -22
  301. package/src/core/controller/controller.js +0 -189
  302. package/src/core/controller/controller.spec.js +0 -334
  303. package/src/core/controller/controller.test.js +0 -12
  304. package/src/core/core.html +0 -20
  305. package/src/core/core.test.js +0 -12
  306. package/src/core/di/injector.html +0 -19
  307. package/src/core/di/injector.js +0 -307
  308. package/src/core/di/injector.md +0 -740
  309. package/src/core/di/injector.spec.js +0 -2310
  310. package/src/core/di/injector.test.js +0 -12
  311. package/src/core/di/internal-injector.js +0 -284
  312. package/src/core/di/ng-module.html +0 -19
  313. package/src/core/di/ng-module.js +0 -226
  314. package/src/core/di/ng-module.spec.js +0 -263
  315. package/src/core/di/ng-module.test.js +0 -12
  316. package/src/core/filter/filter.html +0 -19
  317. package/src/core/filter/filter.js +0 -55
  318. package/src/core/filter/filter.md +0 -132
  319. package/src/core/filter/filter.spec.js +0 -149
  320. package/src/core/filter/filter.test.js +0 -12
  321. package/src/core/interpolate/interpolate.html +0 -22
  322. package/src/core/interpolate/interpolate.js +0 -408
  323. package/src/core/interpolate/interpolate.spec.js +0 -601
  324. package/src/core/interpolate/interpolate.test.js +0 -12
  325. package/src/core/parse/ast/ast-node.ts +0 -81
  326. package/src/core/parse/ast/ast.html +0 -19
  327. package/src/core/parse/ast/ast.js +0 -574
  328. package/src/core/parse/ast/ast.spec.js +0 -1453
  329. package/src/core/parse/ast/ast.test.js +0 -10
  330. package/src/core/parse/ast-type.js +0 -23
  331. package/src/core/parse/interface.ts +0 -84
  332. package/src/core/parse/interpreter.js +0 -915
  333. package/src/core/parse/lexer/lexer.html +0 -19
  334. package/src/core/parse/lexer/lexer.js +0 -338
  335. package/src/core/parse/lexer/lexer.spec.js +0 -303
  336. package/src/core/parse/lexer/lexer.test.js +0 -10
  337. package/src/core/parse/lexer/token.ts +0 -22
  338. package/src/core/parse/parse.html +0 -19
  339. package/src/core/parse/parse.js +0 -337
  340. package/src/core/parse/parse.md +0 -57
  341. package/src/core/parse/parse.spec.js +0 -2107
  342. package/src/core/parse/parse.test.js +0 -10
  343. package/src/core/parse/parser/parser.html +0 -19
  344. package/src/core/parse/parser/parser.js +0 -64
  345. package/src/core/parse/parser/parser.spec.js +0 -8
  346. package/src/core/parse/parser/parser.test.js +0 -10
  347. package/src/core/prop.spec.js +0 -775
  348. package/src/core/root-element.spec.js +0 -14
  349. package/src/core/sanitize/interface.ts +0 -10
  350. package/src/core/sanitize/sanitize-uri.js +0 -75
  351. package/src/core/sanitize/sanitize-uri.spec.js +0 -249
  352. package/src/core/sanitize/sanitize-uri.test.js +0 -12
  353. package/src/core/sanitize/sanitize.html +0 -22
  354. package/src/core/scope/scope.html +0 -19
  355. package/src/core/scope/scope.js +0 -1249
  356. package/src/core/scope/scope.spec.js +0 -3000
  357. package/src/core/scope/scope.test.js +0 -12
  358. package/src/directive/aria/aria.html +0 -19
  359. package/src/directive/aria/aria.js +0 -382
  360. package/src/directive/aria/aria.md +0 -145
  361. package/src/directive/aria/aria.spec.js +0 -1241
  362. package/src/directive/aria/aria.test.js +0 -12
  363. package/src/directive/attrs/attrs.html +0 -19
  364. package/src/directive/attrs/attrs.js +0 -106
  365. package/src/directive/attrs/attrs.md +0 -224
  366. package/src/directive/attrs/attrs.spec.js +0 -71
  367. package/src/directive/attrs/attrs.test.js +0 -12
  368. package/src/directive/attrs/boolean.html +0 -19
  369. package/src/directive/attrs/boolean.spec.js +0 -137
  370. package/src/directive/attrs/boolean.test.js +0 -12
  371. package/src/directive/attrs/element-style.html +0 -22
  372. package/src/directive/attrs/element-style.spec.js +0 -85
  373. package/src/directive/attrs/element-style.test.js +0 -12
  374. package/src/directive/attrs/src.html +0 -19
  375. package/src/directive/attrs/src.spec.js +0 -163
  376. package/src/directive/attrs/src.test.js +0 -12
  377. package/src/directive/bind/bind-html.spec.js +0 -36
  378. package/src/directive/bind/bind.html +0 -20
  379. package/src/directive/bind/bind.js +0 -78
  380. package/src/directive/bind/bind.md +0 -142
  381. package/src/directive/bind/bind.spec.js +0 -314
  382. package/src/directive/bind/bind.test.js +0 -12
  383. package/src/directive/channel/channel.html +0 -19
  384. package/src/directive/channel/channel.js +0 -30
  385. package/src/directive/channel/channel.spec.js +0 -67
  386. package/src/directive/channel/channel.test.js +0 -10
  387. package/src/directive/class/class-test.html +0 -23
  388. package/src/directive/class/class.html +0 -19
  389. package/src/directive/class/class.js +0 -184
  390. package/src/directive/class/class.spec.js +0 -704
  391. package/src/directive/class/class.test.js +0 -12
  392. package/src/directive/cloak/cloak.html +0 -19
  393. package/src/directive/cloak/cloak.js +0 -11
  394. package/src/directive/cloak/cloak.spec.js +0 -44
  395. package/src/directive/cloak/cloak.test.js +0 -12
  396. package/src/directive/controller/controller.html +0 -22
  397. package/src/directive/controller/controller.js +0 -11
  398. package/src/directive/controller/controller.md +0 -46
  399. package/src/directive/controller/controller.spec.js +0 -175
  400. package/src/directive/controller/controller.test.js +0 -12
  401. package/src/directive/events/click.spec.js +0 -35
  402. package/src/directive/events/event.spec.js +0 -267
  403. package/src/directive/events/events-test.html +0 -36
  404. package/src/directive/events/events.html +0 -20
  405. package/src/directive/events/events.js +0 -65
  406. package/src/directive/events/events.md +0 -125
  407. package/src/directive/events/events.test.js +0 -12
  408. package/src/directive/form/form.html +0 -19
  409. package/src/directive/form/form.js +0 -669
  410. package/src/directive/form/form.spec.js +0 -1515
  411. package/src/directive/form/form.test.js +0 -12
  412. package/src/directive/http/delete.spec.js +0 -26
  413. package/src/directive/http/form-router-test.html +0 -44
  414. package/src/directive/http/form-test.html +0 -18
  415. package/src/directive/http/get.spec.js +0 -488
  416. package/src/directive/http/http.html +0 -22
  417. package/src/directive/http/http.js +0 -342
  418. package/src/directive/http/http.test.js +0 -12
  419. package/src/directive/http/post-example.html +0 -30
  420. package/src/directive/http/post.spec.js +0 -521
  421. package/src/directive/http/put.spec.js +0 -26
  422. package/src/directive/if/if-animate-css.html +0 -57
  423. package/src/directive/if/if-animate-svg.html +0 -25
  424. package/src/directive/if/if.html +0 -19
  425. package/src/directive/if/if.js +0 -72
  426. package/src/directive/if/if.md +0 -76
  427. package/src/directive/if/if.spec.js +0 -293
  428. package/src/directive/if/if.test.js +0 -114
  429. package/src/directive/include/include.html +0 -19
  430. package/src/directive/include/include.js +0 -151
  431. package/src/directive/include/include.md +0 -87
  432. package/src/directive/include/include.spec.js +0 -734
  433. package/src/directive/include/include.test.js +0 -12
  434. package/src/directive/init/init.html +0 -19
  435. package/src/directive/init/init.js +0 -22
  436. package/src/directive/init/init.md +0 -41
  437. package/src/directive/init/init.spec.js +0 -68
  438. package/src/directive/init/init.test.js +0 -12
  439. package/src/directive/input/input-example.html +0 -15
  440. package/src/directive/input/input.html +0 -19
  441. package/src/directive/input/input.js +0 -1078
  442. package/src/directive/input/input.md +0 -706
  443. package/src/directive/input/input.spec.js +0 -3700
  444. package/src/directive/input/input.test.js +0 -12
  445. package/src/directive/messages/messages.html +0 -22
  446. package/src/directive/messages/messages.js +0 -349
  447. package/src/directive/messages/messages.md +0 -543
  448. package/src/directive/messages/messages.spec.js +0 -1083
  449. package/src/directive/messages/messages.test.js +0 -12
  450. package/src/directive/model/change.md +0 -25
  451. package/src/directive/model/model.html +0 -19
  452. package/src/directive/model/model.js +0 -1170
  453. package/src/directive/model/model.spec.js +0 -1976
  454. package/src/directive/model/model.test.js +0 -12
  455. package/src/directive/model-options/model-option.test.js +0 -12
  456. package/src/directive/model-options/model-options.html +0 -22
  457. package/src/directive/model-options/model-options.js +0 -142
  458. package/src/directive/model-options/model-options.md +0 -407
  459. package/src/directive/model-options/model-options.spec.js +0 -1022
  460. package/src/directive/non-bindable/non-bindable.html +0 -22
  461. package/src/directive/non-bindable/non-bindable.js +0 -9
  462. package/src/directive/non-bindable/non-bindable.spec.js +0 -59
  463. package/src/directive/non-bindable/non-bindable.test.js +0 -12
  464. package/src/directive/observe/observe-demo.html +0 -184
  465. package/src/directive/observe/observe.html +0 -19
  466. package/src/directive/observe/observe.js +0 -41
  467. package/src/directive/observe/observe.spec.js +0 -106
  468. package/src/directive/observe/observe.test.js +0 -10
  469. package/src/directive/on/on.html +0 -19
  470. package/src/directive/on/on.spec.js +0 -215
  471. package/src/directive/on/on.test.js +0 -12
  472. package/src/directive/options/options-example.html +0 -17
  473. package/src/directive/options/options.html +0 -22
  474. package/src/directive/options/options.js +0 -542
  475. package/src/directive/options/options.md +0 -179
  476. package/src/directive/options/options.spec.js +0 -3554
  477. package/src/directive/options/options.test.js +0 -12
  478. package/src/directive/ref/href.html +0 -19
  479. package/src/directive/ref/href.spec.js +0 -141
  480. package/src/directive/ref/href.test.js +0 -19
  481. package/src/directive/ref/ref.html +0 -19
  482. package/src/directive/ref/ref.js +0 -89
  483. package/src/directive/ref/ref.spec.js +0 -546
  484. package/src/directive/repeat/repeat.html +0 -19
  485. package/src/directive/repeat/repeat.js +0 -333
  486. package/src/directive/repeat/repeat.md +0 -330
  487. package/src/directive/repeat/repeat.spec.js +0 -1209
  488. package/src/directive/repeat/repeat.test.js +0 -12
  489. package/src/directive/script/script.html +0 -19
  490. package/src/directive/script/script.js +0 -17
  491. package/src/directive/script/script.md +0 -11
  492. package/src/directive/script/script.spec.js +0 -47
  493. package/src/directive/script/script.test.js +0 -12
  494. package/src/directive/select/select.html +0 -19
  495. package/src/directive/select/select.js +0 -594
  496. package/src/directive/select/select.md +0 -74
  497. package/src/directive/select/select.spec.js +0 -2566
  498. package/src/directive/select/select.test.js +0 -12
  499. package/src/directive/setter/setter.html +0 -19
  500. package/src/directive/setter/setter.js +0 -59
  501. package/src/directive/setter/setter.spec.js +0 -100
  502. package/src/directive/setter/setter.test.js +0 -12
  503. package/src/directive/show-hide/show-hide.html +0 -22
  504. package/src/directive/show-hide/show-hide.js +0 -65
  505. package/src/directive/show-hide/show-hide.md +0 -255
  506. package/src/directive/show-hide/show-hide.spec.js +0 -268
  507. package/src/directive/show-hide/show-hide.test.js +0 -12
  508. package/src/directive/style/style.html +0 -19
  509. package/src/directive/style/style.js +0 -27
  510. package/src/directive/style/style.md +0 -23
  511. package/src/directive/style/style.spec.js +0 -183
  512. package/src/directive/style/style.test.js +0 -12
  513. package/src/directive/switch/switch.html +0 -19
  514. package/src/directive/switch/switch.js +0 -133
  515. package/src/directive/switch/switch.md +0 -66
  516. package/src/directive/switch/switch.spec.js +0 -509
  517. package/src/directive/switch/switch.test.js +0 -12
  518. package/src/directive/transclude/transclude.js +0 -122
  519. package/src/directive/validators/validators.html +0 -22
  520. package/src/directive/validators/validators.js +0 -346
  521. package/src/directive/validators/validators.spec.js +0 -740
  522. package/src/directive/validators/validators.test.js +0 -12
  523. package/src/filters/filter.js +0 -213
  524. package/src/filters/filter.md +0 -69
  525. package/src/filters/filter.spec.js +0 -719
  526. package/src/filters/filters.html +0 -22
  527. package/src/filters/filters.js +0 -239
  528. package/src/filters/filters.spec.js +0 -36
  529. package/src/filters/filters.test.js +0 -12
  530. package/src/filters/json.md +0 -16
  531. package/src/filters/limit-to.js +0 -55
  532. package/src/filters/limit-to.md +0 -19
  533. package/src/filters/limit-to.spec.js +0 -252
  534. package/src/filters/order-by.js +0 -181
  535. package/src/filters/order-by.md +0 -83
  536. package/src/filters/order-by.spec.js +0 -883
  537. package/src/index.js +0 -6
  538. package/src/index.spec.js +0 -11
  539. package/src/injection-tokens.js +0 -78
  540. package/src/interface.ts +0 -421
  541. package/src/ng.js +0 -289
  542. package/src/ng.spec.js +0 -33
  543. package/src/router/common/trace.js +0 -240
  544. package/src/router/directives/component-example.html +0 -37
  545. package/src/router/directives/state-directives.html +0 -22
  546. package/src/router/directives/state-directives.js +0 -393
  547. package/src/router/directives/state-directives.md +0 -435
  548. package/src/router/directives/state-directives.spec.js +0 -1091
  549. package/src/router/directives/state-directives.test.js +0 -10
  550. package/src/router/directives/view-directive.js +0 -489
  551. package/src/router/directives/view-directive.spec.js +0 -1937
  552. package/src/router/directives/view-directive.test.js +0 -10
  553. package/src/router/directives/view-directives.html +0 -22
  554. package/src/router/glob/glob.html +0 -19
  555. package/src/router/glob/glob.js +0 -102
  556. package/src/router/glob/glob.spec.js +0 -108
  557. package/src/router/glob/glob.test.js +0 -12
  558. package/src/router/hooks/core-resolvables.js +0 -38
  559. package/src/router/hooks/ignored-transition.js +0 -25
  560. package/src/router/hooks/invalid-transition.js +0 -14
  561. package/src/router/hooks/lazy-load.js +0 -104
  562. package/src/router/hooks/on-enter-exit-retain.js +0 -55
  563. package/src/router/hooks/redirect-to.js +0 -38
  564. package/src/router/hooks/resolve.js +0 -57
  565. package/src/router/hooks/update-globals.js +0 -34
  566. package/src/router/hooks/url.js +0 -34
  567. package/src/router/hooks/views.js +0 -41
  568. package/src/router/params/interface.ts +0 -626
  569. package/src/router/params/param-factory.js +0 -23
  570. package/src/router/params/param-type.js +0 -133
  571. package/src/router/params/param-types.js +0 -153
  572. package/src/router/params/param.js +0 -243
  573. package/src/router/params/state-params.js +0 -36
  574. package/src/router/path/path-node.js +0 -78
  575. package/src/router/path/path-utils.js +0 -207
  576. package/src/router/resolve/interface.ts +0 -208
  577. package/src/router/resolve/resolvable.js +0 -123
  578. package/src/router/resolve/resolve-context.js +0 -190
  579. package/src/router/router-test-hashbang.html +0 -45
  580. package/src/router/router-test.html +0 -41
  581. package/src/router/router.html +0 -22
  582. package/src/router/router.js +0 -54
  583. package/src/router/router.test.js +0 -12
  584. package/src/router/services.spec.js +0 -52
  585. package/src/router/state/README.md +0 -21
  586. package/src/router/state/interface.ts +0 -1007
  587. package/src/router/state/state-builder.js +0 -376
  588. package/src/router/state/state-builder.spec.js +0 -86
  589. package/src/router/state/state-matcher.js +0 -64
  590. package/src/router/state/state-object.js +0 -118
  591. package/src/router/state/state-queue-manager.js +0 -95
  592. package/src/router/state/state-registry.js +0 -257
  593. package/src/router/state/state-service.js +0 -699
  594. package/src/router/state/state.html +0 -23
  595. package/src/router/state/state.spec.js +0 -1002
  596. package/src/router/state/state.test.js +0 -12
  597. package/src/router/state/target-state.js +0 -162
  598. package/src/router/state/views.js +0 -195
  599. package/src/router/state-filter.spec.js +0 -139
  600. package/src/router/state-filters.js +0 -46
  601. package/src/router/template-factory.html +0 -19
  602. package/src/router/template-factory.js +0 -249
  603. package/src/router/template-factory.spec.js +0 -155
  604. package/src/router/template-factory.test.js +0 -12
  605. package/src/router/transition/hook-builder.js +0 -133
  606. package/src/router/transition/hook-registry.js +0 -172
  607. package/src/router/transition/interface.js +0 -18
  608. package/src/router/transition/interface.ts +0 -922
  609. package/src/router/transition/reject-factory.js +0 -122
  610. package/src/router/transition/transition-event-type.js +0 -26
  611. package/src/router/transition/transition-hook.js +0 -199
  612. package/src/router/transition/transition-service.js +0 -302
  613. package/src/router/transition/transition.js +0 -652
  614. package/src/router/url/url-config.js +0 -155
  615. package/src/router/url/url-matcher.js +0 -532
  616. package/src/router/url/url-rule.js +0 -231
  617. package/src/router/url/url-rules.js +0 -350
  618. package/src/router/url/url-service.js +0 -446
  619. package/src/router/url/url-service.spec.js +0 -1288
  620. package/src/router/url/url.html +0 -19
  621. package/src/router/url/url.test.js +0 -12
  622. package/src/router/view/interface.ts +0 -51
  623. package/src/router/view/view.html +0 -19
  624. package/src/router/view/view.js +0 -274
  625. package/src/router/view/view.spec.js +0 -100
  626. package/src/router/view/view.test.js +0 -12
  627. package/src/router/view-hook.spec.js +0 -215
  628. package/src/router/view-scroll.js +0 -33
  629. package/src/router/view-scroll.spec.js +0 -72
  630. package/src/services/anchor-scroll.html +0 -76
  631. package/src/services/anchor-scroll.js +0 -147
  632. package/src/services/cookie-reader.js +0 -48
  633. package/src/services/exception/exception-handler.js +0 -75
  634. package/src/services/exception/interface.ts +0 -7
  635. package/src/services/http/http.html +0 -23
  636. package/src/services/http/http.js +0 -922
  637. package/src/services/http/http.md +0 -413
  638. package/src/services/http/http.spec.js +0 -3941
  639. package/src/services/http/http.test.js +0 -11
  640. package/src/services/http/interface.ts +0 -243
  641. package/src/services/http/template-request.spec.js +0 -220
  642. package/src/services/http-backend/http-backend.html +0 -22
  643. package/src/services/http-backend/http-backend.js +0 -158
  644. package/src/services/http-backend/http-backend.spec.js +0 -389
  645. package/src/services/http-backend/http-backend.test.js +0 -12
  646. package/src/services/location/interface.ts +0 -70
  647. package/src/services/location/location.html +0 -22
  648. package/src/services/location/location.js +0 -1006
  649. package/src/services/location/location.spec.js +0 -3792
  650. package/src/services/location/location.test.js +0 -12
  651. package/src/services/log/interface.ts +0 -39
  652. package/src/services/log/log.html +0 -19
  653. package/src/services/log/log.js +0 -74
  654. package/src/services/log/log.spec.js +0 -64
  655. package/src/services/log/log.test.js +0 -12
  656. package/src/services/pubsub/pubsub.html +0 -19
  657. package/src/services/pubsub/pubsub.js +0 -349
  658. package/src/services/pubsub/pubsub.spec.js +0 -400
  659. package/src/services/pubsub/pubsub.test.js +0 -12
  660. package/src/services/sce/sce.html +0 -19
  661. package/src/services/sce/sce.js +0 -847
  662. package/src/services/sce/sce.md +0 -300
  663. package/src/services/sce/sce.spec.js +0 -617
  664. package/src/services/sce/sce.test.js +0 -12
  665. package/src/services/template-cache/interface.ts +0 -10
  666. package/src/services/template-cache/template-cache.html +0 -22
  667. package/src/services/template-cache/template-cache.js +0 -15
  668. package/src/services/template-cache/template-cache.spec.js +0 -134
  669. package/src/services/template-cache/template-cache.test.js +0 -12
  670. package/src/services/template-request.js +0 -142
  671. package/src/shared/cache.js +0 -7
  672. package/src/shared/common.js +0 -438
  673. package/src/shared/common.spec.js +0 -294
  674. package/src/shared/constants.js +0 -21
  675. package/src/shared/dom.js +0 -716
  676. package/src/shared/hof.js +0 -151
  677. package/src/shared/hof.spec.js +0 -60
  678. package/src/shared/interface.ts +0 -21
  679. package/src/shared/min-err.spec.js +0 -178
  680. package/src/shared/noderef.js +0 -225
  681. package/src/shared/predicates.js +0 -34
  682. package/src/shared/queue.js +0 -105
  683. package/src/shared/queue.spec.js +0 -80
  684. package/src/shared/shared.html +0 -24
  685. package/src/shared/shared.test.js +0 -12
  686. package/src/shared/strings.js +0 -142
  687. package/src/shared/strings.spec.js +0 -40
  688. package/src/shared/test-utils.js +0 -47
  689. package/src/shared/url-utils/interface.ts +0 -54
  690. package/src/shared/url-utils/url-utils.html +0 -22
  691. package/src/shared/url-utils/url-utils.js +0 -122
  692. package/src/shared/url-utils/url-utils.spec.js +0 -148
  693. package/src/shared/url-utils/url-utils.test.js +0 -12
  694. package/src/shared/utils.js +0 -1255
  695. package/src/shared/utils.spec.js +0 -178
  696. package/src/src.html +0 -21
  697. package/src/src.test.js +0 -10
  698. package/tsconfig.json +0 -19
  699. package/tsconfig.types.json +0 -14
  700. package/typedoc.json +0 -8
  701. package/utils/express.js +0 -203
  702. package/utils/version.cjs +0 -23
  703. package/vite.config.js +0 -14
@@ -1,3700 +0,0 @@
1
- import { Angular } from "../../angular.js";
2
- import {
3
- createElementFromHTML as $,
4
- dealoc,
5
- getController,
6
- } from "../../shared/dom.js";
7
- import { wait } from "../../shared/test-utils.js";
8
- import { EMAIL_REGEXP, ISO_DATE_REGEXP, URL_REGEXP } from "./input.js";
9
-
10
- describe("input", () => {
11
- let $compile;
12
- let scope;
13
- let inputElm;
14
- let error = [];
15
-
16
- beforeEach(() => {
17
- dealoc(document.getElementById("app"));
18
- error = [];
19
- window.angular = new Angular();
20
- window.angular
21
- .module("myModule", ["ng"])
22
- .decorator("$exceptionHandler", function () {
23
- return (exception) => {
24
- error.push(exception.message);
25
- };
26
- });
27
- window.angular
28
- .bootstrap(document.getElementById("app"), ["myModule"])
29
- .invoke((_$compile_, $rootScope) => {
30
- $compile = _$compile_;
31
- scope = $rootScope.$new();
32
- });
33
- });
34
-
35
- it("should bind to a model", async () => {
36
- inputElm = $compile(
37
- '<input type="text" ng-model="name" name="alias" ng-change="change()" />',
38
- )(scope);
39
-
40
- scope.$apply("name = 'misko'");
41
- await wait();
42
- expect(inputElm.value).toBe("misko");
43
- });
44
-
45
- it('should update the model on "blur" event', async () => {
46
- inputElm = $compile(
47
- '<input type="text" ng-model="name" name="alias" ng-change="change()" />',
48
- )(scope);
49
- await wait();
50
- inputElm.setAttribute("value", "adam");
51
- inputElm.dispatchEvent(new Event("change"));
52
- expect(scope.name).toEqual("adam");
53
- });
54
-
55
- it("should not add the property to the scope if name is unspecified", async () => {
56
- $compile('<input type="text" ng-model="name">')(scope);
57
- await wait();
58
- expect(scope.name).toBeUndefined();
59
- });
60
-
61
- it("should not set the `val` property when the value is equal to the current value", async () => {
62
- // This is a workaround for Firefox validation. Look at #12102.
63
- const input = $('<input type="text" ng-model="foo" required/>');
64
- let setterCalls = 0;
65
- scope.foo = "";
66
- Object.defineProperty(input, "value", {
67
- get() {
68
- return "";
69
- },
70
- set() {
71
- setterCalls++;
72
- },
73
- });
74
- $compile(input)(scope);
75
- await wait();
76
- expect(setterCalls).toBe(0);
77
- });
78
-
79
- describe("compositionevents", () => {
80
- it('should not update the model between "compositionstart" and "compositionend"', async () => {
81
- //$sniffer.android = false;
82
-
83
- inputElm = $compile(
84
- '<input type="text" ng-model="name" name="alias"" />',
85
- )(scope);
86
- await wait();
87
- inputElm.setAttribute("value", "a");
88
- inputElm.dispatchEvent(new Event("change"));
89
- expect(scope.name).toEqual("a");
90
-
91
- inputElm.dispatchEvent(new Event("compositionstart"));
92
- inputElm.setAttribute("value", "adam");
93
- expect(scope.name).toEqual("a");
94
- inputElm.dispatchEvent(new Event("compositionend"));
95
- inputElm.setAttribute("value", "adam");
96
- expect(scope.name).toEqual("adam");
97
- });
98
- });
99
-
100
- describe("interpolated names", () => {
101
- it("should interpolate input names", async () => {
102
- scope.nameID = "47";
103
- inputElm = $compile(
104
- '<form name="form"><input type="text" ng-model="name" name="name{{nameID}}" /></form>',
105
- )(scope);
106
- await wait();
107
- expect(scope.form.name47.$pristine).toBeTruthy();
108
- inputElm.querySelector("input").setAttribute("value", "caitp");
109
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
110
- expect(scope.form.name47.$dirty).toBeTruthy();
111
- });
112
-
113
- it("should rename form controls in form when interpolated name changes", async () => {
114
- scope.nameID = "A";
115
- inputElm = $compile(
116
- '<form name="form"><input type="text" ng-model="name" name="name{{nameID}}" /></form>',
117
- )(scope);
118
- await wait();
119
- expect(scope.form.nameA.$name).toBe("nameA");
120
- const oldModel = scope.form.nameA;
121
- scope.nameID = "B";
122
- await wait();
123
- expect(scope.form.nameA).toBeUndefined();
124
- expect(scope.form.nameB).toBe(oldModel);
125
- expect(scope.form.nameB.$name).toBe("nameB");
126
- });
127
-
128
- it("should rename form controls in null form when interpolated name changes", async () => {
129
- scope.nameID = "A";
130
- inputElm = $compile(
131
- '<input type="text" ng-model="name" name="name{{nameID}}" />',
132
- )(scope);
133
- await wait();
134
- const model = getController(inputElm, "ngModel");
135
- expect(model.$name).toBe("nameA");
136
-
137
- scope.nameID = "B";
138
- await wait();
139
- expect(model.$name).toBe("nameB");
140
- });
141
- });
142
-
143
- describe('"change" event', () => {
144
- let assertBrowserSupportsChangeEvent;
145
-
146
- beforeEach(() => {
147
- assertBrowserSupportsChangeEvent = async function (inputEventSupported) {
148
- inputElm = $compile(
149
- '<input type="text" ng-model="name" name="alias" />',
150
- )(scope);
151
- await wait();
152
- //inputElm.val("mark");
153
- inputElm.setAttribute("value", "mark");
154
- inputElm.dispatchEvent(new Event("change"));
155
- expect(scope.name).toEqual("mark");
156
- };
157
- });
158
-
159
- it('should update the model event if the browser does not support the "input" event', () => {
160
- assertBrowserSupportsChangeEvent(false);
161
- });
162
-
163
- it(
164
- 'should update the model event if the browser supports the "input" ' +
165
- "event so that form auto complete works",
166
- () => {
167
- assertBrowserSupportsChangeEvent(true);
168
- },
169
- );
170
-
171
- describe('"keydown", "paste", "cut" and "drop" events', () => {
172
- it('should update the model on "paste" event if the input value changes', async () => {
173
- inputElm = $compile(
174
- '<input type="text" ng-model="name" name="alias" ng-change="change()" />',
175
- )(scope);
176
- await wait();
177
- inputElm.dispatchEvent(new Event("keydown"));
178
- expect(inputElm.classList.contains("ng-pristine")).toBeTrue();
179
-
180
- inputElm.setAttribute("value", "mark");
181
- inputElm.dispatchEvent(new Event("paste"));
182
- expect(scope.name).toEqual("mark");
183
- });
184
-
185
- it('should update the model on "drop" event if the input value changes', async () => {
186
- inputElm = $compile(
187
- '<input type="text" ng-model="name" name="alias" ng-change="change()" />',
188
- )(scope);
189
- await wait();
190
- inputElm.dispatchEvent(new Event("keydown"));
191
- expect(inputElm.classList.contains("ng-pristine")).toBeTrue();
192
-
193
- inputElm.setAttribute("value", "mark");
194
- inputElm.dispatchEvent(new Event("drop"));
195
- expect(scope.name).toEqual("mark");
196
- });
197
-
198
- it('should update the model on "cut" event', async () => {
199
- inputElm = $compile(
200
- '<input type="text" ng-model="name" name="alias" ng-change="change()" />',
201
- )(scope);
202
- await wait();
203
- inputElm.setAttribute("value", "john");
204
- inputElm.dispatchEvent(new Event("cut"));
205
- expect(scope.name).toEqual("john");
206
- });
207
-
208
- it("should cancel the delayed dirty if a change occurs", async () => {
209
- inputElm = $compile('<input type="text" ng-model="name" />')(scope);
210
- await wait();
211
- const ctrl = getController(inputElm, "ngModel");
212
-
213
- inputElm.dispatchEvent(new Event("keydown", { target: inputElm }));
214
- inputElm.value = "f";
215
- inputElm.dispatchEvent(new Event("change"));
216
- expect(inputElm.classList.contains("ng-dirty")).toBeTrue();
217
-
218
- ctrl.$setPristine();
219
- await wait();
220
-
221
- expect(inputElm.classList.contains("ng-pristine")).toBeTrue();
222
- });
223
-
224
- describe("ngTrim", () => {
225
- it("should update the model and trim the value", async () => {
226
- inputElm = $compile(
227
- '<input type="text" ng-model="name" name="alias" ng-change="change()" />',
228
- )(scope);
229
- await wait();
230
- inputElm.setAttribute("value", " a ");
231
- inputElm.dispatchEvent(new Event("change"));
232
- expect(scope.name).toEqual("a");
233
- });
234
-
235
- it("should update the model and not trim the value", async () => {
236
- inputElm = $compile(
237
- '<input type="text" ng-model="name" name="alias" ng-trim="false" />',
238
- )(scope);
239
- await wait();
240
- inputElm.setAttribute("value", " a ");
241
- inputElm.dispatchEvent(new Event("change"));
242
- expect(scope.name).toEqual(" a ");
243
- });
244
- });
245
-
246
- it("should allow complex reference binding", async () => {
247
- inputElm = $compile(
248
- '<input type="text" ng-model="obj[\'abc\'].name"/>',
249
- )(scope);
250
- scope.$apply("obj = { abc: { name: 'Misko'} }");
251
- await wait();
252
- expect(inputElm.value).toEqual("Misko");
253
- });
254
-
255
- it("should ignore input without ngModel directive", async () => {
256
- inputElm = $compile('<input type="text" name="whatever" required />')(
257
- scope,
258
- );
259
- await wait();
260
- inputElm.setAttribute("value", "");
261
- inputElm.dispatchEvent(new Event("change"));
262
- expect(inputElm.classList.contains("ng-valid")).toBe(false);
263
- expect(inputElm.classList.contains("ng-invalid")).toBe(false);
264
- expect(inputElm.classList.contains("ng-pristine")).toBe(false);
265
- expect(inputElm.classList.contains("ng-dirty")).toBe(false);
266
- });
267
-
268
- it("should report error on assignment error", () => {
269
- expect(() => {
270
- inputElm = $compile('<input type="text" ng-model="throw \'\'">')(
271
- scope,
272
- );
273
- }).toThrowError(/Syntax Error/);
274
- });
275
-
276
- it("should render as blank if null", async () => {
277
- inputElm = $compile('<input type="text" ng-model="age" />')(scope);
278
- await wait();
279
- scope.$apply("age = null");
280
- await wait();
281
- expect(scope.age).toBeNull();
282
- expect(inputElm.value).toEqual("");
283
- });
284
-
285
- it("should render 0 even if it is a number", async () => {
286
- inputElm = $compile('<input type="text" ng-model="value" />')(scope);
287
- scope.$apply("value = 0");
288
- await wait();
289
- expect(inputElm.value).toBe("0");
290
- });
291
-
292
- it("should render the $viewValue when $modelValue is empty", async () => {
293
- inputElm = $compile('<input type="text" ng-model="value" />')(scope);
294
- await wait();
295
- const ctrl = getController(inputElm, "ngModel");
296
-
297
- ctrl.$modelValue = null;
298
-
299
- expect(ctrl.$isEmpty(ctrl.$modelValue)).toBe(true);
300
-
301
- ctrl.$viewValue = "abc";
302
- ctrl.$render();
303
- await wait();
304
- expect(inputElm.value).toBe("abc");
305
- });
306
- });
307
-
308
- // INPUT TYPES
309
- describe("month", () => {
310
- // IN ANGULAR.JS month types were converted to Date object. This is not standard behavior
311
- it("should allow a String object in format 'YYYY-MM'", async () => {
312
- inputElm = $compile('<input type="month" ng-model="january"/>')(scope);
313
- await wait();
314
- scope.january = "2013-01";
315
- await wait();
316
- expect(inputElm.value).toBe("2013-01");
317
- });
318
-
319
- it("should throw if the model is a Date object", async () => {
320
- inputElm = $compile('<input type="month" ng-model="march"/>')(scope);
321
- await wait();
322
- scope.march = new Date(2013, 2, 1);
323
- await wait();
324
- expect(error[0].match(/datefmt/)).toBeTruthy();
325
- });
326
-
327
- it("should throw if the model is a Invalid string", async () => {
328
- inputElm = $compile('<input type="month" ng-model="march"/>')(scope);
329
- scope.march = "fail";
330
- await wait();
331
- expect(error[0].match(/datefmt/)).toBeTruthy();
332
- });
333
-
334
- it("should not change the model if the input is an invalid month string", async () => {
335
- inputElm = $compile('<input type="month" ng-model="value"/>')(scope);
336
-
337
- scope.value = "2013-01";
338
- await wait();
339
- expect(inputElm.value).toBe("2013-01");
340
-
341
- inputElm.setAttribute("value", "stuff");
342
- inputElm.dispatchEvent(new Event("change"));
343
- expect(inputElm.value).toBe("2013-01");
344
- expect(scope.value).toBe("2013-01");
345
- });
346
-
347
- it("should render as blank if null", async () => {
348
- inputElm = $compile('<input type="month" ng-model="test" />')(scope);
349
-
350
- scope.$apply("test = null");
351
- await wait();
352
- expect(scope.test).toBeNull();
353
- expect(inputElm.value).toEqual("");
354
- });
355
-
356
- it("should come up blank when no value specified", async () => {
357
- inputElm = $compile('<input type="month" ng-model="test" />')(scope);
358
- await wait();
359
- expect(inputElm.value).toBe("");
360
-
361
- scope.$apply("test = null");
362
- await wait();
363
- expect(scope.test).toBeNull();
364
- expect(inputElm.value).toBe("");
365
- });
366
-
367
- it("should parse empty string to null", async () => {
368
- scope.test = "init";
369
- inputElm = $compile('<input type="month" ng-model="test" />')(scope);
370
- await wait();
371
- inputElm.setAttribute("value", "");
372
- inputElm.dispatchEvent(new Event("change"));
373
- await wait();
374
- expect(scope.test).toBeNull();
375
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
376
- });
377
-
378
- it("should set scope to a string value", async () => {
379
- inputElm = $compile('<input type="month" ng-model="value" />')(scope);
380
- await wait();
381
- inputElm.setAttribute("value", "2013-07");
382
- inputElm.dispatchEvent(new Event("change"));
383
- expect(scope.value).toBe("2013-07");
384
- });
385
-
386
- describe("min", () => {
387
- let inputElm;
388
- beforeEach(async () => {
389
- scope.minVal = "2013-01";
390
- inputElm = $compile(
391
- '<form name="form"><input type="month" ng-model="value" name="alias" min="{{ minVal }}" /></form>',
392
- )(scope);
393
- await wait();
394
- });
395
-
396
- it("should invalidate", () => {
397
- inputElm.querySelector("input").setAttribute("value", "2012-12");
398
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
399
- expect(
400
- inputElm.querySelector("input").classList.contains("ng-invalid"),
401
- ).toBeTrue();
402
- expect(scope.value).toBeFalsy();
403
- expect(scope.form.alias.$error.min).toBeTruthy();
404
- });
405
-
406
- it("should validate", () => {
407
- inputElm.querySelector("input").setAttribute("value", "2013-07");
408
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
409
- expect(
410
- inputElm.querySelector("input").classList.contains("ng-valid"),
411
- ).toBeTrue();
412
- expect(scope.value).toBe("2013-07");
413
- expect(scope.form.alias.$error.min).toBeFalsy();
414
- });
415
-
416
- it("should revalidate when the min value changes", async () => {
417
- inputElm.querySelector("input").setAttribute("value", "2013-07");
418
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
419
- await wait();
420
- expect(
421
- inputElm.querySelector("input").classList.contains("ng-valid"),
422
- ).toBeTrue();
423
- expect(scope.form.alias.$error.min).toBeFalsy();
424
-
425
- scope.minVal = "2014-01";
426
- await wait();
427
- expect(
428
- inputElm.querySelector("input").classList.contains("ng-invalid"),
429
- ).toBeTrue();
430
- expect(scope.form.alias.$error.min).toBeTruthy();
431
- });
432
-
433
- it("should validate if min is empty", async () => {
434
- scope.minVal = undefined;
435
- scope.value = "2014-01";
436
- await wait();
437
- expect(scope.form.alias.$error.min).toBeFalsy();
438
- });
439
- });
440
-
441
- describe("max", () => {
442
- let inputElm;
443
- beforeEach(async () => {
444
- scope.maxVal = "2013-01";
445
- inputElm = $compile(
446
- '<form name="form"><input type="month" ng-model="value" name="alias" max="{{ maxVal }}" /></form>',
447
- )(scope);
448
- await wait();
449
- });
450
-
451
- it("should validate", () => {
452
- inputElm.querySelector("input").setAttribute("value", "2012-03");
453
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
454
- expect(
455
- inputElm.querySelector("input").classList.contains("ng-valid"),
456
- ).toBeTrue();
457
- expect(scope.value).toBe("2012-03");
458
- expect(scope.form.alias.$error.max).toBeFalsy();
459
- });
460
-
461
- it("should invalidate", () => {
462
- inputElm.querySelector("input").setAttribute("value", "2013-05");
463
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
464
- expect(
465
- inputElm.querySelector("input").classList.contains("ng-invalid"),
466
- ).toBeTrue();
467
- expect(scope.value).toBeUndefined();
468
- expect(scope.form.alias.$error.max).toBeTruthy();
469
- });
470
-
471
- it("should revalidate when the max value changes", async () => {
472
- inputElm.querySelector("input").setAttribute("value", "2012-07");
473
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
474
- expect(
475
- inputElm.querySelector("input").classList.contains("ng-valid"),
476
- ).toBeTrue();
477
- expect(scope.form.alias.$error.max).toBeFalsy();
478
-
479
- scope.maxVal = "2012-01";
480
- await wait();
481
- expect(
482
- inputElm.querySelector("input").classList.contains("ng-invalid"),
483
- ).toBeTrue();
484
- expect(scope.form.alias.$error.max).toBeTruthy();
485
- });
486
-
487
- it("should validate if max is empty", async () => {
488
- scope.maxVal = undefined;
489
- scope.value = "2012-03";
490
- await wait();
491
- expect(scope.form.alias.$error.max).toBeFalsy();
492
- });
493
- });
494
- });
495
-
496
- describe("week", () => {
497
- it("should throw if model is a Date object", async () => {
498
- inputElm = $compile('<input type="week" ng-model="secondWeek"/>')(
499
- scope,
500
- );
501
- await wait();
502
- scope.$apply(() => {
503
- scope.secondWeek = new Date(2013, 0, 11);
504
- });
505
- await wait();
506
- expect(error[0]).toMatch("datefmt");
507
- });
508
-
509
- it("should set the view if the model is a valid String object", async () => {
510
- inputElm = $compile('<input type="week" ng-model="secondWeek"/>')(
511
- scope,
512
- );
513
- await wait();
514
- scope.$apply(() => {
515
- scope.secondWeek = "2013-W02";
516
- });
517
- await wait();
518
- expect(inputElm.value).toBe("2013-W02");
519
- });
520
-
521
- it("should set scope to a string value", async () => {
522
- inputElm = $compile('<input type="week" ng-model="secondWeek" />')(
523
- scope,
524
- );
525
- await wait();
526
- scope.$apply(() => {
527
- scope.secondWeek = "2013-W02";
528
- });
529
- await wait();
530
- expect(scope.secondWeek).toBe("2013-W02");
531
- // input type week in Chrome does not react to changes on the attribute. Value must be set directly
532
- inputElm.value = "2014-W03";
533
- inputElm.dispatchEvent(new Event("change"));
534
-
535
- expect(scope.secondWeek).toBe("2014-W03");
536
- });
537
-
538
- it("should set the model undefined if the input is an invalid week string", async () => {
539
- inputElm = $compile('<input type="week" ng-model="secondWeek"/>')(
540
- scope,
541
- );
542
- await wait();
543
- scope.$apply(() => {
544
- scope.secondWeek = "2013-W02";
545
- });
546
- await wait();
547
- expect(inputElm.value).toBe("2013-W02");
548
-
549
- // set to text for browsers with datetime-local validation.
550
- inputElm.value = "stuff";
551
- inputElm.dispatchEvent(new Event("change"));
552
- expect(inputElm.value).toBe("");
553
- expect(scope.value).toBeUndefined();
554
- });
555
-
556
- it("should render as blank if null", async () => {
557
- inputElm = $compile('<input type="week" ng-model="test" />')(scope);
558
- await wait();
559
- scope.$apply("test = null");
560
- await wait();
561
- expect(scope.test).toBeNull();
562
- expect(inputElm.value).toEqual("");
563
- });
564
-
565
- it("should come up blank when no value specified", async () => {
566
- inputElm = $compile('<input type="week" ng-model="test" />')(scope);
567
- await wait();
568
- expect(inputElm.value).toBe("");
569
-
570
- scope.$apply("test = null");
571
- await wait();
572
- expect(scope.test).toBeNull();
573
- expect(inputElm.value).toBe("");
574
- });
575
-
576
- it("should parse empty string to null", async () => {
577
- inputElm = $compile('<input type="week" ng-model="test" />')(scope);
578
- await wait();
579
- scope.$apply(() => {
580
- scope.test = "2013-W02";
581
- });
582
- await wait();
583
- inputElm.value = "";
584
- inputElm.dispatchEvent(new Event("change"));
585
- await wait();
586
- expect(scope.test).toBeNull();
587
- });
588
-
589
- describe("min", () => {
590
- let inputElm;
591
- beforeEach(async () => {
592
- scope.minVal = "2013-W01";
593
- inputElm = $compile(
594
- '<form name="form"><input type="week" ng-model="value" name="alias" min="{{ minVal }}" /></from>',
595
- )(scope);
596
- await wait();
597
- });
598
-
599
- it("should invalidate", () => {
600
- inputElm.querySelector("input").value = "2012-W12";
601
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
602
- expect(scope.value).toBeFalsy();
603
- expect(scope.form.alias.$error.min).toBeTruthy();
604
- });
605
-
606
- it("should validate", () => {
607
- inputElm.querySelector("input").value = "2013-W03";
608
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
609
- expect(
610
- inputElm.querySelector("input").classList.contains("ng-valid"),
611
- ).toBeTrue();
612
- expect(scope.value).toBe("2013-W03");
613
- expect(scope.form.alias.$error.min).toBeFalsy();
614
- });
615
-
616
- // THIS WORKED WITH LEGACY DIGEST CYCLE BUT IT IS UNCLEAR IF THE CASE STILL APPLIES AS THERE IS NO MODEL CHANGE AND THUS NO TRIGGER
617
- // it("should revalidate when the min value changes", async () => {
618
- // inputElm.querySelector("input").value = "2013-W03";
619
- // inputElm.querySelector("input").dispatchEvent(new Event("change"));
620
- // expect(
621
- // inputElm.querySelector("input").classList.contains("ng-valid"),
622
- // ).toBeTrue();
623
- // expect(scope.form.alias.$error.min).toBeFalsy();
624
-
625
- // scope.minVal = "2014-W01";
626
- // debugger
627
- // await wait();
628
- // expect(
629
- // inputElm.querySelector("input").classList.contains("ng-invalid"),
630
- // ).toBeTrue();
631
- // expect(scope.form.alias.$error.min).toBeTruthy();
632
- // });
633
-
634
- it("should validate if min is empty", async () => {
635
- scope.minVal = undefined;
636
- scope.value = "2013-W03";
637
- await wait();
638
- expect(scope.form.alias.$error.min).toBeFalsy();
639
- });
640
- });
641
-
642
- describe("max", () => {
643
- let inputElm;
644
-
645
- beforeEach(async () => {
646
- scope.maxVal = "2013-W01";
647
- inputElm = $compile(
648
- '<form name="form"><input type="week" ng-model="value" name="alias" max="{{ maxVal }}" /></form>',
649
- )(scope);
650
- await wait();
651
- });
652
-
653
- it("should validate", () => {
654
- inputElm.querySelector("input").value = "2012-W01";
655
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
656
- expect(
657
- inputElm.querySelector("input").classList.contains("ng-valid"),
658
- ).toBeTrue();
659
- expect(scope.value).toBe("2012-W01");
660
- expect(scope.form.alias.$error.max).toBeFalsy();
661
- });
662
-
663
- it("should invalidate", () => {
664
- inputElm.querySelector("input").value = "2013-W03";
665
- inputElm.querySelector("input").dispatchEvent(new Event("change"));
666
- expect(
667
- inputElm.querySelector("input").classList.contains("ng-invalid"),
668
- ).toBeTrue();
669
- expect(scope.value).toBeUndefined();
670
- expect(scope.form.alias.$error.max).toBeTruthy();
671
- });
672
-
673
- // TODO
674
- // it("should revalidate when the max value changes", async () => {
675
- // inputElm.querySelector("input").value = "2012-W03";
676
- // inputElm.querySelector("input").dispatchEvent(new Event("change"));
677
- // expect(
678
- // inputElm.querySelector("input").classList.contains("ng-valid"),
679
- // ).toBeTrue();
680
- // expect(scope.form.alias.$error.max).toBeFalsy();
681
-
682
- // scope.maxVal = "2012-W01";
683
- // await wait();
684
- // expect(
685
- // inputElm.querySelector("input").classList.contains("ng-invalid"),
686
- // ).toBeTrue();
687
- // expect(scope.form.alias.$error.max).toBeTruthy();
688
- // });
689
-
690
- it("should validate if max is empty", async () => {
691
- scope.maxVal = undefined;
692
- scope.value = "2012-W01";
693
- await wait();
694
- expect(scope.form.alias.$error.max).toBeFalsy();
695
- });
696
- });
697
- });
698
-
699
- describe("datetime-local", () => {
700
- it("should throw if model is a Date object", async () => {
701
- inputElm = $compile(
702
- '<input type="datetime-local" ng-model="lunchtime"/>',
703
- )(scope);
704
- await wait();
705
- scope.$apply(() => {
706
- scope.lunchtime = new Date(2013, 11, 31, 23, 59, 59, 500);
707
- });
708
- await wait();
709
- expect(error[0]).toMatch("datefmt");
710
- });
711
-
712
- it("should set the view if the model if a valid String.", async () => {
713
- inputElm = $compile(
714
- '<input type="datetime-local" ng-model="halfSecondToNextYear"/>',
715
- )(scope);
716
- await wait();
717
- scope.$apply(() => {
718
- scope.halfSecondToNextYear = "2013-12-16T11:30";
719
- });
720
- await wait();
721
- expect(inputElm.value).toBe("2013-12-16T11:30");
722
- });
723
-
724
- it("should bind to the model if a valid String.", async () => {
725
- inputElm = $compile(
726
- '<input type="datetime-local" ng-model="halfSecondToNextYear"/>',
727
- )(scope);
728
- await wait();
729
- inputElm.value = "2013-12-16T11:30";
730
- inputElm.dispatchEvent(new Event("change"));
731
-
732
- expect(inputElm.value).toBe("2013-12-16T11:30");
733
- expect(scope.halfSecondToNextYear).toBe("2013-12-16T11:30");
734
- });
735
-
736
- it("should set the model null if the view is invalid", async () => {
737
- inputElm = $compile(
738
- '<input type="datetime-local" ng-model="breakMe"/>',
739
- )(scope);
740
- await wait();
741
- scope.$apply(() => {
742
- scope.breakMe = "2013-12-16T11:30";
743
- });
744
- await wait();
745
- expect(inputElm.value).toBe("2013-12-16T11:30");
746
-
747
- // set to text for browsers with datetime-local validation.
748
-
749
- inputElm.value = "stuff";
750
- inputElm.dispatchEvent(new Event("change"));
751
- expect(inputElm.value).toBe("");
752
- expect(scope.breakMe).toBeNull();
753
- });
754
-
755
- it("should render as blank if null", async () => {
756
- inputElm = $compile('<input type="datetime-local" ng-model="test" />')(
757
- scope,
758
- );
759
- await wait();
760
- scope.$apply("test = null");
761
- await wait();
762
- expect(scope.test).toBeNull();
763
- expect(inputElm.value).toEqual("");
764
- });
765
-
766
- it("should come up blank when no value specified", async () => {
767
- inputElm = $compile('<input type="datetime-local" ng-model="test" />')(
768
- scope,
769
- );
770
- await wait();
771
- expect(inputElm.value).toBe("");
772
-
773
- scope.$apply("test = null");
774
- await wait();
775
- expect(scope.test).toBeNull();
776
- expect(inputElm.value).toBe("");
777
- });
778
-
779
- it("should parse empty string to null", async () => {
780
- inputElm = $compile('<input type="datetime-local" ng-model="test" />')(
781
- scope,
782
- );
783
- await wait();
784
- scope.$apply(() => {
785
- scope.test = "2013-12-16T11:30";
786
- });
787
- await wait();
788
- inputElm.value = "";
789
- inputElm.dispatchEvent(new Event("change"));
790
- expect(scope.test).toBeNull();
791
- });
792
-
793
- describe("min", () => {
794
- let inputElm;
795
- beforeEach(() => {
796
- scope.minVal = "2000-01-01T12:30:00";
797
- let formElm = $compile(
798
- `<form name="form">
799
- <input type="datetime-local" ng-model="value" name="alias" min="{{ minVal }}" />
800
- </form>`,
801
- )(scope);
802
- inputElm = formElm.querySelector("input");
803
- });
804
-
805
- it("should invalidate", () => {
806
- inputElm.value = "1999-12-31T01:02:00";
807
- inputElm.dispatchEvent(new Event("change"));
808
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
809
- expect(scope.value).toBeFalsy();
810
- expect(scope.form.alias.$error.min).toBeTruthy();
811
- });
812
-
813
- it("should validate", () => {
814
- inputElm.value = "2000-01-01T23:02:00";
815
- inputElm.dispatchEvent(new Event("change"));
816
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
817
- expect(scope.value).toBe("2000-01-01T23:02");
818
- expect(scope.form.alias.$error.min).toBeFalsy();
819
- });
820
-
821
- // it("should revalidate when the min value changes", async () => {
822
- // inputElm.value = "2000-02-01T01:02:00";
823
- // inputElm.dispatchEvent(new Event("change"));
824
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
825
- // expect(scope.form.alias.$error.min).toBeFalsy();
826
-
827
- // scope.minVal = "2010-01-01T01:02:00";
828
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
829
- // expect(scope.form.alias.$error.min).toBeTruthy();
830
- // });
831
-
832
- it("should validate if min is empty", () => {
833
- scope.minVal = undefined;
834
- scope.value = "2010-01-01T01:02:00";
835
- expect(scope.form.alias.$error.min).toBeFalsy();
836
- });
837
- });
838
-
839
- describe("max", () => {
840
- let inputElm;
841
- beforeEach(() => {
842
- scope.maxVal = "2019-01-01T01:02:00";
843
- let formElm = $compile(
844
- '<form name="form"><input type="datetime-local" ng-model="value" name="alias" max="{{ maxVal }}" /></form>',
845
- )(scope);
846
- inputElm = formElm.querySelector("input");
847
- });
848
-
849
- it("should invalidate", () => {
850
- inputElm.value = "2019-12-31T01:02:00";
851
- inputElm.dispatchEvent(new Event("change"));
852
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
853
- expect(scope.value).toBeFalsy();
854
- expect(scope.form.alias.$error.max).toBeTruthy();
855
- });
856
-
857
- it("should validate", () => {
858
- inputElm.value = "2000-01-01T01:02:00";
859
- inputElm.dispatchEvent(new Event("change"));
860
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
861
- expect(scope.value).toBe("2000-01-01T01:02");
862
- expect(scope.form.alias.$error.max).toBeFalsy();
863
- });
864
-
865
- // it("should revalidate when the max value changes", () => {
866
- // inputElm.value = "2000-02-01T01:02:00";
867
- // inputElm.dispatchEvent(new Event("change"));
868
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
869
- // expect(scope.form.alias.$error.max).toBeFalsy();
870
-
871
- // scope.maxVal = "2000-01-01T01:02:00";
872
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
873
- // expect(scope.form.alias.$error.max).toBeTruthy();
874
- // });
875
-
876
- it("should validate if max is empty", () => {
877
- scope.maxVal = undefined;
878
- scope.value = "2000-01-01T01:02:00";
879
- expect(scope.form.alias.$error.max).toBeFalsy();
880
- });
881
-
882
- it("should validate when timezone is provided.", () => {
883
- inputElm = $compile(
884
- '<input type="datetime-local" ng-model="value" name="alias" ' +
885
- 'max="{{ maxVal }}" ng-model-options="{timezone: \'UTC\', allowInvalid: true}"/>',
886
- )(scope);
887
- scope.maxVal = "2013-01-01T00:00:00";
888
- scope.value = "2012-01-01T00:00:00";
889
- expect(scope.form.alias.$error.max).toBeFalsy();
890
- expect(scope.form.alias.$valid).toBeTruthy();
891
-
892
- scope.value = "";
893
- inputElm.value = "2013-01-01T00:00:00";
894
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
895
- expect(scope.form.alias.$error.max).toBeFalsy();
896
- expect(scope.form.alias.$valid).toBeTruthy();
897
- });
898
- });
899
-
900
- // it("should validate even if max value changes on-the-fly", () => {
901
- // scope.max = "2013-01-01T01:02:00";
902
- // inputElm = $compile(
903
- // '<input type="datetime-local" ng-model="value" name="alias" max="{{max}}" />',
904
- // )(scope);
905
-
906
- // inputElm.value = "2014-01-01T12:34:00";
907
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
908
-
909
- // scope.max = "2001-01-01T01:02:00";
910
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
911
-
912
- // scope.max = "2024-01-01T01:02:00";
913
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
914
- // });
915
-
916
- // it("should validate even if min value changes on-the-fly", () => {
917
- // scope.min = "2013-01-01T01:02:00";
918
- // inputElm = $compile(
919
- // '<input type="datetime-local" ng-model="value" name="alias" min="{{min}}" />',
920
- // )(scope);
921
-
922
- // inputElm.value = "2010-01-01T12:34:00";
923
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
924
-
925
- // scope.min = "2014-01-01T01:02:00";
926
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
927
-
928
- // scope.min = "2009-01-01T01:02:00";
929
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
930
- // });
931
-
932
- // it("should validate even if ng-max value changes on-the-fly", () => {
933
- // scope.max = "2013-01-01T01:02:00";
934
- // inputElm = $compile(
935
- // '<input type="datetime-local" ng-model="value" name="alias" ng-max="max" />',
936
- // )(scope);
937
-
938
- // inputElm.value = "2014-01-01T12:34:00";
939
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
940
-
941
- // scope.max = "2001-01-01T01:02:00";
942
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
943
-
944
- // scope.max = "2024-01-01T01:02:00";
945
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
946
- // });
947
-
948
- // it("should validate even if ng-min value changes on-the-fly", () => {
949
- // scope.min = "2013-01-01T01:02:00";
950
- // inputElm = $compile(
951
- // '<input type="datetime-local" ng-model="value" name="alias" ng-min="min" />',
952
- // )(scope);
953
-
954
- // inputElm.value = "2010-01-01T12:34:00";
955
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
956
-
957
- // scope.min = "2014-01-01T01:02:00";
958
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
959
-
960
- // scope.min = "2009-01-01T01:02:00";
961
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
962
- // });
963
- });
964
-
965
- describe("time", () => {
966
- it("should throw if model is a Date object", async () => {
967
- inputElm = $compile('<input type="time" ng-model="lunchtime"/>')(scope);
968
- scope.$apply(() => {
969
- scope.lunchtime = new Date(1970, 0, 1, 15, 41, 0, 500);
970
- });
971
- await wait();
972
- expect(error[0]).toMatch("datefmt");
973
- });
974
-
975
- it("should set the view if the model is a valid String object.", async () => {
976
- inputElm = $compile('<input type="time" ng-model="threeFortyOnePm"/>')(
977
- scope,
978
- );
979
-
980
- scope.$apply(() => {
981
- scope.threeFortyOnePm = "15:41:00.500";
982
- });
983
- await wait();
984
- expect(inputElm.value).toBe("15:41:00.500");
985
- });
986
-
987
- it("should bind to mode if a valid String object.", () => {
988
- inputElm = $compile('<input type="time" ng-model="threeFortyOnePm"/>')(
989
- scope,
990
- );
991
-
992
- inputElm.value = "15:41:00.500";
993
- inputElm.dispatchEvent(new Event("change"));
994
-
995
- expect(inputElm.value).toBe("15:41:00.500");
996
- expect(scope.threeFortyOnePm).toBe("15:41:00.500");
997
- });
998
-
999
- it("should set the model to null if the view is invalid", async () => {
1000
- inputElm = $compile('<input type="time" ng-model="breakMe"/>')(scope);
1001
-
1002
- scope.$apply(() => {
1003
- scope.breakMe = "16:25:00.000";
1004
- });
1005
- await wait();
1006
- expect(inputElm.value).toBe("16:25:00.000");
1007
-
1008
- inputElm.value = "stuff";
1009
- inputElm.dispatchEvent(new Event("change"));
1010
- await wait();
1011
- expect(inputElm.value).toBe("");
1012
- expect(scope.breakMe).toBeNull();
1013
- });
1014
-
1015
- it("should set blank if null", () => {
1016
- inputElm = $compile('<input type="time" ng-model="test" />')(scope);
1017
-
1018
- scope.$apply("test = null");
1019
-
1020
- expect(scope.test).toBeNull();
1021
- expect(inputElm.value).toEqual("");
1022
- });
1023
-
1024
- it("should set blank when no value specified", () => {
1025
- inputElm = $compile('<input type="time" ng-model="test" />')(scope);
1026
-
1027
- expect(inputElm.value).toBe("");
1028
-
1029
- scope.$apply("test = null");
1030
-
1031
- expect(scope.test).toBeNull();
1032
- expect(inputElm.value).toBe("");
1033
- });
1034
-
1035
- it("should parse empty string to null", () => {
1036
- inputElm = $compile('<input type="time" ng-model="test" />')(scope);
1037
-
1038
- scope.$apply(() => {
1039
- scope.test = "16:25:00";
1040
- });
1041
-
1042
- inputElm.value = "";
1043
- inputElm.dispatchEvent(new Event("change"));
1044
- expect(scope.test).toBeNull();
1045
- });
1046
-
1047
- it("should allow to specify the milliseconds", () => {
1048
- inputElm = $compile('<input type="time" ng-model="value"" />')(scope);
1049
-
1050
- inputElm.value = "01:02:03.500";
1051
- inputElm.dispatchEvent(new Event("change"));
1052
- expect(scope.value).toBe("01:02:03.500");
1053
- });
1054
-
1055
- it("should allow to specify single digit milliseconds", () => {
1056
- inputElm = $compile('<input type="time" ng-model="value"" />')(scope);
1057
-
1058
- inputElm.value = "01:02:03.4";
1059
- inputElm.dispatchEvent(new Event("change"));
1060
- expect(scope.value).toBe("01:02:03.4");
1061
- });
1062
-
1063
- it("should allow to specify the seconds", async () => {
1064
- inputElm = $compile('<input type="time" ng-model="value"" />')(scope);
1065
-
1066
- inputElm.value = "01:02:03";
1067
- inputElm.dispatchEvent(new Event("change"));
1068
- await wait();
1069
- expect(scope.value).toBe("01:02:03");
1070
-
1071
- scope.$apply(() => {
1072
- scope.value = "01:02:03.000";
1073
- });
1074
- await wait();
1075
- expect(inputElm.value).toBe("01:02:03.000");
1076
- });
1077
-
1078
- describe("min", () => {
1079
- let inputElm;
1080
- beforeEach(() => {
1081
- scope.minVal = "09:30:00";
1082
- let formElm = $compile(
1083
- '<form name="form"><input type="time" ng-model="value" name="alias" min="{{ minVal }}" /></form>',
1084
- )(scope);
1085
- inputElm = formElm.querySelector("input");
1086
- });
1087
-
1088
- it("should invalidate", () => {
1089
- inputElm.value = "01:02:03";
1090
- inputElm.dispatchEvent(new Event("change"));
1091
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1092
- expect(scope.value).toBeFalsy();
1093
- expect(scope.form.alias.$error.min).toBeTruthy();
1094
- });
1095
-
1096
- it("should validate", () => {
1097
- inputElm.value = "23:02:00";
1098
- inputElm.dispatchEvent(new Event("change"));
1099
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1100
- expect(scope.value).toBe("23:02:00");
1101
- expect(scope.form.alias.$error.min).toBeFalsy();
1102
- });
1103
-
1104
- // it("should revalidate when the min value changes", async () => {
1105
- // inputElm.value = "23:02:00";
1106
- // inputElm.dispatchEvent(new Event("change"));
1107
- // await wait();
1108
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1109
- // expect(scope.form.alias.$error.min).toBeFalsy();
1110
-
1111
- // scope.minVal = "23:55:00";
1112
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1113
- // expect(scope.form.alias.$error.min).toBeTruthy();
1114
- // });
1115
-
1116
- it("should validate if min is empty", () => {
1117
- scope.minVal = undefined;
1118
- scope.value = "23:55:00";
1119
- expect(scope.form.alias.$error.min).toBeFalsy();
1120
- });
1121
- });
1122
-
1123
- describe("max", () => {
1124
- let inputElm;
1125
- beforeEach(() => {
1126
- scope.maxVal = "22:30:00";
1127
- let formElm = $compile(
1128
- '<form name="form"><input type="time" ng-model="value" name="alias" max="{{ maxVal }}" /></form>',
1129
- )(scope);
1130
- inputElm = formElm.querySelector("input");
1131
- });
1132
-
1133
- it("should invalidate", () => {
1134
- inputElm.value = "23:00:00";
1135
- inputElm.dispatchEvent(new Event("change"));
1136
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1137
- expect(scope.value).toBeFalsy();
1138
- expect(scope.form.alias.$error.max).toBeTruthy();
1139
- });
1140
-
1141
- it("should validate", () => {
1142
- inputElm.value = "05:30:00";
1143
- inputElm.dispatchEvent(new Event("change"));
1144
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1145
- expect(scope.value).toBe("05:30:00");
1146
- expect(scope.form.alias.$error.max).toBeFalsy();
1147
- });
1148
-
1149
- it("should validate if max is empty", () => {
1150
- scope.maxVal = undefined;
1151
- scope.value = "05:30:00";
1152
- expect(scope.form.alias.$error.max).toBeFalsy();
1153
- });
1154
- });
1155
-
1156
- // it("should validate even if max value changes on-the-fly", async () => {
1157
- // scope.max = "04:02:00";
1158
- // inputElm = $compile(
1159
- // '<input type="time" ng-model="value" name="alias" max="{{max}}" />',
1160
- // )(scope);
1161
-
1162
- // inputElm.value = "05:34:00";
1163
- // inputElm.dispatchEvent(new Event("change"));
1164
-
1165
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1166
-
1167
- // scope.max = "06:34:00";
1168
- // await wait();
1169
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1170
- // });
1171
-
1172
- // it("should validate even if min value changes on-the-fly", () => {
1173
- // scope.min = "08:45:00";
1174
- // inputElm = $compile(
1175
- // '<input type="time" ng-model="value" name="alias" min="{{min}}" />',
1176
- // )(scope);
1177
-
1178
- // inputElm.value = "06:15:00";
1179
- // inputElm.dispatchEvent(new Event("change"));
1180
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1181
-
1182
- // scope.min = "05:50:00";
1183
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1184
- // });
1185
-
1186
- // it("should validate even if ng-max value changes on-the-fly", () => {
1187
- // scope.max = "04:02:00";
1188
- // inputElm = $compile(
1189
- // '<input type="time" ng-model="value" name="alias" ng-max="max" />',
1190
- // )(scope);
1191
-
1192
- // inputElm.value = "05:34:00";
1193
- // inputElm.dispatchEvent(new Event("change"));
1194
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1195
-
1196
- // scope.max = "06:34:00";
1197
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1198
- // });
1199
-
1200
- // it("should validate even if ng-min value changes on-the-fly", () => {
1201
- // scope.min = "08:45:00";
1202
- // inputElm = $compile(
1203
- // '<input type="time" ng-model="value" name="alias" ng-min="min" />',
1204
- // )(scope);
1205
-
1206
- // inputElm.value = "06:15:00";
1207
- // inputElm.dispatchEvent(new Event("change"));
1208
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1209
-
1210
- // scope.min = "05:50:00";
1211
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1212
- // });
1213
- });
1214
-
1215
- describe("date", () => {
1216
- it("should throw if model is a Date object", async () => {
1217
- inputElm = $compile('<input type="date" ng-model="birthday"/>')(scope);
1218
- scope.$apply(() => {
1219
- scope.birthday = new Date("a");
1220
- });
1221
- await wait();
1222
- expect(error[0]).toMatch("datefmt");
1223
- });
1224
-
1225
- it("should set the view when the model is an valid String", async () => {
1226
- inputElm = $compile('<input type="date" ng-model="val"/>')(scope);
1227
-
1228
- scope.$apply(() => {
1229
- scope.val = "1977-10-22";
1230
- });
1231
- await wait();
1232
- expect(inputElm.value).toBe("1977-10-22");
1233
- });
1234
-
1235
- it("should bind to scope when the model is an valid String", () => {
1236
- inputElm = $compile('<input type="date" ng-model="val"/>')(scope);
1237
-
1238
- inputElm.value = "1977-10-22";
1239
- inputElm.dispatchEvent(new Event("change"));
1240
-
1241
- expect(scope.val).toBe("1977-10-22");
1242
- });
1243
-
1244
- it("should set the model to null if the view is invalid", async () => {
1245
- inputElm = $compile('<input type="date" ng-model="arrMatey"/>')(scope);
1246
-
1247
- scope.$apply(() => {
1248
- scope.arrMatey = "2014-09-14";
1249
- });
1250
- await wait();
1251
- expect(inputElm.value).toBe("2014-09-14");
1252
-
1253
- // set to text for browsers with date validation.
1254
- inputElm.value = "1-2-3";
1255
- inputElm.dispatchEvent(new Event("change"));
1256
- await wait();
1257
- expect(inputElm.value).toBe("");
1258
- expect(scope.arrMatey).toBeNull();
1259
- });
1260
-
1261
- it("should render as blank if null", () => {
1262
- inputElm = $compile('<input type="date" ng-model="test" />')(scope);
1263
-
1264
- scope.$apply("test = null");
1265
-
1266
- expect(scope.test).toBeNull();
1267
- expect(inputElm.value).toEqual("");
1268
- });
1269
-
1270
- it("should come up blank when no value specified", () => {
1271
- inputElm = $compile('<input type="date" ng-model="test" />')(scope);
1272
-
1273
- expect(inputElm.value).toBe("");
1274
-
1275
- scope.$apply("test = null");
1276
-
1277
- expect(scope.test).toBeNull();
1278
- expect(inputElm.value).toBe("");
1279
- });
1280
-
1281
- it("should parse empty string to null", () => {
1282
- inputElm = $compile('<input type="date" ng-model="test" />')(scope);
1283
-
1284
- scope.$apply(() => {
1285
- scope.test = "2014-09-14";
1286
- });
1287
-
1288
- inputElm.value = "";
1289
- inputElm.dispatchEvent(new Event("change"));
1290
- expect(scope.test).toBeNull();
1291
- });
1292
-
1293
- describe("min", () => {
1294
- it("should invalidate", () => {
1295
- const formElm = $compile(
1296
- '<form name="form"><input type="date" ng-model="value" name="alias" min="2000-01-01" /></form>',
1297
- )(scope);
1298
- inputElm = formElm.querySelector("input");
1299
- inputElm.value = "1999-12-31";
1300
- inputElm.dispatchEvent(new Event("change"));
1301
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1302
- expect(scope.value).toBeFalsy();
1303
- expect(scope.form.alias.$error.min).toBeTruthy();
1304
- });
1305
-
1306
- it("should validate", () => {
1307
- const formElm = $compile(
1308
- '<form name="form"><input type="date" ng-model="value" name="alias" min="2000-01-01" /></form>',
1309
- )(scope);
1310
- inputElm = formElm.querySelector("input");
1311
- inputElm.value = "2000-01-01";
1312
- inputElm.dispatchEvent(new Event("change"));
1313
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1314
- expect(scope.value).toBe("2000-01-01");
1315
- expect(scope.form.alias.$error.min).toBeFalsy();
1316
- });
1317
-
1318
- it("should validate if min is empty", () => {
1319
- const formElm = $compile(
1320
- '<form name="form"><input name="alias" ng-model="value" type="date" min >',
1321
- )(scope);
1322
- inputElm = formElm.querySelector("input");
1323
-
1324
- scope.value = "2000-01-01";
1325
- expect(scope.form.alias.$error.min).toBeFalsy();
1326
- });
1327
- });
1328
-
1329
- describe("max", () => {
1330
- it("should invalidate", () => {
1331
- const formElm = $compile(
1332
- '<form name="form"><input type="date" ng-model="value" name="alias" max="2019-01-01" /></form>',
1333
- )(scope);
1334
- inputElm = formElm.querySelector("input");
1335
-
1336
- inputElm.value = "2019-12-31";
1337
- inputElm.dispatchEvent(new Event("change"));
1338
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1339
- expect(scope.value).toBeFalsy();
1340
- expect(scope.form.alias.$error.max).toBeTruthy();
1341
- });
1342
-
1343
- it("should validate", () => {
1344
- const formElm = $compile(
1345
- '<form name="form"><input type="date" ng-model="value" name="alias" max="2019-01-01" /></form>',
1346
- )(scope);
1347
- inputElm = formElm.querySelector("input");
1348
-
1349
- inputElm.value = "2000-01-01";
1350
- inputElm.dispatchEvent(new Event("change"));
1351
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1352
- expect(scope.value).toBe("2000-01-01");
1353
- expect(scope.form.alias.$error.max).toBeFalsy();
1354
- });
1355
-
1356
- it("should parse ISO-based date strings as a valid max date value", async () => {
1357
- scope.max = new Date(2014, 10, 10, 0, 0, 0).toISOString();
1358
- $compile(
1359
- '<form name="form"><input name="myControl" type="date" max="{{ max }}" ng-model="value"></form>',
1360
- )(scope);
1361
- await wait();
1362
- scope.value = "2020-01-01";
1363
- await wait();
1364
- expect(scope.form.myControl.$error.max).toBeTruthy();
1365
- });
1366
-
1367
- it("should validate if max is empty", () => {
1368
- $compile(
1369
- '<form name="form"><input type="date" name="alias" ng-model="value" max /></form>',
1370
- )(scope);
1371
-
1372
- scope.value = "2020-01-01";
1373
- expect(scope.form.alias.$error.max).toBeFalsy();
1374
- });
1375
- });
1376
-
1377
- // it("should validate even if max value changes on-the-fly", () => {
1378
- // scope.max = "2013-01-01";
1379
- // inputElm = $compile(
1380
- // '<input type="date" ng-model="value" name="alias" max="{{max}}" />',
1381
- // )(scope);
1382
-
1383
- // inputElm.value = "2014-01-01";
1384
- // inputElm.dispatchEvent(new Event("change"));
1385
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1386
-
1387
- // scope.max = "2001-01-01";
1388
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1389
-
1390
- // scope.max = "2021-01-01";
1391
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1392
- // });
1393
-
1394
- // it("should validate even if min value changes on-the-fly", () => {
1395
- // scope.min = "2013-01-01";
1396
- // inputElm = $compile(
1397
- // '<input type="date" ng-model="value" name="alias" min="{{min}}" />',
1398
- // )(scope);
1399
-
1400
- // inputElm.value = "2010-01-01";
1401
- // inputElm.dispatchEvent(new Event("change"));
1402
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1403
-
1404
- // scope.min = "2014-01-01";
1405
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1406
-
1407
- // scope.min = "2009-01-01";
1408
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1409
- // });
1410
-
1411
- // it("should validate even if ng-max value changes on-the-fly", () => {
1412
- // scope.max = "2013-01-01";
1413
- // inputElm = $compile(
1414
- // '<input type="date" ng-model="value" name="alias" ng-max="max" />',
1415
- // )(scope);
1416
-
1417
- // inputElm.value = "2014-01-01";
1418
- // inputElm.dispatchEvent(new Event("change"));
1419
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1420
-
1421
- // scope.max = "2001-01-01";
1422
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1423
-
1424
- // scope.max = "2021-01-01";
1425
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1426
- // });
1427
-
1428
- // it("should validate even if ng-min value changes on-the-fly", () => {
1429
- // scope.min = "2013-01-01";
1430
- // inputElm = $compile(
1431
- // '<input type="date" ng-model="value" name="alias" ng-min="min" />',
1432
- // )(scope);
1433
-
1434
- // inputElm.value = "2010-01-01";
1435
- // inputElm.dispatchEvent(new Event("change"));
1436
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1437
-
1438
- // scope.min = "2014-01-01";
1439
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1440
-
1441
- // scope.min = "2009-01-01";
1442
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1443
- // });
1444
-
1445
- it("should allow Date objects as valid ng-max values", async () => {
1446
- scope.max = new Date(2012, 1, 1, 1, 2, 0);
1447
- inputElm = $compile(
1448
- '<input type="date" ng-model="value" name="alias" ng-max="max" />',
1449
- )(scope);
1450
- await wait();
1451
- inputElm.value = "2014-01-01";
1452
- inputElm.dispatchEvent(new Event("change"));
1453
- await wait();
1454
-
1455
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1456
-
1457
- // scope.max = new Date(2013, 1, 1, 1, 2, 0);
1458
- // await wait();
1459
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1460
-
1461
- // scope.max = new Date(2014, 1, 1, 1, 2, 0);
1462
- // await wait();
1463
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1464
- });
1465
-
1466
- it("should allow Date objects as valid ng-min values", async () => {
1467
- scope.min = new Date(2013, 1, 1, 1, 2, 0);
1468
- inputElm = $compile(
1469
- '<input type="date" ng-model="value" name="alias" ng-min="min" />',
1470
- )(scope);
1471
- await wait();
1472
- inputElm.value = "2010-01-01";
1473
- inputElm.dispatchEvent(new Event("change"));
1474
- await wait();
1475
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1476
-
1477
- // scope.min = new Date(2014, 1, 1, 1, 2, 0);
1478
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1479
-
1480
- // scope.min = new Date(2009, 1, 1, 1, 2, 0);
1481
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1482
- });
1483
-
1484
- describe("ISO_DATE_REGEXP", () => {
1485
- [
1486
- // Validate date
1487
- ["00:00:00.0000+01:01", false], // date must be specified
1488
- ["2010.06.15T00:00:00.0000+01:01", false], // date must use dash separator
1489
- ["x2010-06-15T00:00:00.0000+01:01", false], // invalid leading characters
1490
-
1491
- // Validate year
1492
- ["2010-06-15T00:00:00.0000+01:01", true], // year has four or more digits
1493
- ["20100-06-15T00:00:00.0000+01:01", true], // year has four or more digits
1494
- ["-06-15T00:00:00.0000+01:01", false], // year has too few digits
1495
- ["2-06-15T00:00:00.0000+01:01", false], // year has too few digits
1496
- ["20-06-15T00:00:00.0000+01:01", false], // year has too few digits
1497
- ["201-06-15T00:00:00.0000+01:01", false], // year has too few digits
1498
-
1499
- // Validate month
1500
- ["2010-01-15T00:00:00.0000+01:01", true], // month has two digits
1501
- ["2010--15T00:00:00.0000+01:01", false], // month has too few digits
1502
- ["2010-0-15T00:00:00.0000+01:01", false], // month has too few digits
1503
- ["2010-1-15T00:00:00.0000+01:01", false], // month has too few digits
1504
- ["2010-111-15T00:00:00.0000+01:01", false], // month has too many digits
1505
- ["2010-22-15T00:00:00.0000+01:01", false], // month is too large
1506
-
1507
- // Validate day
1508
- ["2010-01-01T00:00:00.0000+01:01", true], // day has two digits
1509
- ["2010-01-T00:00:00.0000+01:01", false], // day has too few digits
1510
- ["2010-01-1T00:00:00.0000+01:01", false], // day has too few digits
1511
- ["2010-01-200T00:00:00.0000+01:01", false], // day has too many digits
1512
- ["2010-01-41T00:00:00.0000+01:01", false], // day is too large
1513
-
1514
- // Validate time
1515
- ["2010-01-01", false], // time must be specified
1516
- ["2010-01-0101:00:00.0000+01:01", false], // missing date time separator
1517
- ["2010-01-01V01:00:00.0000+01:01", false], // invalid date time separator
1518
- ["2010-01-01T01-00-00.0000+01:01", false], // time must use colon separator
1519
-
1520
- // Validate hour
1521
- ["2010-01-01T01:00:00.0000+01:01", true], // hour has two digits
1522
- ["2010-01-01T-01:00:00.0000+01:01", false], // hour must be positive
1523
- ["2010-01-01T:00:00.0000+01:01", false], // hour has too few digits
1524
- ["2010-01-01T1:00:00.0000+01:01", false], // hour has too few digits
1525
- ["2010-01-01T220:00:00.0000+01:01", false], // hour has too many digits
1526
- ["2010-01-01T32:00:00.0000+01:01", false], // hour is too large
1527
-
1528
- // Validate minutes
1529
- ["2010-01-01T01:00:00.0000+01:01", true], // minute has two digits
1530
- ["2010-01-01T01:-00:00.0000+01:01", false], // minute must be positive
1531
- ["2010-01-01T01::00.0000+01:01", false], // minute has too few digits
1532
- ["2010-01-01T01:0:00.0000+01:01", false], // minute has too few digits
1533
- ["2010-01-01T01:100:00.0000+01:01", false], // minute has too many digits
1534
- ["2010-01-01T01:60:00.0000+01:01", false], // minute is too large
1535
-
1536
- // Validate seconds
1537
- ["2010-01-01T01:00:00.0000+01:01", true], // second has two digits
1538
- ["2010-01-01T01:00:-00.0000+01:01", false], // second must be positive
1539
- ["2010-01-01T01:00:.0000+01:01", false], // second has too few digits
1540
- ["2010-01-01T01:00:0.0000+01:01", false], // second has too few digits
1541
- ["2010-01-01T01:00:100.0000+01:01", false], // second has too many digits
1542
- ["2010-01-01T01:00:60.0000+01:01", false], // second is too large
1543
-
1544
- // Validate milliseconds
1545
- ["2010-01-01T01:00:00+01:01", false], // millisecond must be specified
1546
- ["2010-01-01T01:00:00.-0000+01:01", false], // millisecond must be positive
1547
- ["2010-01-01T01:00:00:0000+01:01", false], // millisecond must use period separator
1548
- ["2010-01-01T01:00:00.+01:01", false], // millisecond has too few digits
1549
-
1550
- // Validate timezone
1551
- ["2010-06-15T00:00:00.0000", false], // timezone must be specified
1552
-
1553
- // Validate timezone offset
1554
- ["2010-06-15T00:00:00.0000+01:01", true], // timezone offset can be positive hours and minutes
1555
- ["2010-06-15T00:00:00.0000-01:01", true], // timezone offset can be negative hours and minutes
1556
- ["2010-06-15T00:00:00.0000~01:01", false], // timezone has postive/negative indicator
1557
- ["2010-06-15T00:00:00.000001:01", false], // timezone has postive/negative indicator
1558
- ["2010-06-15T00:00:00.0000+00:01Z", false], // timezone invalid trailing characters
1559
- ["2010-06-15T00:00:00.0000+00:01 ", false], // timezone invalid trailing characters
1560
-
1561
- // Validate timezone hour offset
1562
- ["2010-06-15T00:00:00.0000+:01", false], // timezone hour offset has too few digits
1563
- ["2010-06-15T00:00:00.0000+0:01", false], // timezone hour offset has too few digits
1564
- ["2010-06-15T00:00:00.0000+211:01", false], // timezone hour offset too many digits
1565
- ["2010-06-15T00:00:00.0000+31:01", false], // timezone hour offset value too large
1566
-
1567
- // Validate timezone minute offset
1568
- ["2010-06-15T00:00:00.0000+00:-01", false], // timezone minute offset must be positive
1569
- ["2010-06-15T00:00:00.0000+00.01", false], // timezone minute offset must use colon separator
1570
- ["2010-06-15T00:00:00.0000+0101", false], // timezone minute offset must use colon separator
1571
- ["2010-06-15T00:00:00.0000+010", false], // timezone minute offset must use colon separator
1572
- ["2010-06-15T00:00:00.0000+00", false], // timezone minute offset has too few digits
1573
- ["2010-06-15T00:00:00.0000+00:", false], // timezone minute offset has too few digits
1574
- ["2010-06-15T00:00:00.0000+00:0", false], // timezone minute offset has too few digits
1575
- ["2010-06-15T00:00:00.0000+00:211", false], // timezone minute offset has too many digits
1576
- ["2010-06-15T00:00:00.0000+01010", false], // timezone minute offset has too many digits
1577
- ["2010-06-15T00:00:00.0000+00:61", false], // timezone minute offset is too large
1578
-
1579
- // Validate timezone UTC
1580
- ["2010-06-15T00:00:00.0000Z", true], // UTC timezone can be indicated with Z
1581
- ["2010-06-15T00:00:00.0000K", false], // UTC timezone indicator is invalid
1582
- ["2010-06-15T00:00:00.0000 Z", false], // UTC timezone indicator has extra space
1583
- ["2010-06-15T00:00:00.0000ZZ", false], // UTC timezone indicator invalid trailing characters
1584
- ["2010-06-15T00:00:00.0000Z ", false], // UTC timezone indicator invalid trailing characters
1585
- ].forEach((item) => {
1586
- it("should validate date: $prop", () => {
1587
- const date = item[0];
1588
- const valid = item[1];
1589
-
1590
- expect(ISO_DATE_REGEXP.test(date)).toBe(valid);
1591
- });
1592
- });
1593
- });
1594
- });
1595
-
1596
- describe("number", () => {
1597
- // Helpers for min / max tests
1598
- const subtract = function (value) {
1599
- return value - 5;
1600
- };
1601
-
1602
- const add = function (value) {
1603
- return value + 5;
1604
- };
1605
-
1606
- it("should reset the model if view is invalid", async () => {
1607
- inputElm = $compile('<input type="number" ng-model="age"/>')(scope);
1608
-
1609
- scope.$apply("age = 123");
1610
- await wait();
1611
- expect(inputElm.value).toBe("123");
1612
-
1613
- inputElm.value = "123X";
1614
- inputElm.dispatchEvent(new Event("change"));
1615
-
1616
- expect(inputElm.value).toBe("");
1617
- expect(scope.age).toBeNull();
1618
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1619
- });
1620
-
1621
- it("should render as blank if null", async () => {
1622
- inputElm = $compile('<input type="number" ng-model="age" />')(scope);
1623
-
1624
- scope.$apply("age = null");
1625
- await wait();
1626
- expect(scope.age).toBeNull();
1627
- expect(inputElm.value).toEqual("");
1628
- });
1629
-
1630
- it("should come up blank when no value specified", async () => {
1631
- inputElm = $compile('<input type="number" ng-model="age" />')(scope);
1632
-
1633
- expect(inputElm.value).toBe("");
1634
-
1635
- scope.$apply("age = null");
1636
- await wait();
1637
- expect(scope.age).toBeNull();
1638
- expect(inputElm.value).toBe("");
1639
- });
1640
-
1641
- it("should parse empty string to null", async () => {
1642
- inputElm = $compile('<input type="number" ng-model="age" />')(scope);
1643
-
1644
- scope.$apply("age = 10");
1645
- await wait();
1646
- inputElm.value = "";
1647
- inputElm.dispatchEvent(new Event("change"));
1648
-
1649
- expect(scope.age).toBeNull();
1650
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1651
- });
1652
-
1653
- it("should only invalidate the model if suffering from bad input when the data is parsed", async () => {
1654
- inputElm = $compile('<input type="number" ng-model="age" />')(scope);
1655
- await wait();
1656
- expect(scope.age).toBeUndefined();
1657
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1658
-
1659
- inputElm.value = "this-will-fail-because-of-the-badInput-flag";
1660
- inputElm.dispatchEvent(new Event("change"));
1661
- await wait();
1662
- expect(scope.age).toBeUndefined();
1663
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1664
- });
1665
-
1666
- it("should validate number if transition from bad input to empty string", async () => {
1667
- inputElm = $compile('<input type="number" ng-model="age" />')(scope);
1668
- inputElm.value = "10a";
1669
- inputElm.dispatchEvent(new Event("change"));
1670
- await wait();
1671
- inputElm.value = "";
1672
- inputElm.dispatchEvent(new Event("change"));
1673
- await wait();
1674
- expect(scope.age).toBeUndefined();
1675
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1676
- });
1677
-
1678
- it("should validate with undefined viewValue when $validate() called", () => {
1679
- inputElm = $compile(
1680
- '<form name="form"><input type="number" name="alias" ng-model="value" /></form>',
1681
- )(scope);
1682
-
1683
- scope.form.alias.$validate();
1684
-
1685
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1686
- expect(scope.form.alias.$error.number).toBeUndefined();
1687
- });
1688
-
1689
- it("should throw if the model value is not a number", async () => {
1690
- scope.value = "one";
1691
- $compile('<input type="number" ng-model="value" />')(scope);
1692
- await wait();
1693
- expect(error[0]).toMatch("numfmt");
1694
- });
1695
-
1696
- it("should parse exponential notation", () => {
1697
- const formElm = $compile(
1698
- '<form name="form"><input type="number" name="alias" ng-model="value" /></form>',
1699
- )(scope);
1700
- inputElm = formElm.querySelector("input");
1701
-
1702
- // #.###e+##
1703
- scope.form.alias.$setViewValue("1.23214124123412412e+26");
1704
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1705
- expect(scope.value).toBe(1.23214124123412412e26);
1706
-
1707
- // #.###e##
1708
- scope.form.alias.$setViewValue("1.23214124123412412e26");
1709
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1710
- expect(scope.value).toBe(1.23214124123412412e26);
1711
-
1712
- // #.###e-##
1713
- scope.form.alias.$setViewValue("1.23214124123412412e-26");
1714
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1715
- expect(scope.value).toBe(1.23214124123412412e-26);
1716
-
1717
- // ####e+##
1718
- scope.form.alias.$setViewValue("123214124123412412e+26");
1719
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1720
- expect(scope.value).toBe(123214124123412412e26);
1721
-
1722
- // ####e##
1723
- scope.form.alias.$setViewValue("123214124123412412e26");
1724
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1725
- expect(scope.value).toBe(123214124123412412e26);
1726
-
1727
- // ####e-##
1728
- scope.form.alias.$setViewValue("123214124123412412e-26");
1729
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1730
- expect(scope.value).toBe(123214124123412412e-26);
1731
-
1732
- // #.###E+##
1733
- scope.form.alias.$setViewValue("1.23214124123412412E+26");
1734
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1735
- expect(scope.value).toBe(1.23214124123412412e26);
1736
-
1737
- // #.###E##
1738
- scope.form.alias.$setViewValue("1.23214124123412412E26");
1739
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1740
- expect(scope.value).toBe(1.23214124123412412e26);
1741
-
1742
- // #.###E-##
1743
- scope.form.alias.$setViewValue("1.23214124123412412E-26");
1744
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1745
- expect(scope.value).toBe(1.23214124123412412e-26);
1746
-
1747
- // ####E+##
1748
- scope.form.alias.$setViewValue("123214124123412412E+26");
1749
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1750
- expect(scope.value).toBe(123214124123412412e26);
1751
-
1752
- // ####E##
1753
- scope.form.alias.$setViewValue("123214124123412412E26");
1754
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1755
- expect(scope.value).toBe(123214124123412412e26);
1756
-
1757
- // ####E-##
1758
- scope.form.alias.$setViewValue("123214124123412412E-26");
1759
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1760
- expect(scope.value).toBe(123214124123412412e-26);
1761
- });
1762
-
1763
- it("should bind to scope if input is valid", async () => {
1764
- inputElm = $compile('<input type="number" ng-model="age"/>')(scope);
1765
- const ctrl = getController(inputElm, "ngModel");
1766
-
1767
- let previousParserFail = false;
1768
- let laterParserFail = false;
1769
-
1770
- ctrl.$parsers.unshift((value) =>
1771
- previousParserFail ? undefined : value,
1772
- );
1773
-
1774
- ctrl.$parsers.push((value) => (laterParserFail ? undefined : value));
1775
-
1776
- inputElm.value = "123X";
1777
- inputElm.dispatchEvent(new Event("change"));
1778
- await wait();
1779
- expect(inputElm.value).toBe("");
1780
-
1781
- expect(scope.age).toBeUndefined();
1782
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1783
- expect(ctrl.$error.number).toBeUndefined();
1784
-
1785
- inputElm.value = "123";
1786
- inputElm.dispatchEvent(new Event("change"));
1787
- await wait();
1788
- expect(inputElm.value).toBe("123");
1789
- expect(scope.age).toBe(123);
1790
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1791
- expect(ctrl.$error.number).toBeFalsy();
1792
- expect(ctrl.$error.parse).toBe(undefined);
1793
- });
1794
-
1795
- describe("min", () => {
1796
- it("should validate", () => {
1797
- const formElm = $compile(
1798
- '<form name="form"><input type="number" ng-model="value" name="alias" min="10" /></form>',
1799
- )(scope);
1800
- inputElm = formElm.querySelector("input");
1801
-
1802
- inputElm.value = "1";
1803
- inputElm.dispatchEvent(new Event("change"));
1804
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1805
- expect(scope.value).toBeFalsy();
1806
- expect(scope.form.alias.$error.min).toBeTruthy();
1807
-
1808
- inputElm.value = "100";
1809
- inputElm.dispatchEvent(new Event("change"));
1810
-
1811
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1812
- expect(scope.value).toBe(100);
1813
- expect(scope.form.alias.$error.min).toBeFalsy();
1814
- });
1815
-
1816
- it("should validate against the viewValue", () => {
1817
- const formElm = $compile(
1818
- '<form name="form"><input type="number" ng-model-options="{allowInvalid: true}" ng-model="value" name="alias" min="10" /></form>',
1819
- )(scope);
1820
- inputElm = formElm.querySelector("input");
1821
- const ngModelCtrl = getController(inputElm, "ngModel");
1822
- ngModelCtrl.$parsers.push(subtract);
1823
-
1824
- inputElm.value = "10";
1825
- inputElm.dispatchEvent(new Event("change"));
1826
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1827
- expect(scope.value).toBe(5);
1828
- expect(scope.form.alias.$error.min).toBeFalsy();
1829
-
1830
- ngModelCtrl.$parsers.pop();
1831
- ngModelCtrl.$parsers.push(add);
1832
-
1833
- inputElm.value = "5";
1834
- inputElm.dispatchEvent(new Event("change"));
1835
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1836
- expect(scope.form.alias.$error.min).toBeTruthy();
1837
- expect(scope.value).toBe(10);
1838
- });
1839
-
1840
- // it("should validate even if min value changes on-the-fly", () => {
1841
- // scope.min = undefined;
1842
- // inputElm = $compile(
1843
- // '<input type="number" ng-model="value" name="alias" min="{{min}}" />',
1844
- // )(scope);
1845
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1846
-
1847
- // inputElm.value = "15";
1848
- // inputElm.dispatchEvent(new Event("change"));
1849
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1850
-
1851
- // scope.min = 10;
1852
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1853
-
1854
- // scope.min = 20;
1855
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1856
-
1857
- // scope.min = null;
1858
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1859
-
1860
- // scope.min = "20";
1861
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1862
-
1863
- // scope.min = "abc";
1864
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1865
- // });
1866
- });
1867
-
1868
- describe("ngMin", () => {
1869
- it("should validate", () => {
1870
- const formElm = $compile(
1871
- '<form name="form"><input type="number" ng-model="value" name="alias" ng-min="50" /></form>',
1872
- )(scope);
1873
- inputElm = formElm.querySelector("input");
1874
-
1875
- inputElm.value = "1";
1876
- inputElm.dispatchEvent(new Event("change"));
1877
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1878
- expect(scope.value).toBeFalsy();
1879
- expect(scope.form.alias.$error.min).toBeTruthy();
1880
-
1881
- inputElm.value = "100";
1882
- inputElm.dispatchEvent(new Event("change"));
1883
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1884
- expect(scope.value).toBe(100);
1885
- expect(scope.form.alias.$error.min).toBeFalsy();
1886
- });
1887
-
1888
- it("should validate against the viewValue", () => {
1889
- const formElm = $compile(
1890
- '<form name="form"><input type="number" ng-model="value" name="alias" ng-min="10" /></form>',
1891
- )(scope);
1892
- inputElm = formElm.querySelector("input");
1893
- const ngModelCtrl = getController(inputElm, "ngModel");
1894
- ngModelCtrl.$parsers.push(subtract);
1895
-
1896
- inputElm.value = "10";
1897
- inputElm.dispatchEvent(new Event("change"));
1898
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1899
- expect(scope.value).toBe(5);
1900
- expect(scope.form.alias.$error.min).toBeFalsy();
1901
-
1902
- ngModelCtrl.$parsers.pop();
1903
- ngModelCtrl.$parsers.push(add);
1904
-
1905
- inputElm.value = "5";
1906
- inputElm.dispatchEvent(new Event("change"));
1907
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1908
- expect(scope.form.alias.$error.min).toBeTruthy();
1909
- expect(scope.value).toBe(undefined);
1910
- });
1911
-
1912
- // it("should validate even if the ngMin value changes on-the-fly", () => {
1913
- // scope.min = undefined;
1914
- // inputElm = $compile(
1915
- // '<input type="number" ng-model="value" name="alias" ng-min="min" />',
1916
- // )(scope);
1917
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1918
-
1919
- // inputElm.value = "15";
1920
- // inputElm.dispatchEvent(new Event("change"));
1921
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1922
-
1923
- // scope.min = 10;
1924
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1925
-
1926
- // scope.min = 20;
1927
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1928
-
1929
- // scope.min = null;
1930
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1931
-
1932
- // scope.min = "20";
1933
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1934
-
1935
- // scope.min = "abc";
1936
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1937
- // });
1938
- });
1939
-
1940
- describe("max", () => {
1941
- it("should validate", () => {
1942
- const formElm = $compile(
1943
- '<form name="form"><input type="number" ng-model="value" name="alias" max="10" /></form>',
1944
- )(scope);
1945
- inputElm = formElm.querySelector("input");
1946
-
1947
- inputElm.value = "20";
1948
- inputElm.dispatchEvent(new Event("change"));
1949
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1950
- expect(scope.value).toBeUndefined();
1951
- expect(scope.form.alias.$error.max).toBeTruthy();
1952
-
1953
- inputElm.value = "0";
1954
- inputElm.dispatchEvent(new Event("change"));
1955
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1956
- expect(scope.value).toBe(0);
1957
- expect(scope.form.alias.$error.max).toBeFalsy();
1958
- });
1959
-
1960
- it("should validate against the viewValue", () => {
1961
- const formElm = $compile(
1962
- '<form name="form"><input type="number"' +
1963
- 'ng-model-options="{allowInvalid: true}" ng-model="value" name="alias" max="10" /></form>',
1964
- )(scope);
1965
- inputElm = formElm.querySelector("input");
1966
- const ngModelCtrl = getController(inputElm, "ngModel");
1967
- ngModelCtrl.$parsers.push(add);
1968
-
1969
- inputElm.value = "10";
1970
- inputElm.dispatchEvent(new Event("change"));
1971
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1972
- expect(scope.value).toBe(15);
1973
- expect(scope.form.alias.$error.max).toBeFalsy();
1974
-
1975
- ngModelCtrl.$parsers.pop();
1976
- ngModelCtrl.$parsers.push(subtract);
1977
-
1978
- inputElm.value = "15";
1979
- inputElm.dispatchEvent(new Event("change"));
1980
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
1981
- expect(scope.form.alias.$error.max).toBeTruthy();
1982
- expect(scope.value).toBe(10);
1983
- });
1984
-
1985
- // it("should validate even if max value changes on-the-fly", () => {
1986
- // scope.max = undefined;
1987
- // inputElm = $compile(
1988
- // '<input type="number" ng-model="value" name="alias" max="{{max}}" />',
1989
- // )(scope);
1990
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1991
-
1992
- // inputElm.value = "5";
1993
- // inputElm.dispatchEvent(new Event("change"));
1994
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1995
-
1996
- // scope.max = 10;
1997
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
1998
-
1999
- // scope.max = 0;
2000
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2001
-
2002
- // scope.max = null;
2003
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2004
-
2005
- // scope.max = "4";
2006
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2007
-
2008
- // scope.max = "abc";
2009
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2010
- // });
2011
- });
2012
-
2013
- describe("ngMax", () => {
2014
- it("should validate", () => {
2015
- const formElm = $compile(
2016
- '<form name="form"><input type="number" ng-model="value" name="alias" ng-max="5" /></form>',
2017
- )(scope);
2018
- inputElm = formElm.querySelector("input");
2019
-
2020
- inputElm.value = "20";
2021
- inputElm.dispatchEvent(new Event("change"));
2022
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2023
- expect(scope.value).toBeUndefined();
2024
- expect(scope.form.alias.$error.max).toBeTruthy();
2025
-
2026
- inputElm.value = "0";
2027
- inputElm.dispatchEvent(new Event("change"));
2028
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2029
- expect(scope.value).toBe(0);
2030
- expect(scope.form.alias.$error.max).toBeFalsy();
2031
- });
2032
-
2033
- it("should validate against the viewValue", () => {
2034
- const formElm = $compile(
2035
- '<form name="form"><input type="number"' +
2036
- 'ng-model-options="{allowInvalid: true}" ng-model="value" name="alias" ng-max="10" /></form>',
2037
- )(scope);
2038
- inputElm = formElm.querySelector("input");
2039
- const ngModelCtrl = getController(inputElm, "ngModel");
2040
- ngModelCtrl.$parsers.push(add);
2041
-
2042
- inputElm.value = "10";
2043
- inputElm.dispatchEvent(new Event("change"));
2044
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2045
- expect(scope.value).toBe(15);
2046
- expect(scope.form.alias.$error.max).toBeFalsy();
2047
-
2048
- ngModelCtrl.$parsers.pop();
2049
- ngModelCtrl.$parsers.push(subtract);
2050
-
2051
- inputElm.value = "15";
2052
- inputElm.dispatchEvent(new Event("change"));
2053
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2054
- expect(scope.form.alias.$error.max).toBeTruthy();
2055
- expect(scope.value).toBe(10);
2056
- });
2057
-
2058
- // it("should validate even if the ngMax value changes on-the-fly", () => {
2059
- // scope.max = undefined;
2060
- // inputElm = $compile(
2061
- // '<input type="number" ng-model="value" name="alias" ng-max="max" />',
2062
- // )(scope);
2063
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2064
-
2065
- // inputElm.value = "5";
2066
- // inputElm.dispatchEvent(new Event("change"));
2067
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2068
-
2069
- // scope.max = 10;
2070
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2071
-
2072
- // scope.max = 0;
2073
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2074
-
2075
- // scope.max = null;
2076
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2077
-
2078
- // scope.max = "4";
2079
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2080
-
2081
- // scope.max = "abc";
2082
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2083
- // });
2084
- });
2085
-
2086
- Object.entries({
2087
- step: 'step="{{step}}"',
2088
- ngStep: 'ng-step="step"',
2089
- }).forEach(([attrName, attrHtml]) => {
2090
- describe(attrName, () => {
2091
- it("should validate", async () => {
2092
- scope.step = 10;
2093
- scope.value = 20;
2094
- const formElm = $compile(
2095
- `<form name="form"><input type="number" ng-model="value" name="alias" ${attrHtml} /></form>`,
2096
- )(scope);
2097
- inputElm = formElm.querySelector("input");
2098
- await wait();
2099
- expect(inputElm.value).toBe("20");
2100
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2101
- expect(scope.value).toBe(20);
2102
- expect(scope.form.alias.$error.step).toBeFalsy();
2103
-
2104
- inputElm.value = "18";
2105
- inputElm.dispatchEvent(new Event("change"));
2106
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2107
- expect(inputElm.value).toBe("18");
2108
- expect(scope.value).toBeUndefined();
2109
- expect(scope.form.alias.$error.step).toBeTruthy();
2110
-
2111
- inputElm.value = "10";
2112
- inputElm.dispatchEvent(new Event("change"));
2113
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2114
- expect(inputElm.value).toBe("10");
2115
- expect(scope.value).toBe(10);
2116
- expect(scope.form.alias.$error.step).toBeFalsy();
2117
-
2118
- scope.$apply("value = 12");
2119
- await wait();
2120
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2121
- expect(inputElm.value).toBe("12");
2122
- expect(scope.value).toBe(12);
2123
- expect(scope.form.alias.$error.step).toBeTruthy();
2124
- });
2125
-
2126
- // it("should validate even if the step value changes on-the-fly", () => {
2127
- // scope.step = 10;
2128
- // const formElm = $compile(
2129
- // `<form name="form"><input type="number" ng-model="value" name="alias" ${attrHtml} /></form>`,
2130
- // )(scope);
2131
- // inputElm = formElm.querySelector("input");
2132
- // inputElm.value = "10";
2133
- // inputElm.dispatchEvent(new Event("change"));
2134
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2135
- // expect(scope.value).toBe(10);
2136
-
2137
- // // Step changes, but value matches
2138
- // scope.$apply("step = 5");
2139
- // expect(inputElm.value).toBe("10");
2140
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2141
- // expect(scope.value).toBe(10);
2142
- // expect(scope.form.alias.$error.step).toBeFalsy();
2143
-
2144
- // // Step changes, value does not match
2145
- // scope.$apply("step = 6");
2146
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2147
- // expect(scope.value).toBeUndefined();
2148
- // expect(inputElm.value).toBe("10");
2149
- // expect(scope.form.alias.$error.step).toBeTruthy();
2150
-
2151
- // // null = valid
2152
- // scope.$apply("step = null");
2153
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2154
- // expect(scope.value).toBe(10);
2155
- // expect(inputElm.value).toBe("10");
2156
- // expect(scope.form.alias.$error.step).toBeFalsy();
2157
-
2158
- // // Step val as string
2159
- // scope.$apply('step = "7"');
2160
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2161
- // expect(scope.value).toBeUndefined();
2162
- // expect(inputElm.value).toBe("10");
2163
- // expect(scope.form.alias.$error.step).toBeTruthy();
2164
-
2165
- // // unparsable string is ignored
2166
- // scope.$apply('step = "abc"');
2167
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2168
- // expect(scope.value).toBe(10);
2169
- // expect(inputElm.value).toBe("10");
2170
- // expect(scope.form.alias.$error.step).toBeFalsy();
2171
- // });
2172
-
2173
- it('should use the correct "step base" when `[min]` is specified', async () => {
2174
- scope.min = 5;
2175
- scope.step = 10;
2176
- scope.value = 10;
2177
- inputElm = $compile(
2178
- `<input type="number" ng-model="value" min="{{min}}" ${attrHtml} />`,
2179
- )(scope);
2180
- const ngModel = getController(inputElm, "ngModel");
2181
- await wait();
2182
- expect(inputElm.value).toBe("10");
2183
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2184
- expect(ngModel.$error.step).toBe(true);
2185
- expect(scope.value).toBe(10); // an initially invalid value should not be changed
2186
-
2187
- inputElm.value = "15";
2188
- inputElm.dispatchEvent(new Event("change"));
2189
- await wait();
2190
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2191
- expect(scope.value).toBe(15);
2192
- // TODO
2193
- // scope.$apply("step = 3");
2194
- // await wait();
2195
- // expect(inputElm.value).toBe("15");
2196
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2197
- // expect(ngModel.$error.step).toBe(true);
2198
- // expect(scope.value).toBeUndefined();
2199
-
2200
- // inputElm.value = "8";
2201
- // inputElm.dispatchEvent(new Event("change"));
2202
- // await wait();
2203
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2204
- // expect(scope.value).toBe(8);
2205
-
2206
- // scope.$apply("min = 10; step = 20");
2207
- // inputElm.value = "30";
2208
- // inputElm.dispatchEvent(new Event("change"));
2209
- // await wait();
2210
- // expect(inputElm.value).toBe("30");
2211
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2212
- // expect(scope.value).toBe(30);
2213
-
2214
- // scope.$apply("min = 5");
2215
- // await wait();
2216
- // expect(inputElm.value).toBe("30");
2217
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2218
- // expect(ngModel.$error.step).toBe(true);
2219
- // expect(scope.value).toBeUndefined();
2220
-
2221
- // scope.$apply("step = 0.00000001");
2222
- // await wait();
2223
- // expect(inputElm.value).toBe("30");
2224
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2225
- // expect(scope.value).toBe(30);
2226
-
2227
- // // 0.3 - 0.2 === 0.09999999999999998
2228
- // scope.$apply("min = 0.2; step = (0.3 - 0.2)");
2229
- // inputElm.value = "0.3";
2230
- // inputElm.dispatchEvent(new Event("change"));
2231
- // await wait();
2232
- // expect(inputElm.value).toBe("0.3");
2233
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2234
- // expect(ngModel.$error.step).toBe(true);
2235
- // expect(scope.value).toBeUndefined();
2236
- });
2237
-
2238
- // it("should correctly validate even in cases where the JS floating point arithmetic fails", async () => {
2239
- // scope.step = 0.1;
2240
- // inputElm = $compile(
2241
- // `<input type="number" ng-model="value" ${attrHtml} />`,
2242
- // )(scope);
2243
- // await wait();
2244
- // const ngModel = getController(inputElm, "ngModel");
2245
-
2246
- // expect(inputElm.value).toBe("");
2247
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2248
- // expect(scope.value).toBeUndefined();
2249
-
2250
- // inputElm.value = "0.3";
2251
- // inputElm.dispatchEvent(new Event("change"));
2252
- // await wait();
2253
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2254
- // expect(scope.value).toBe(0.3);
2255
-
2256
- // inputElm.value = "2.9999999999999996";
2257
- // inputElm.dispatchEvent(new Event("change"));
2258
- // await wait();
2259
- // expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2260
- // expect(ngModel.$error.step).toBe(true);
2261
- // expect(scope.value).toBeUndefined();
2262
-
2263
- // // 0.5 % 0.1 === 0.09999999999999998
2264
- // inputElm.value = "0.5";
2265
- // inputElm.dispatchEvent(new Event("change"));
2266
- // await wait();
2267
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2268
- // expect(scope.value).toBe(0.5);
2269
-
2270
- // // // 3.5 % 0.1 === 0.09999999999999981
2271
- // inputElm.value = "3.5";
2272
- // inputElm.dispatchEvent(new Event("change"));
2273
- // await wait();
2274
- // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2275
- // expect(scope.value).toBe(3.5);
2276
-
2277
- // // // 1.16 % 0.01 === 0.009999999999999896
2278
- // // // 1.16 * 100 === 115.99999999999999
2279
- // // scope.step = 0.01;
2280
- // // inputElm.value = "1.16";
2281
- // // inputElm.dispatchEvent(new Event("change"));
2282
- // // await wait();
2283
- // // expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2284
- // // expect(scope.value).toBe(1.16);
2285
- // });
2286
- });
2287
- });
2288
-
2289
- describe("required", () => {
2290
- it("should be valid even if value is 0", () => {
2291
- const formElm = $compile(
2292
- '<form name="form"><input type="number" ng-model="value" name="alias" required /></form>',
2293
- )(scope);
2294
- inputElm = formElm.querySelector("input");
2295
-
2296
- inputElm.value = "0";
2297
- inputElm.dispatchEvent(new Event("change"));
2298
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2299
- expect(scope.value).toBe(0);
2300
- expect(scope.form.alias.$error.required).toBeFalsy();
2301
- });
2302
-
2303
- it("should be valid even if value 0 is set from model", async () => {
2304
- const formElm = $compile(
2305
- '<form name="form"><input type="number" ng-model="value" name="alias" required /></form>',
2306
- )(scope);
2307
- await wait();
2308
- inputElm = formElm.querySelector("input");
2309
- scope.$apply("value = 0");
2310
- await wait();
2311
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2312
- expect(inputElm.value).toBe("0");
2313
- expect(scope.form.alias.$error.required).toBeFalsy();
2314
- });
2315
-
2316
- it("should register required on non boolean elements", async () => {
2317
- const formElm = $compile(
2318
- '<form name="form"><div ng-model="value" name="alias" required></form>',
2319
- )(scope);
2320
- inputElm = formElm.querySelector("div");
2321
-
2322
- scope.$apply("value = ''");
2323
- await wait();
2324
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2325
- expect(scope.form.alias.$error.required).toBeTruthy();
2326
- });
2327
-
2328
- it("should not invalidate number if ng-required=false and viewValue has not been committed", () => {
2329
- inputElm = $compile(
2330
- '<input type="number" ng-model="value" name="alias" ng-required="required">',
2331
- )(scope);
2332
-
2333
- scope.$apply("required = false");
2334
-
2335
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2336
- });
2337
- });
2338
-
2339
- describe("ngRequired", () => {
2340
- describe("when the ngRequired expression initially evaluates to true", () => {
2341
- it("should be valid even if value is 0", () => {
2342
- const formElm = $compile(
2343
- '<form name="form"><input type="number" ng-model="value" name="numberInput" ng-required="true" /></form>',
2344
- )(scope);
2345
- inputElm = formElm.querySelector("input");
2346
-
2347
- inputElm.value = "0";
2348
- inputElm.dispatchEvent(new Event("change"));
2349
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2350
- expect(scope.value).toBe(0);
2351
- expect(scope.form.numberInput.$error.required).toBeFalsy();
2352
- });
2353
-
2354
- it("should be valid even if value 0 is set from model", async () => {
2355
- const formElm = $compile(
2356
- '<form name="form"><input type="number" ng-model="value" name="numberInput" ng-required="true" /></form>',
2357
- )(scope);
2358
- inputElm = formElm.querySelector("input");
2359
-
2360
- scope.$apply("value = 0");
2361
- await wait();
2362
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2363
- expect(inputElm.value).toBe("0");
2364
- expect(scope.form.numberInput.$error.required).toBeFalsy();
2365
- });
2366
-
2367
- it("should register required on non boolean elements", async () => {
2368
- const formElm = $compile(
2369
- '<form name="form"><div ng-model="value" name="numberInput" ng-required="true"></form>',
2370
- )(scope);
2371
- inputElm = formElm.querySelector("div");
2372
-
2373
- scope.$apply("value = ''");
2374
- await wait();
2375
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2376
- expect(scope.form.numberInput.$error.required).toBeTruthy();
2377
- });
2378
-
2379
- it("should change from invalid to valid when the value is empty and the ngRequired expression changes to false", async () => {
2380
- const formElm = $compile(
2381
- '<form name="form"><input type="number" ng-model="value" name="numberInput" ng-required="ngRequiredExpr" /></form>',
2382
- )(scope);
2383
- inputElm = formElm.querySelector("input");
2384
-
2385
- scope.$apply("ngRequiredExpr = true");
2386
- await wait();
2387
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2388
- expect(scope.value).toBeUndefined();
2389
- expect(scope.form.numberInput.$error.required).toBeTruthy();
2390
-
2391
- scope.$apply("ngRequiredExpr = false");
2392
- await wait();
2393
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2394
- expect(scope.value).toBeUndefined();
2395
- expect(scope.form.numberInput.$error.required).toBeFalsy();
2396
- });
2397
- });
2398
-
2399
- describe("when the ngRequired expression initially evaluates to false", () => {
2400
- it("should be valid even if value is empty", () => {
2401
- const formElm = $compile(
2402
- '<form name="form"><input type="number" ng-model="value" name="numberInput" ng-required="false" /></form>',
2403
- )(scope);
2404
- inputElm = formElm.querySelector("input");
2405
-
2406
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2407
- expect(scope.value).toBeUndefined();
2408
- expect(scope.form.numberInput.$error.required).toBeFalsy();
2409
- expect(scope.form.numberInput.$error.number).toBeFalsy();
2410
- });
2411
-
2412
- it("should be valid if value is non-empty", () => {
2413
- const formElm = $compile(
2414
- '<form name="form"><input type="number" ng-model="value" name="numberInput" ng-required="false" /></form>',
2415
- )(scope);
2416
- inputElm = formElm.querySelector("input");
2417
-
2418
- inputElm.value = "42";
2419
- inputElm.dispatchEvent(new Event("change"));
2420
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2421
- expect(scope.value).toBe(42);
2422
- expect(scope.form.numberInput.$error.required).toBeFalsy();
2423
- });
2424
-
2425
- it("should not register required on non boolean elements", async () => {
2426
- const formElm = $compile(
2427
- '<form name="form"><div ng-model="value" name="numberInput" ng-required="false"><form>',
2428
- )(scope);
2429
- inputElm = formElm.querySelector("div");
2430
-
2431
- scope.$apply("value = ''");
2432
- await wait();
2433
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2434
- expect(scope.form.numberInput.$error.required).toBeFalsy();
2435
- });
2436
-
2437
- it("should change from valid to invalid when the value is empty and the ngRequired expression changes to true", async () => {
2438
- const formElm = $compile(
2439
- '<form name="form"><input type="number" ng-model="value" name="numberInput" ng-required="ngRequiredExpr" /><form>',
2440
- )(scope);
2441
- inputElm = formElm.querySelector("input");
2442
-
2443
- scope.$apply("ngRequiredExpr = false");
2444
- await wait();
2445
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2446
- expect(scope.value).toBeUndefined();
2447
- expect(scope.form.numberInput.$error.required).toBeFalsy();
2448
-
2449
- scope.$apply("ngRequiredExpr = true");
2450
- await wait();
2451
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2452
- expect(scope.value).toBeUndefined();
2453
- expect(scope.form.numberInput.$error.required).toBeTruthy();
2454
- });
2455
- });
2456
- });
2457
-
2458
- describe("minlength", () => {
2459
- it("should invalidate values that are shorter than the given minlength", () => {
2460
- inputElm = $compile(
2461
- '<input type="number" ng-model="value" ng-minlength="3" />',
2462
- )(scope);
2463
-
2464
- inputElm.value = "12";
2465
- inputElm.dispatchEvent(new Event("change"));
2466
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2467
-
2468
- inputElm.value = "123";
2469
- inputElm.dispatchEvent(new Event("change"));
2470
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2471
- });
2472
-
2473
- it("should observe the standard minlength attribute and register it as a validator on the model", async () => {
2474
- const formElm = $compile(
2475
- '<form name="form"><input type="number" name="input" ng-model="value" minlength="{{ min }}" /></form>',
2476
- )(scope);
2477
- inputElm = formElm.querySelector("input");
2478
- scope.min = 10;
2479
- await wait();
2480
- inputElm.value = "12345";
2481
- inputElm.dispatchEvent(new Event("change"));
2482
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2483
- expect(scope.form.input.$error.minlength).toBe(true);
2484
-
2485
- scope.min = 5;
2486
- await wait();
2487
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2488
- expect(scope.form.input.$error.minlength).not.toBe(true);
2489
- });
2490
- });
2491
-
2492
- describe("maxlength", () => {
2493
- it("should invalidate values that are longer than the given maxlength", () => {
2494
- inputElm = $compile(
2495
- '<input type="number" ng-model="value" ng-maxlength="5" />',
2496
- )(scope);
2497
-
2498
- inputElm.value = "12345678";
2499
- inputElm.dispatchEvent(new Event("change"));
2500
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2501
-
2502
- inputElm.value = "123";
2503
- inputElm.dispatchEvent(new Event("change"));
2504
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2505
- });
2506
-
2507
- it("should observe the standard maxlength attribute and register it as a validator on the model", async () => {
2508
- const formElm = $compile(
2509
- '<form name="form"><input type="number" name="input" ng-model="value" maxlength="{{ max }}" /></form>',
2510
- )(scope);
2511
- inputElm = formElm.querySelector("input");
2512
- scope.$apply(() => {
2513
- scope.max = 1;
2514
- });
2515
- await wait();
2516
- inputElm.value = "12345";
2517
- inputElm.dispatchEvent(new Event("change"));
2518
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2519
- expect(scope.form.input.$error.maxlength).toBe(true);
2520
-
2521
- scope.$apply(() => {
2522
- scope.max = 6;
2523
- });
2524
- await wait();
2525
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2526
- expect(scope.form.input.$error.maxlength).not.toBe(true);
2527
- });
2528
- });
2529
- });
2530
-
2531
- describe("range", () => {
2532
- const rangeTestEl = '<input type="range">';
2533
- const supportsRange = rangeTestEl.type === "range";
2534
-
2535
- it("should render as 50 if null", async () => {
2536
- inputElm = $compile('<input type="range" ng-model="age" />')(scope);
2537
- inputElm.value = "25";
2538
- inputElm.dispatchEvent(new Event("change"));
2539
- await wait();
2540
- expect(scope.age).toBe(25);
2541
-
2542
- scope.$apply("age = null");
2543
- await wait();
2544
- expect(inputElm.value).toEqual("50");
2545
- });
2546
-
2547
- it("should set model to 50 when no value specified and default min/max", async () => {
2548
- inputElm = $compile('<input type="range" ng-model="age" />')(scope);
2549
- await wait();
2550
- expect(inputElm.value).toBe("50");
2551
-
2552
- scope.$apply("age = null");
2553
- await wait();
2554
- expect(scope.age).toBe(50);
2555
- });
2556
-
2557
- it("should parse non-number values to 50 when default min/max", async () => {
2558
- inputElm = $compile('<input type="range" ng-model="age" />')(scope);
2559
-
2560
- scope.$apply("age = 10");
2561
- await wait();
2562
- expect(inputElm.value).toBe("10");
2563
-
2564
- inputElm.value = "";
2565
- inputElm.dispatchEvent(new Event("change"));
2566
- await wait();
2567
- expect(scope.age).toBe(50);
2568
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2569
- });
2570
-
2571
- it("should parse the input value to a Number", () => {
2572
- inputElm = $compile('<input type="range" ng-model="age" />')(scope);
2573
-
2574
- inputElm.value = "75";
2575
- inputElm.dispatchEvent(new Event("change"));
2576
- expect(scope.age).toBe(75);
2577
- });
2578
-
2579
- it("should only invalidate the model if suffering from bad input when the data is parsed", () => {
2580
- scope.age = 60;
2581
-
2582
- inputElm = $compile('<input type="range" ng-model="age" />')(scope);
2583
-
2584
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2585
-
2586
- inputElm.value = "this-will-fail-because-of-the-badInput-flag";
2587
- inputElm.dispatchEvent(new Event("change"));
2588
-
2589
- expect(scope.age).toBe(50);
2590
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2591
- });
2592
-
2593
- it("should throw if the model value is not a number", async () => {
2594
- scope.value = "one";
2595
- inputElm = $compile('<input type="range" ng-model="value" />')(scope);
2596
- await wait();
2597
- expect(error[0]).toMatch("numfmt");
2598
- });
2599
-
2600
- describe("min", () => {
2601
- it("should initialize correctly with non-default model and min value", async () => {
2602
- scope.value = -3;
2603
- scope.min = -5;
2604
- const formElm = $compile(
2605
- '<form name="form"><input type="range" ng-model="value" name="alias" min="{{min}}" /></form>',
2606
- )(scope);
2607
- await wait();
2608
- inputElm = formElm.querySelector("input");
2609
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2610
- expect(inputElm.value).toBe("-3");
2611
- expect(scope.value).toBe(-3);
2612
- expect(scope.form.alias.$error.min).toBeFalsy();
2613
- });
2614
-
2615
- // Browsers that implement range will never allow you to set the value < min values
2616
- it("should adjust invalid input values", () => {
2617
- const formElm = $compile(
2618
- '<form name="form"><input type="range" ng-model="value" name="alias" min="10" /></form>',
2619
- )(scope);
2620
- inputElm = formElm.querySelector("input");
2621
-
2622
- inputElm.value = "5";
2623
- inputElm.dispatchEvent(new Event("change"));
2624
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2625
- expect(scope.value).toBe(10);
2626
- expect(scope.form.alias.$error.min).toBeFalsy();
2627
-
2628
- inputElm.value = "100";
2629
- inputElm.dispatchEvent(new Event("change"));
2630
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2631
- expect(scope.value).toBe(100);
2632
- expect(scope.form.alias.$error.min).toBeFalsy();
2633
- });
2634
-
2635
- it("should set the model to the min val if it is less than the min val", async () => {
2636
- scope.value = -10;
2637
- // Default min is 0
2638
- inputElm = $compile(
2639
- '<input type="range" ng-model="value" name="alias" min="{{min}}" />',
2640
- )(scope);
2641
- await wait();
2642
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2643
- expect(inputElm.value).toBe("0");
2644
- expect(scope.value).toBe(0);
2645
-
2646
- scope.$apply("value = 5; min = 10");
2647
- await wait();
2648
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2649
- expect(inputElm.value).toBe("10");
2650
- expect(scope.value).toBe(10);
2651
- });
2652
-
2653
- it("should adjust the element and model value when the min value changes on-the-fly", async () => {
2654
- scope.min = 10;
2655
- inputElm = $compile(
2656
- '<input type="range" ng-model="value" name="alias" min="{{min}}" />',
2657
- )(scope);
2658
- inputElm.value = "15";
2659
- inputElm.dispatchEvent(new Event("change"));
2660
- await wait();
2661
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2662
-
2663
- scope.min = 20;
2664
- await wait();
2665
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2666
- expect(scope.value).toBe(20);
2667
- expect(inputElm.value).toBe("20");
2668
-
2669
- scope.min = null;
2670
- await wait();
2671
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2672
- expect(scope.value).toBe(20);
2673
- expect(inputElm.value).toBe("20");
2674
-
2675
- scope.min = "15";
2676
- await wait();
2677
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2678
- expect(scope.value).toBe(20);
2679
- expect(inputElm.value).toBe("20");
2680
-
2681
- scope.min = "abc";
2682
- await wait();
2683
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2684
- expect(scope.value).toBe(20);
2685
- expect(inputElm.value).toBe("20");
2686
- });
2687
- });
2688
-
2689
- describe("max", () => {
2690
- // Browsers that implement range will never allow you to set the value > max value
2691
- it("should initialize correctly with non-default model and max value", async () => {
2692
- scope.value = 130;
2693
- scope.max = 150;
2694
- const formElm = $compile(
2695
- '<form name="form"><input type="range" ng-model="value" name="alias" max="{{max}}" /></form>',
2696
- )(scope);
2697
- inputElm = formElm.querySelector("input");
2698
- await wait();
2699
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2700
- expect(inputElm.value).toBe("130");
2701
- expect(scope.value).toBe(130);
2702
- expect(scope.form.alias.$error.max).toBeFalsy();
2703
- });
2704
-
2705
- it("should validate", () => {
2706
- const formElm = $compile(
2707
- '<form name="form"><input type="range" ng-model="value" name="alias" max="10" /></form>',
2708
- )(scope);
2709
- inputElm = formElm.querySelector("input");
2710
-
2711
- inputElm.value = "20";
2712
- inputElm.dispatchEvent(new Event("change"));
2713
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2714
- expect(scope.value).toBe(10);
2715
- expect(scope.form.alias.$error.max).toBeFalsy();
2716
-
2717
- inputElm.value = "0";
2718
- inputElm.dispatchEvent(new Event("change"));
2719
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2720
- expect(scope.value).toBe(0);
2721
- expect(scope.form.alias.$error.max).toBeFalsy();
2722
- });
2723
-
2724
- it("should set the model to the max val if it is greater than the max val", async () => {
2725
- scope.value = 110;
2726
- // Default max is 100
2727
- inputElm = $compile(
2728
- '<input type="range" ng-model="value" name="alias" max="{{max}}" />',
2729
- )(scope);
2730
- await wait();
2731
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2732
- expect(inputElm.value).toBe("100");
2733
- expect(scope.value).toBe(100);
2734
-
2735
- scope.$apply("value = 90; max = 10");
2736
- await wait();
2737
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2738
- expect(inputElm.value).toBe("10");
2739
- expect(scope.value).toBe(10);
2740
- });
2741
-
2742
- it("should adjust the element and model value if the max value changes on-the-fly", async () => {
2743
- scope.max = 10;
2744
- inputElm = $compile(
2745
- '<input type="range" ng-model="value" name="alias" max="{{max}}" />',
2746
- )(scope);
2747
- await wait();
2748
- inputElm.value = "5";
2749
- inputElm.dispatchEvent(new Event("change"));
2750
- await wait();
2751
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2752
-
2753
- scope.max = 0;
2754
- await wait();
2755
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2756
- expect(scope.value).toBe(0);
2757
- expect(inputElm.value).toBe("0");
2758
-
2759
- scope.max = null;
2760
- await wait();
2761
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2762
- expect(scope.value).toBe(0);
2763
- expect(inputElm.value).toBe("0");
2764
-
2765
- scope.max = "4";
2766
- await wait();
2767
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2768
- expect(scope.value).toBe(0);
2769
- expect(inputElm.value).toBe("0");
2770
-
2771
- scope.max = "abc";
2772
- await wait();
2773
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2774
- expect(scope.value).toBe(0);
2775
- expect(inputElm.value).toBe("0");
2776
- });
2777
- });
2778
-
2779
- describe("min and max", () => {
2780
- it("should set the correct initial value when min and max are specified", async () => {
2781
- scope.max = 80;
2782
- scope.min = 40;
2783
- inputElm = $compile(
2784
- '<input type="range" ng-model="value" name="alias" max="{{max}}" min="{{min}}" />',
2785
- )(scope);
2786
- await wait();
2787
- expect(inputElm.value).toBe("60");
2788
- expect(scope.value).toBe(60);
2789
- });
2790
-
2791
- it("should set element and model value to min if max is less than min", async () => {
2792
- scope.min = 40;
2793
- inputElm = $compile(
2794
- '<input type="range" ng-model="value" name="alias" max="{{max}}" min="{{min}}" />',
2795
- )(scope);
2796
- await wait();
2797
- expect(inputElm.value).toBe("70");
2798
- expect(scope.value).toBe(70);
2799
-
2800
- scope.max = 20;
2801
- await wait();
2802
- expect(inputElm.value).toBe("40");
2803
- expect(scope.value).toBe(40);
2804
- });
2805
- });
2806
-
2807
- describe("step", () => {
2808
- // Browsers that implement range will never allow you to set a value that doesn't match the step value
2809
- // However, currently only Firefox fully implements the spec when setting the value after the step value changes.
2810
- // Other browsers fail in various edge cases, which is why they are not tested here.
2811
-
2812
- it("should round the input value to the nearest step on user input", () => {
2813
- const formElm = $compile(
2814
- '<form name="form"><input type="range" ng-model="value" name="alias" step="5" /></form>',
2815
- )(scope);
2816
- inputElm = formElm.querySelector("input");
2817
-
2818
- inputElm.value = "5";
2819
- inputElm.dispatchEvent(new Event("change"));
2820
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2821
- expect(scope.value).toBe(5);
2822
- expect(scope.form.alias.$error.step).toBeFalsy();
2823
-
2824
- inputElm.value = "10";
2825
- inputElm.dispatchEvent(new Event("change"));
2826
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2827
- expect(scope.value).toBe(10);
2828
- expect(scope.form.alias.$error.step).toBeFalsy();
2829
-
2830
- inputElm.value = "9";
2831
- inputElm.dispatchEvent(new Event("change"));
2832
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2833
- expect(scope.value).toBe(10);
2834
- expect(scope.form.alias.$error.step).toBeFalsy();
2835
-
2836
- inputElm.value = "7";
2837
- inputElm.dispatchEvent(new Event("change"));
2838
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2839
- expect(scope.value).toBe(5);
2840
- expect(scope.form.alias.$error.step).toBeFalsy();
2841
-
2842
- inputElm.value = "7.5";
2843
- inputElm.dispatchEvent(new Event("change"));
2844
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2845
- expect(scope.value).toBe(10);
2846
- expect(scope.form.alias.$error.step).toBeFalsy();
2847
- });
2848
-
2849
- it("should round the input value to the nearest step when setting the model", async () => {
2850
- const formElm = $compile(
2851
- '<form name="form"><input type="range" ng-model="value" name="alias" step="5" /></form>',
2852
- )(scope);
2853
- inputElm = formElm.querySelector("input");
2854
-
2855
- scope.$apply("value = 10");
2856
- await wait();
2857
- expect(inputElm.value).toBe("10");
2858
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2859
- expect(scope.value).toBe(10);
2860
- expect(scope.form.alias.$error.step).toBeFalsy();
2861
-
2862
- scope.$apply("value = 5");
2863
- await wait();
2864
- expect(inputElm.value).toBe("5");
2865
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2866
- expect(scope.value).toBe(5);
2867
- expect(scope.form.alias.$error.step).toBeFalsy();
2868
-
2869
- scope.$apply("value = 7.5");
2870
- await wait();
2871
- expect(inputElm.value).toBe("10");
2872
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2873
- expect(scope.value).toBe(10);
2874
- expect(scope.form.alias.$error.step).toBeFalsy();
2875
-
2876
- scope.$apply("value = 7");
2877
- await wait();
2878
- expect(inputElm.value).toBe("5");
2879
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2880
- expect(scope.value).toBe(5);
2881
- expect(scope.form.alias.$error.step).toBeFalsy();
2882
-
2883
- scope.$apply("value = 9");
2884
- await wait();
2885
- expect(inputElm.value).toBe("10");
2886
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2887
- expect(scope.value).toBe(10);
2888
- expect(scope.form.alias.$error.step).toBeFalsy();
2889
- });
2890
- });
2891
- });
2892
-
2893
- describe("email", () => {
2894
- it("should validate e-mail", () => {
2895
- const formElm = $compile(
2896
- '<form name="form">' +
2897
- '<input type="email" ng-model="email" name="alias" />' +
2898
- "</form>",
2899
- )(scope);
2900
- inputElm = formElm.querySelector("input");
2901
-
2902
- const widget = scope.form.alias;
2903
- inputElm.value = "vojta@google.com";
2904
- inputElm.dispatchEvent(new Event("change"));
2905
-
2906
- expect(scope.email).toBe("vojta@google.com");
2907
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
2908
- expect(widget.$error.email).toBeFalsy();
2909
-
2910
- inputElm.value = "invalid@";
2911
- inputElm.dispatchEvent(new Event("change"));
2912
- expect(scope.email).toBeUndefined();
2913
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
2914
- expect(widget.$error.email).toBeTruthy();
2915
- });
2916
-
2917
- describe("EMAIL_REGEXP", () => {
2918
- it("should validate email", () => {
2919
- /* basic functionality */
2920
- expect(EMAIL_REGEXP.test("a@b.com")).toBe(true);
2921
- expect(EMAIL_REGEXP.test("a@b.museum")).toBe(true);
2922
- expect(EMAIL_REGEXP.test("a@B.c")).toBe(true);
2923
- /* domain label separation, hyphen-minus, syntax */
2924
- expect(EMAIL_REGEXP.test("a@b.c.")).toBe(false);
2925
- expect(EMAIL_REGEXP.test("a@.b.c")).toBe(false);
2926
- expect(EMAIL_REGEXP.test("a@-b.c")).toBe(false);
2927
- expect(EMAIL_REGEXP.test("a@b-.c")).toBe(false);
2928
- expect(EMAIL_REGEXP.test("a@b-c")).toBe(true);
2929
- expect(EMAIL_REGEXP.test("a@-")).toBe(false);
2930
- expect(EMAIL_REGEXP.test("a@.")).toBe(false);
2931
- expect(EMAIL_REGEXP.test("a@host_name")).toBe(false);
2932
- /* leading or sole digit */
2933
- expect(EMAIL_REGEXP.test("a@3b.c")).toBe(true);
2934
- expect(EMAIL_REGEXP.test("a@3")).toBe(true);
2935
- /* TLD eMail address */
2936
- expect(EMAIL_REGEXP.test("a@b")).toBe(true);
2937
- /* domain valid characters */
2938
- expect(
2939
- EMAIL_REGEXP.test(
2940
- "a@abcdefghijklmnopqrstuvwxyz-ABCDEFGHIJKLMNOPQRSTUVWXYZ.0123456789",
2941
- ),
2942
- ).toBe(true);
2943
- /* domain invalid characters */
2944
- expect(EMAIL_REGEXP.test("a@")).toBe(false);
2945
- expect(EMAIL_REGEXP.test("a@ ")).toBe(false);
2946
- expect(EMAIL_REGEXP.test("a@!")).toBe(false);
2947
- expect(EMAIL_REGEXP.test('a@"')).toBe(false);
2948
- expect(EMAIL_REGEXP.test("a@#")).toBe(false);
2949
- expect(EMAIL_REGEXP.test("a@$")).toBe(false);
2950
- expect(EMAIL_REGEXP.test("a@%")).toBe(false);
2951
- expect(EMAIL_REGEXP.test("a@&")).toBe(false);
2952
- expect(EMAIL_REGEXP.test("a@'")).toBe(false);
2953
- expect(EMAIL_REGEXP.test("a@(")).toBe(false);
2954
- expect(EMAIL_REGEXP.test("a@)")).toBe(false);
2955
- expect(EMAIL_REGEXP.test("a@*")).toBe(false);
2956
- expect(EMAIL_REGEXP.test("a@+")).toBe(false);
2957
- expect(EMAIL_REGEXP.test("a@,")).toBe(false);
2958
- expect(EMAIL_REGEXP.test("a@/")).toBe(false);
2959
- expect(EMAIL_REGEXP.test("a@:")).toBe(false);
2960
- expect(EMAIL_REGEXP.test("a@;")).toBe(false);
2961
- expect(EMAIL_REGEXP.test("a@<")).toBe(false);
2962
- expect(EMAIL_REGEXP.test("a@=")).toBe(false);
2963
- expect(EMAIL_REGEXP.test("a@>")).toBe(false);
2964
- expect(EMAIL_REGEXP.test("a@?")).toBe(false);
2965
- expect(EMAIL_REGEXP.test("a@@")).toBe(false);
2966
- expect(EMAIL_REGEXP.test("a@[")).toBe(false);
2967
- expect(EMAIL_REGEXP.test("a@\\")).toBe(false);
2968
- expect(EMAIL_REGEXP.test("a@]")).toBe(false);
2969
- expect(EMAIL_REGEXP.test("a@^")).toBe(false);
2970
- expect(EMAIL_REGEXP.test("a@_")).toBe(false);
2971
- expect(EMAIL_REGEXP.test("a@`")).toBe(false);
2972
- expect(EMAIL_REGEXP.test("a@{")).toBe(false);
2973
- expect(EMAIL_REGEXP.test("a@|")).toBe(false);
2974
- expect(EMAIL_REGEXP.test("a@}")).toBe(false);
2975
- expect(EMAIL_REGEXP.test("a@~")).toBe(false);
2976
- expect(EMAIL_REGEXP.test("a@İ")).toBe(false);
2977
- expect(EMAIL_REGEXP.test("a@ı")).toBe(false);
2978
- /* domain length, label and total */
2979
- expect(
2980
- EMAIL_REGEXP.test(
2981
- "a@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
2982
- ),
2983
- ).toBe(true);
2984
- expect(
2985
- EMAIL_REGEXP.test(
2986
- "a@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
2987
- ),
2988
- ).toBe(false);
2989
- expect(
2990
- EMAIL_REGEXP.test(
2991
- "a@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
2992
- ),
2993
- ).toBe(true);
2994
- expect(
2995
- EMAIL_REGEXP.test(
2996
- "a@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.x",
2997
- ),
2998
- ).toBe(true);
2999
- expect(
3000
- EMAIL_REGEXP.test(
3001
- "a@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xx",
3002
- ),
3003
- ).toBe(false);
3004
- expect(
3005
- EMAIL_REGEXP.test(
3006
- "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xx",
3007
- ),
3008
- ).toBe(true);
3009
- expect(
3010
- EMAIL_REGEXP.test(
3011
- "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xxx",
3012
- ),
3013
- ).toBe(false);
3014
-
3015
- /* local-part valid characters and dot-atom syntax */
3016
- expect(EMAIL_REGEXP.test("'@x")).toBe(true);
3017
- expect(
3018
- EMAIL_REGEXP.test(
3019
- "-!#$%&*+/0123456789=?ABCDEFGHIJKLMNOPQRSTUVWXYZ@x",
3020
- ),
3021
- ).toBe(true);
3022
- expect(EMAIL_REGEXP.test("^_`abcdefghijklmnopqrstuvwxyz{|}~@x")).toBe(
3023
- true,
3024
- );
3025
- expect(EMAIL_REGEXP.test(".@x")).toBe(false);
3026
- expect(EMAIL_REGEXP.test("'.@x")).toBe(false);
3027
- expect(EMAIL_REGEXP.test(".'@x")).toBe(false);
3028
- expect(EMAIL_REGEXP.test("'.'@x")).toBe(true);
3029
- /* local-part invalid characters */
3030
- expect(EMAIL_REGEXP.test("@x")).toBe(false);
3031
- expect(EMAIL_REGEXP.test(" @x")).toBe(false);
3032
- expect(EMAIL_REGEXP.test('"@x')).toBe(false);
3033
- expect(EMAIL_REGEXP.test("(@x")).toBe(false);
3034
- expect(EMAIL_REGEXP.test(")@x")).toBe(false);
3035
- expect(EMAIL_REGEXP.test(",@x")).toBe(false);
3036
- expect(EMAIL_REGEXP.test(":@x")).toBe(false);
3037
- expect(EMAIL_REGEXP.test(";@x")).toBe(false);
3038
- expect(EMAIL_REGEXP.test("<@x")).toBe(false);
3039
- expect(EMAIL_REGEXP.test(">@x")).toBe(false);
3040
- expect(EMAIL_REGEXP.test("@@x")).toBe(false);
3041
- expect(EMAIL_REGEXP.test("[@x")).toBe(false);
3042
- expect(EMAIL_REGEXP.test("\\@x")).toBe(false);
3043
- expect(EMAIL_REGEXP.test("]@x")).toBe(false);
3044
- expect(EMAIL_REGEXP.test("İ@x")).toBe(false);
3045
- expect(EMAIL_REGEXP.test("ı@x")).toBe(false);
3046
- /* local-part size limit */
3047
- expect(
3048
- EMAIL_REGEXP.test(
3049
- "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx@x",
3050
- ),
3051
- ).toBe(true);
3052
- expect(
3053
- EMAIL_REGEXP.test(
3054
- "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx@x",
3055
- ),
3056
- ).toBe(false);
3057
- /* content (local-part + ‘@’ + domain) is required */
3058
- expect(EMAIL_REGEXP.test("")).toBe(false);
3059
- expect(EMAIL_REGEXP.test("a")).toBe(false);
3060
- expect(EMAIL_REGEXP.test("aa")).toBe(false);
3061
- });
3062
- });
3063
- });
3064
-
3065
- describe("url", () => {
3066
- it("should validate url", () => {
3067
- const formElm = $compile(
3068
- '<form name="form">' +
3069
- '<input type="url" ng-model="url" name="alias" />',
3070
- +"</form>",
3071
- )(scope);
3072
- inputElm = formElm.querySelector("input");
3073
-
3074
- const widget = scope.form.alias;
3075
-
3076
- inputElm.value = "http://www.something.com";
3077
- inputElm.dispatchEvent(new Event("change"));
3078
- expect(scope.url).toBe("http://www.something.com");
3079
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
3080
- expect(widget.$error.url).toBeFalsy();
3081
-
3082
- inputElm.value = "invalid.com";
3083
- inputElm.dispatchEvent(new Event("change"));
3084
- expect(scope.url).toBeUndefined();
3085
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
3086
- expect(widget.$error.url).toBeTruthy();
3087
- });
3088
-
3089
- describe("URL_REGEXP", () => {
3090
- // See valid URLs in RFC3987 (http://tools.ietf.org/html/rfc3987)
3091
- // Note: We are being more lenient, because browsers are too.
3092
- const urls = [
3093
- ["scheme://hostname", true],
3094
- [
3095
- "scheme://username:password@host.name:7678/pa/t.h?q=u&e=r&y#fragment",
3096
- true,
3097
- ],
3098
-
3099
- // Validating `scheme`
3100
- ["://example.com", false],
3101
- ["0scheme://example.com", false],
3102
- [".scheme://example.com", false],
3103
- ["+scheme://example.com", false],
3104
- ["-scheme://example.com", false],
3105
- ["_scheme://example.com", false],
3106
- ["scheme0://example.com", true],
3107
- ["scheme.://example.com", true],
3108
- ["scheme+://example.com", true],
3109
- ["scheme-://example.com", true],
3110
- ["scheme_://example.com", false],
3111
-
3112
- // Validating `:` and `/` after `scheme`
3113
- ["scheme//example.com", false],
3114
- ["scheme:example.com", true],
3115
- ["scheme:/example.com", true],
3116
- ["scheme:///example.com", true],
3117
-
3118
- // Validating `username` and `password`
3119
- ["scheme://@example.com", true],
3120
- ["scheme://username@example.com", true],
3121
- ["scheme://u0s.e+r-n_a~m!e@example.com", true],
3122
- ["scheme://u#s$e%r^n&a*m;e@example.com", true],
3123
- ["scheme://:password@example.com", true],
3124
- ["scheme://username:password@example.com", true],
3125
- ["scheme://username:pass:word@example.com", true],
3126
- ["scheme://username:p0a.s+s-w_o~r!d@example.com", true],
3127
- ["scheme://username:p#a$s%s^w&o*r;d@example.com", true],
3128
-
3129
- // Validating `hostname`
3130
- ["scheme:", false], // Chrome, FF: true
3131
- ["scheme://", false], // Chrome, FF: true
3132
- ["scheme:// example.com:", false], // Chrome, FF: true
3133
- ["scheme://example com:", false], // Chrome, FF: true
3134
- ["scheme://:", false], // Chrome, FF: true
3135
- ["scheme://?", false], // Chrome, FF: true
3136
- ["scheme://#", false], // Chrome, FF: true
3137
- ["scheme://username:password@:", false], // Chrome, FF: true
3138
- ["scheme://username:password@/", false], // Chrome, FF: true
3139
- ["scheme://username:password@?", false], // Chrome, FF: true
3140
- ["scheme://username:password@#", false], // Chrome, FF: true
3141
- ["scheme://host.name", true],
3142
- ["scheme://123.456.789.10", true],
3143
- ["scheme://[1234:0000:0000:5678:9abc:0000:0000:def]", true],
3144
- ["scheme://[1234:0000:0000:5678:9abc:0000:0000:def]:7678", true],
3145
- ["scheme://[1234:0:0:5678:9abc:0:0:def]", true],
3146
- ["scheme://[1234::5678:9abc::def]", true],
3147
- ["scheme://~`!@$%^&*-_=+|\\;'\",.()[]{}<>", true],
3148
-
3149
- // Validating `port`
3150
- ["scheme://example.com/no-port", true],
3151
- ["scheme://example.com:7678", true],
3152
- ["scheme://example.com:76T8", false], // Chrome, FF: true
3153
- ["scheme://example.com:port", false], // Chrome, FF: true
3154
-
3155
- // Validating `path`
3156
- ["scheme://example.com/", true],
3157
- ["scheme://example.com/path", true],
3158
- ["scheme://example.com/path/~`!@$%^&*-_=+|\\;:'\",./()[]{}<>", true],
3159
-
3160
- // Validating `query`
3161
- ["scheme://example.com?query", true],
3162
- ["scheme://example.com/?query", true],
3163
- ["scheme://example.com/path?query", true],
3164
- ["scheme://example.com/path?~`!@$%^&*-_=+|\\;:'\",.?/()[]{}<>", true],
3165
-
3166
- // Validating `fragment`
3167
- ["scheme://example.com#fragment", true],
3168
- ["scheme://example.com/#fragment", true],
3169
- ["scheme://example.com/path#fragment", true],
3170
- ["scheme://example.com/path/#fragment", true],
3171
- ["scheme://example.com/path?query#fragment", true],
3172
- [
3173
- "scheme://example.com/path?query#~`!@#$%^&*-_=+|\\;:'\",.?/()[]{}<>",
3174
- true,
3175
- ],
3176
-
3177
- // Validating miscellaneous
3178
- ["scheme://☺.✪.⌘.➡/䨹", true],
3179
- ["scheme://مثال.إختبار", true],
3180
- ["scheme://例子.测试", true],
3181
- ["scheme://उदाहरण.परीक्षा", true],
3182
-
3183
- // Legacy tests
3184
- ["http://server:123/path", true],
3185
- ["https://server:123/path", true],
3186
- ["file:///home/user", true],
3187
- ["mailto:user@example.com?subject=Foo", true],
3188
- ["r2-d2.c3-p0://localhost/foo", true],
3189
- ["abc:/foo", true],
3190
- ["http://example.com/path;path", true],
3191
- ["http://example.com/[]$'()*,~)", true],
3192
- ["http:", false], // FF: true
3193
- ["a@B.c", false],
3194
- ["a_B.c", false],
3195
- ["0scheme://example.com", false],
3196
- ["http://example.com:9999/``", true],
3197
- ].forEach((item) => {
3198
- it("should validate url: $prop", () => {
3199
- const url = item[0];
3200
- const valid = item[1];
3201
-
3202
- expect(URL_REGEXP.test(url)).toBe(valid);
3203
- });
3204
- });
3205
- });
3206
- });
3207
-
3208
- describe("radio", () => {
3209
- ["click", "change"].forEach((event) => {
3210
- it("should update the model on $prop event", async () => {
3211
- let res = $compile(
3212
- '<div><input type="radio" ng-model="color" value="white" />' +
3213
- '<input type="radio" ng-model="color" value="red" />' +
3214
- '<input type="radio" ng-model="color" value="blue" /></div>',
3215
- )(scope);
3216
- await wait();
3217
- inputElm = res.querySelectorAll("input");
3218
-
3219
- scope.$apply("color = 'white'");
3220
- await wait();
3221
- expect(inputElm[0].checked).toBe(true);
3222
- expect(inputElm[1].checked).toBe(false);
3223
- expect(inputElm[2].checked).toBe(false);
3224
-
3225
- scope.$apply("color = 'red'");
3226
- await wait();
3227
- expect(inputElm[0].checked).toBe(false);
3228
- expect(inputElm[1].checked).toBe(true);
3229
- expect(inputElm[2].checked).toBe(false);
3230
-
3231
- if (event === "change") inputElm[2].checked = true;
3232
- if (event === "click") inputElm[2].click();
3233
- inputElm[2].dispatchEvent(new Event("change"));
3234
- await wait();
3235
- expect(scope.color).toBe("blue");
3236
- });
3237
- });
3238
-
3239
- it("should treat the value as a string when evaluating checked-ness", async () => {
3240
- inputElm = $compile(
3241
- '<input type="radio" ng-model="model" value="0" />',
3242
- )(scope);
3243
-
3244
- scope.$apply("model = '0'");
3245
- await wait();
3246
- expect(inputElm.checked).toBe(true);
3247
-
3248
- scope.$apply("model = 0");
3249
- await wait();
3250
- expect(inputElm.checked).toBe(false);
3251
- });
3252
-
3253
- it("should allow {{expr}} as value", async () => {
3254
- scope.some = 11;
3255
- let res = $compile(
3256
- '<div><input type="radio" ng-model="value" value="{{some}}" />' +
3257
- '<input type="radio" ng-model="value" value="{{other}}" /></div>',
3258
- )(scope);
3259
- inputElm = res.querySelectorAll("input");
3260
- await wait();
3261
- scope.$apply(() => {
3262
- scope.value = "blue";
3263
- scope.some = "blue";
3264
- scope.other = "red";
3265
- });
3266
- await wait();
3267
- expect(inputElm[0].checked).toBe(true);
3268
- expect(inputElm[1].checked).toBe(false);
3269
-
3270
- inputElm[1].click();
3271
- inputElm[1].dispatchEvent(new Event("change"));
3272
- await wait();
3273
- expect(scope.value).toBe("red");
3274
-
3275
- scope.$apply("other = 'non-red'");
3276
- await wait();
3277
- expect(inputElm[0].checked).toBe(false);
3278
- expect(inputElm[1].checked).toBe(false);
3279
- });
3280
-
3281
- it("should allow the use of ngTrim", async () => {
3282
- scope.some = 11;
3283
- let res = $compile(
3284
- '<div><input type="radio" ng-model="value" value="opt1" />' +
3285
- '<input type="radio" ng-model="value" value=" opt2 " />' +
3286
- '<input type="radio" ng-model="value" ng-trim="false" value=" opt3 " />' +
3287
- '<input type="radio" ng-model="value" ng-trim="false" value="{{some}}" />' +
3288
- '<input type="radio" ng-model="value" ng-trim="false" value=" {{some}} " /></div>',
3289
- )(scope);
3290
- inputElm = res.querySelectorAll("input");
3291
- scope.$apply(() => {
3292
- scope.value = "blue";
3293
- scope.some = "blue";
3294
- });
3295
- await wait();
3296
- expect(inputElm[0].checked).toBe(false);
3297
- expect(inputElm[1].checked).toBe(false);
3298
- expect(inputElm[2].checked).toBe(false);
3299
- expect(inputElm[3].checked).toBe(true);
3300
- expect(inputElm[4].checked).toBe(false);
3301
-
3302
- inputElm[1].click();
3303
- inputElm[1].dispatchEvent(new Event("change"));
3304
- await wait();
3305
- expect(scope.value).toBe("opt2");
3306
- inputElm[2].click();
3307
- inputElm[2].dispatchEvent(new Event("change"));
3308
- await wait();
3309
- expect(scope.value).toBe(" opt3 ");
3310
- inputElm[3].click();
3311
- inputElm[3].dispatchEvent(new Event("change"));
3312
- await wait();
3313
- expect(scope.value).toBe("blue");
3314
- inputElm[4].click();
3315
- inputElm[4].dispatchEvent(new Event("change"));
3316
- await wait();
3317
- expect(scope.value).toBe(" blue ");
3318
-
3319
- scope.$apply("value = ' opt2 '");
3320
- await wait();
3321
- expect(inputElm[1].checked).toBe(false);
3322
- scope.$apply("value = 'opt2'");
3323
- await wait();
3324
- expect(inputElm[1].checked).toBe(true);
3325
- scope.$apply("value = ' opt3 '");
3326
- await wait();
3327
- expect(inputElm[2].checked).toBe(true);
3328
- scope.$apply("value = 'opt3'");
3329
- await wait();
3330
- expect(inputElm[2].checked).toBe(false);
3331
-
3332
- scope.$apply("value = 'blue'");
3333
- await wait();
3334
- expect(inputElm[3].checked).toBe(true);
3335
- expect(inputElm[4].checked).toBe(false);
3336
- scope.$apply("value = ' blue '");
3337
- await wait();
3338
- expect(inputElm[3].checked).toBe(false);
3339
- expect(inputElm[4].checked).toBe(true);
3340
- });
3341
- });
3342
-
3343
- describe("checkbox", () => {
3344
- it("should ignore checkbox without ngModel directive", async () => {
3345
- inputElm = $compile(
3346
- '<input type="checkbox" name="whatever" required />',
3347
- )(scope);
3348
-
3349
- inputElm.value = "";
3350
- inputElm.dispatchEvent(new Event("change"));
3351
- await wait();
3352
- expect(inputElm.classList.contains("ng-valid")).toBe(false);
3353
- expect(inputElm.classList.contains("ng-invalid")).toBe(false);
3354
- expect(inputElm.classList.contains("ng-pristine")).toBe(false);
3355
- expect(inputElm.classList.contains("ng-dirty")).toBe(false);
3356
- });
3357
-
3358
- ["click", "change"].forEach((event) => {
3359
- it("should update the model on $prop event", async () => {
3360
- inputElm = $compile('<input type="checkbox" ng-model="checkbox" />')(
3361
- scope,
3362
- );
3363
-
3364
- expect(inputElm.checked).toBe(false);
3365
-
3366
- scope.$apply("checkbox = true");
3367
- await wait();
3368
- expect(inputElm.checked).toBe(true);
3369
-
3370
- scope.$apply("checkbox = false");
3371
- await wait();
3372
- expect(inputElm.checked).toBe(false);
3373
-
3374
- if (event === "change") inputElm.checked = true;
3375
- if (event === "click") inputElm.click();
3376
- inputElm.dispatchEvent(new Event("change"));
3377
- await wait();
3378
- expect(scope.checkbox).toBe(true);
3379
- });
3380
- });
3381
-
3382
- it("should format booleans", async () => {
3383
- inputElm = $compile('<input type="checkbox" ng-model="name" />')(scope);
3384
-
3385
- scope.$apply("name = false");
3386
- await wait();
3387
- expect(inputElm.checked).toBe(false);
3388
-
3389
- scope.$apply("name = true");
3390
- await wait();
3391
- expect(inputElm.checked).toBe(true);
3392
- });
3393
-
3394
- it('should support type="checkbox" with non-standard capitalization', async () => {
3395
- inputElm = $compile('<input type="checkBox" ng-model="checkbox" />')(
3396
- scope,
3397
- );
3398
- await wait();
3399
- inputElm.click();
3400
- inputElm.dispatchEvent(new Event("change"));
3401
- await wait();
3402
- expect(scope.checkbox).toBe(true);
3403
-
3404
- inputElm.click();
3405
- inputElm.dispatchEvent(new Event("change"));
3406
- await wait();
3407
- expect(scope.checkbox).toBe(false);
3408
- });
3409
-
3410
- it("should allow custom enumeration", async () => {
3411
- inputElm = $compile(
3412
- '<input type="checkbox" ng-model="name" ng-true-value="\'y\'" ' +
3413
- "ng-false-value=\"'n'\">",
3414
- )(scope);
3415
-
3416
- scope.$apply("name = 'y'");
3417
- await wait();
3418
- expect(inputElm.checked).toBe(true);
3419
-
3420
- scope.$apply("name = 'n'");
3421
- await wait();
3422
- expect(inputElm.checked).toBe(false);
3423
-
3424
- scope.$apply("name = 'something else'");
3425
- await wait();
3426
- expect(inputElm.checked).toBe(false);
3427
-
3428
- inputElm.click();
3429
- inputElm.dispatchEvent(new Event("change"));
3430
- await wait();
3431
- expect(scope.name).toEqual("y");
3432
-
3433
- inputElm.click();
3434
- inputElm.dispatchEvent(new Event("change"));
3435
- await wait();
3436
- expect(scope.name).toEqual("n");
3437
- });
3438
-
3439
- it("should throw if ngTrueValue is present and not a constant expression", async () => {
3440
- inputElm = $compile(
3441
- '<input type="checkbox" ng-model="value" ng-true-value="yes" />',
3442
- )(scope);
3443
- await wait();
3444
- expect(error[0]).toMatch("constexpr");
3445
- });
3446
-
3447
- it("should throw if ngFalseValue is present and not a constant expression", async () => {
3448
- inputElm = $compile(
3449
- '<input type="checkbox" ng-model="value" ng-false-value="no" />',
3450
- )(scope);
3451
- await wait();
3452
- expect(error[0]).toMatch("constexpr");
3453
- });
3454
-
3455
- it("should not throw if ngTrueValue or ngFalseValue are not present", async () => {
3456
- inputElm = $compile('<input type="checkbox" ng-model="value" />')(
3457
- scope,
3458
- );
3459
- await wait();
3460
- expect(error.length).toBe(0);
3461
- });
3462
-
3463
- it("should be required if false", async () => {
3464
- inputElm = $compile(
3465
- '<input type="checkbox" ng-model="value" required />',
3466
- )(scope);
3467
-
3468
- inputElm.click();
3469
- inputElm.dispatchEvent(new Event("change"));
3470
- await wait();
3471
- expect(inputElm.checked).toBe(true);
3472
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
3473
-
3474
- inputElm.click();
3475
- inputElm.dispatchEvent(new Event("change"));
3476
- await wait();
3477
- expect(inputElm.checked).toBe(false);
3478
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
3479
- });
3480
-
3481
- it('should pass validation for "required" when trueValue is a string', async () => {
3482
- const formElm = $compile(
3483
- '<form name="form">' +
3484
- '<input type="checkbox" required name="cb" ng-model="value" ng-true-value="\'yes\'" />' +
3485
- "</form>",
3486
- )(scope);
3487
- inputElm = formElm.querySelector("input");
3488
- await wait();
3489
- expect(inputElm.classList.contains("ng-invalid")).toBeTrue();
3490
- expect(scope.form.cb.$error.required).toBe(true);
3491
-
3492
- inputElm.click();
3493
- inputElm.dispatchEvent(new Event("change"));
3494
- await wait();
3495
- expect(inputElm.checked).toBe(true);
3496
- expect(inputElm.classList.contains("ng-valid")).toBeTrue();
3497
- expect(scope.form.cb.$error.required).toBeUndefined();
3498
- });
3499
- });
3500
-
3501
- describe("textarea", () => {
3502
- it("should process textarea", async () => {
3503
- inputElm = $compile('<textarea ng-model="name"></textarea>')(scope);
3504
-
3505
- scope.$apply("name = 'Adam'");
3506
- await wait();
3507
- expect(inputElm.value).toEqual("Adam");
3508
-
3509
- inputElm.value = "Shyam";
3510
- inputElm.dispatchEvent(new Event("change"));
3511
- await wait();
3512
- expect(scope.name).toEqual("Shyam");
3513
-
3514
- inputElm.value = "Kai";
3515
- inputElm.dispatchEvent(new Event("change"));
3516
- await wait();
3517
- expect(scope.name).toEqual("Kai");
3518
- });
3519
-
3520
- it("should ignore textarea without ngModel directive", () => {
3521
- inputElm = $compile('<textarea name="whatever" required></textarea>')(
3522
- scope,
3523
- );
3524
-
3525
- inputElm.value = "";
3526
- inputElm.dispatchEvent(new Event("change"));
3527
- expect(inputElm.classList.contains("ng-valid")).toBe(false);
3528
- expect(inputElm.classList.contains("ng-invalid")).toBe(false);
3529
- expect(inputElm.classList.contains("ng-pristine")).toBe(false);
3530
- expect(inputElm.classList.contains("ng-dirty")).toBe(false);
3531
- });
3532
- });
3533
-
3534
- describe("ngValue", () => {
3535
- it('should update the dom "value" property and attribute', async () => {
3536
- inputElm = $compile('<input type="submit" ng-value="value">')(scope);
3537
-
3538
- scope.$apply("value = 'something'");
3539
- await wait();
3540
- expect(inputElm.value).toBe("something");
3541
- expect(inputElm.getAttribute("value")).toBe("something");
3542
- });
3543
-
3544
- it('should clear the "dom" value property and attribute when the value is undefined', async () => {
3545
- inputElm = $compile('<input type="text" ng-value="value">')(scope);
3546
-
3547
- scope.$apply('value = "something"');
3548
- await wait();
3549
- expect(inputElm.value).toBe("something");
3550
- expect(inputElm.getAttribute("value")).toBe("something");
3551
-
3552
- scope.$apply(() => {
3553
- delete scope.value;
3554
- });
3555
- await wait();
3556
- expect(inputElm.value).toBe("");
3557
- // Support: IE 9-11, Edge
3558
- // In IE it is not possible to remove the `value` attribute from an input element.
3559
- expect(inputElm.getAttribute("value")).toBeNull();
3560
- // } else {
3561
- // // Support: IE 9-11, Edge
3562
- // // This will fail if the Edge bug gets fixed
3563
- // expect(inputElm.getAttribute("value")).toBe("something");
3564
- // }
3565
- });
3566
-
3567
- // they(
3568
- // 'should update the $prop "value" property and attribute after the bound expression changes',
3569
- // {
3570
- // input: '<input type="text" ng-value="value">',
3571
- // textarea: '<textarea ng-value="value"></textarea>',
3572
- // },
3573
- // (tmpl) => {
3574
- // const element = $compile(tmpl)(scope);
3575
-
3576
- // helper.changeInputValueTo("newValue");
3577
- // expect(element.value).toBe("newValue");
3578
- // expect(element.getAttribute("value")).toBeNull();
3579
-
3580
- // scope.$apply(() => {
3581
- // scope.value = "anotherValue";
3582
- // });
3583
- // expect(element.value).toBe("anotherValue");
3584
- // expect(element.getAttribute("value")).toBe("anotherValue");
3585
- // },
3586
- // );
3587
-
3588
- it("should evaluate and set constant expressions", async () => {
3589
- let res = $compile(
3590
- '<div><input type="radio" ng-model="selected" ng-value="true">' +
3591
- '<input type="radio" ng-model="selected" ng-value="false">' +
3592
- '<input type="radio" ng-model="selected" ng-value="1"></div>',
3593
- )(scope);
3594
- inputElm = res.querySelectorAll("input");
3595
- inputElm[0].click();
3596
- inputElm[0].dispatchEvent(new Event("change"));
3597
- await wait();
3598
- expect(scope.selected).toBe(true);
3599
-
3600
- inputElm[1].click();
3601
- inputElm[1].dispatchEvent(new Event("change"));
3602
- await wait();
3603
- expect(scope.selected).toBe(false);
3604
-
3605
- inputElm[2].click();
3606
- inputElm[2].dispatchEvent(new Event("change"));
3607
- await wait();
3608
- expect(scope.selected).toBe(1);
3609
- });
3610
-
3611
- it("should use strict comparison between model and value", async () => {
3612
- scope.selected = false;
3613
- const res = $compile(
3614
- '<div><input type="radio" ng-model="selected" ng-value="false">' +
3615
- '<input type="radio" ng-model="selected" ng-value="\'\'">' +
3616
- '<input type="radio" ng-model="selected" ng-value="0"></div>',
3617
- )(scope);
3618
- inputElm = res.querySelectorAll("input");
3619
- await wait();
3620
- expect(inputElm[0].checked).toBe(true);
3621
- expect(inputElm[1].checked).toBe(false);
3622
- expect(inputElm[2].checked).toBe(false);
3623
- });
3624
-
3625
- it("should watch the expression", async () => {
3626
- inputElm = $compile(
3627
- '<input type="radio" ng-model="selected" ng-value="value">',
3628
- )(scope);
3629
- expect(inputElm.checked).toBe(false);
3630
- await wait();
3631
- scope.value = { some: "object" };
3632
- scope.selected = scope.value;
3633
- await wait();
3634
- expect(inputElm.checked).toBe(true);
3635
-
3636
- // inputElm = $compile(
3637
- // '<input type="radio" ng-model="selected" ng-value="value">',
3638
- // )(scope);
3639
- // expect(inputElm.checked).toBe(false);
3640
- // await wait();
3641
-
3642
- // inputElm.click();
3643
- // inputElm.dispatchEvent(new Event("change"));
3644
- // await wait();
3645
- // expect(scope.selected).toEqual(scope.value);
3646
- });
3647
-
3648
- it("should work inside ngRepeat", async () => {
3649
- inputElm = $compile(
3650
- '<div><input type="radio" ng-repeat="i in items" ng-model="selected" ng-value="i.id"></div>',
3651
- )(scope);
3652
-
3653
- scope.$apply(() => {
3654
- scope.items = [{ id: 1 }, { id: 2 }];
3655
- scope.selected = 1;
3656
- });
3657
- await wait();
3658
-
3659
- expect(inputElm.children[0].checked).toBe(true);
3660
- expect(inputElm.children[1].checked).toBe(false);
3661
- // TODO INVESIGATE
3662
- // inputElm.children[1].click();
3663
- // inputElm.children[1].dispatchEvent(new Event("change"));
3664
- // await wait(100);
3665
- // expect(scope.selected).toBe(2);
3666
- });
3667
- });
3668
-
3669
- describe("password", () => {
3670
- // Under no circumstances should input[type=password] trim inputs
3671
- it("should not trim if ngTrim is unspecified", () => {
3672
- inputElm = $compile('<input type="password" ng-model="password">')(
3673
- scope,
3674
- );
3675
-
3676
- inputElm.value = " - - untrimmed - - ";
3677
- inputElm.dispatchEvent(new Event("change"));
3678
- expect(scope.password.length).toBe(" - - untrimmed - - ".length);
3679
- });
3680
-
3681
- it("should not trim if ngTrim !== false", () => {
3682
- inputElm = $compile(
3683
- '<input type="password" ng-model="password" ng-trim="true">',
3684
- )(scope);
3685
- inputElm.value = " - - untrimmed - - ";
3686
- inputElm.dispatchEvent(new Event("change"));
3687
- expect(scope.password.length).toBe(" - - untrimmed - - ".length);
3688
- });
3689
-
3690
- it("should not trim if ngTrim === false", () => {
3691
- inputElm = $compile(
3692
- '<input type="password" ng-model="password" ng-trim="false">',
3693
- )(scope);
3694
- inputElm.value = " - - untrimmed - - ";
3695
- inputElm.dispatchEvent(new Event("change"));
3696
- expect(scope.password.length).toBe(" - - untrimmed - - ".length);
3697
- });
3698
- });
3699
- });
3700
- });