Compare commits

..

157 Commits

Author SHA1 Message Date
dce1c7cf58 build: fix comment formatting to make closure happy 2018-10-25 16:38:52 -07:00
2c7386c961 feat(ivy): support injecting the injector (#26699)
PR Close #26699
2018-10-25 18:47:56 -04:00
d5cbcef0ea fix(core): ignore comment nodes under unsafe elements (#25879)
Comment nodes that are child nodes of unsafe elements are identified as text nodes. This results in the comment node being returned as an encoded string.
Add a check to ignore such comment nodes.

PR Close #25879
2018-10-25 11:20:19 -07:00
b0476f308b feat(ivy): support providers and viewProviders (#25803)
PR Close #25803
2018-10-25 12:58:40 -04:00
9dc52d9d04 feat(ivy): expose a series of debug console tools (#26705)
PR Close #26705
2018-10-24 20:30:51 -04:00
297dc2bc02 fix(ivy): ensure ngClass works with [class] bindings (#26559)
PR Close #26559
2018-10-24 20:27:12 -04:00
0cc9842bf6 test(upgrade): make e2e tests for upgrade docs examples less flaky (#26726)
PR Close #26726
2018-10-24 19:49:14 -04:00
54ea10288e test(elements): make e2e tests for elements docs examples even less flaky (#26726)
PR Close #26726
2018-10-24 19:49:14 -04:00
1880c9531f ci: only publish builds if relevant aio jobs pass (#26722)
Some of the `aio`-/`docs`-related jobs rely on the locally built Angular
packages. When these jobs fail, it could mean that there is an issue
with the Angular packages (e.g. an unintentional breaking change).

This commit ensures that the `publish_artifacts` job is not run, unless
those `aio`-/`docs`-related jobs pass.

(The `test_aio_tools` job also uses the locally built Angular packages,
but it does not exercise them in a meaningful way to be worth making it
a prerequisite for `publish_artifacts`.)

PR Close #26722
2018-10-24 19:48:41 -04:00
13a803d4f7 build(docs-infra): fix parameter type rendering (#26688)
Closes #24355

PR Close #26688
2018-10-24 19:48:10 -04:00
f6c2db818e fix(ivy): ensure styling pipes are allocated before used in bindings (#26593)
PR Close #26593
2018-10-24 18:42:59 -04:00
67789f10ef release: cut the v7.1.0-beta.0 release 2018-10-24 14:47:20 -07:00
b83f1300bd docs: release notes for the v7.0.1 release 2018-10-24 14:42:37 -07:00
6e16a17015 ci(docs-infra): fix deployment script (#26731)
PR Close #26731
2018-10-24 13:20:53 -07:00
d744dd70e0 build: downgrade yarn.lock file to bazel generated version 2018-10-24 12:58:02 -07:00
4e91ead40b style: format (#26708)
PR Close #26708
2018-10-24 12:13:46 -07:00
7f39f37003 fix(bazel): support --nolegacy_external_runfiles in protractor rule (#26708)
PR Close #26708
2018-10-24 12:13:46 -07:00
bf9ab53f12 build(ivy): fix typo in build file 2018-10-24 10:07:49 -07:00
d99f661af7 build(ivy): properly tag the js_expected_symbol_test rules
Previously the rules were tagged ivy-only, but missing the ivy-aot tag
which would cause them to run under CI.
2018-10-24 10:04:06 -07:00
5d58a31d86 fix(ivy): rename broken reflect_metadata switch file
This file was missed during the rename of the --define=compile
flag value from 'local' to 'aot. It's referenced as
reflect_metadata_${compile}.
2018-10-24 09:53:10 -07:00
07b89902d5 ci: don't publish ivy build artifacts on a non-master branch 2018-10-23 15:31:55 -07:00
ce6948fc1b ci(docs-infra): remove jobs from Travis config (#26377)
PR Close #26377
2018-10-23 14:35:38 -07:00
38d626a3fa ci(docs-infra): move deployment to CircleCI (#26377)
PR Close #26377
2018-10-23 14:35:38 -07:00
9b8a244a15 ci: fix payload-size.sh (#26377)
PR Close #26377
2018-10-23 14:35:38 -07:00
1bbf28ad19 ci(docs-infra): add jobs to CircleCI config (#26377)
PR Close #26377
2018-10-23 14:35:37 -07:00
3b24e0edb6 build: use CI-provider independent variable names (#26377)
PR Close #26377
2018-10-23 14:35:37 -07:00
b647608c96 test(elements): make e2e tests for elements docs examples less flaky (#26377)
PR Close #26377
2018-10-23 14:35:37 -07:00
31c462ae3f test(animations): make e2e tests for animations docs examples less flaky (#26377)
PR Close #26377
2018-10-23 14:35:37 -07:00
da39fd70d2 test(docs-infra): improve logging output in test-pwa-score[-localhost] (#26377)
PR Close #26377
2018-10-23 14:35:37 -07:00
ee0b857172 build: rename the ivy compile mode 'local' to 'aot' (#26686)
PR Close #26686
2018-10-23 14:14:49 -07:00
e0d6782d26 build: add test-ivy-jit, test-fixme-ivy-jit, test-ivy-aot and test-fixme-ivy-aot yarn scripts (#26686)
PR Close #26686
2018-10-23 14:14:49 -07:00
2f9e957523 ci: re-encrypt .circleci/github_token (#26698)
PR Close #26698
2018-10-23 13:31:48 -07:00
38dbae9ca0 build: fix BUILD file formatting 2018-10-23 12:29:26 -07:00
5a3077f46c ci: fix broken master branch due to conflicting merges (#26697)
PR Close #26697
2018-10-23 12:28:35 -07:00
d0cc019c1a ci: re-encrypt github publish token with recent ngcontainer (#26692)
Something about the docker image changed such that the encrypted value is different

PR Close #26692
2018-10-23 12:00:20 -07:00
26e8032bd0 docs: update npm packages to be accurate for v7 (#26422)
PR Close #26422
2018-10-23 08:58:43 -07:00
84af7b065d docs(service-worker): Specify format of datagroups.cacheConfig.timeout (#26469)
Fixes #26454

PR Close #26469
2018-10-23 08:58:17 -07:00
83dc3c0ee0 build: add config_env_vars = ["compile"] to ngc-wrapped (#26471)
PR Close #26471
2018-10-23 08:57:42 -07:00
5952775a03 ci: build-packages-dist.sh should publish only regular and --compile=local packages (#26471)
We don't need to publish JIT compiled packages as this is not useful for real-world use-cases.

PR Close #26471
2018-10-23 08:57:42 -07:00
57531737e5 build: add source-map-support to various rules within our repo (#26471)
This removes an verbose warning and adds source-mapping support to our build/ci.

Related issue: https://github.com/bazelbuild/rules_nodejs/issues/389

PR Close #26471
2018-10-23 08:57:42 -07:00
3fd50f07fd build: add aio/node_modules to the .bazelignore file (#26471)
PR Close #26471
2018-10-23 08:57:42 -07:00
4237c34c78 test(ivy): mark failing test targets with fixme-ivy-jit and fixme-ivy-local tags (#26471)
We are close enough to blacklist a few test targets, rather than whitelist targets to run...

Because bazel rules can be composed of other rules that don't inherit tags automatically,
I had to explicitly mark all of our ts_library and ng_module targes with "ivy-local" and
"ivy-jit" tags so that we can create a query that excludes all fixme- tagged targets even
if those targets are composed of other targets that don't inherit this tag.

This is the updated overview of ivy related bazel tags:

- ivy-only: target that builds or runs only under ivy
- fixme-ivy-jit: target that doesn't yet build or run under ivy with --compile=jit
- fixme-ivy-local: target that doesn't yet build or run under ivy with --compile=local
- no-ivy-jit: target that is not intended to build or run under ivy with --compile=jit
- no-ivy-local: target that is not intended to build or run under ivy with --compile=local

PR Close #26471
2018-10-23 08:57:42 -07:00
361eaf1888 build: remove obsolete files (#26471)
PR Close #26471
2018-10-23 08:57:41 -07:00
cca89ec36e docs: reorganize events to highlight recent events before older events and move mix to past (#26551)
PR Close #26551
2018-10-23 08:56:52 -07:00
e4c7f369f2 docs: add Brian Love to GDE resources (#26594)
PR Close #26594
2018-10-23 08:54:41 -07:00
d573a14119 fix(ivy): update tree benchmark to use ngIf (#26608)
PR Close #26608
2018-10-23 08:53:19 -07:00
ff767dd153 fix(ivy): support ViewContainerRef ng-container children (#26646)
Issue found while running NgPlural tests with ivy

PR Close #26646
2018-10-23 08:52:30 -07:00
34c6ce6b08 docs: update release info now that v7 is released (#26660)
PR Close #26660
2018-10-23 08:51:48 -07:00
6737e91974 docs(core): fix spelling in ComponentFactory (#26603)
PR Close #26603
2018-10-22 10:38:56 -07:00
1006eab482 fix(ivy): update largetable benchmark to use ngFor (#26604)
PR Close #26604
2018-10-22 10:37:02 -07:00
a9f2952882 build(ivy): fix benchmarks (#26601)
PR Close #26601
2018-10-22 10:36:31 -07:00
100c7eff25 build: fix ivy package-dist generation (#26629)
PR Close #26629
2018-10-20 21:03:46 -07:00
dc7349915d build(bazel): fix //tools/testing:node target deps (#26629)
PR Close #26629
2018-10-20 21:03:46 -07:00
213c25fb08 build: remove manual tags from platform jasmine tests (#26606)
PR Close #26606
2018-10-19 22:52:12 -07:00
615a515bba build: run CI (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
838a3f204f style: ran buildifier (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
15c2467dbd build: review comments addressed (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
74ea4e9b5d style: run buildifier (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
4481571999 ci: don't run google3 tests on bazel external files (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
2132c8f461 refactor(bazel): allow google3 overrides for external deps (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
2b3cac5b31 build: add comment to /integration/bazel/package.json (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
8d5e3e6981 build: update to rules_typescript 0.20.3 and rules_nodejs 0.15.1 (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
30f1dc002a build: add npm deps after rebase (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
5da3b00222 build: restore integrity lines in yarn.lock (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
631998b2df build: idiomatic install of @angular/bazel npm package (#26258) (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
30d6233e83 build: update ngcontainer to bazel 0.18.0 (#26465) (#26488)
* build: update ngcontainer to bazel 0.18.0

* build: update skylint to bazel 0.18

use .bazelignore file to ignore node_modules directory

PR Close #26488
2018-10-19 20:59:29 -07:00
6468711e16 build(bazel): update to rules_typescript 0.20.2 (#26279) (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
d698b0eadf build: update to rules_typescript 0.20.1 and rules_nodejs 0.15.0 (#26260) (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
1f3331f5e6 build(bazel): use fine-grained npm deps (#26111) (#26488)
PR Close #26488
2018-10-19 20:59:29 -07:00
b6c9678f21 build: introduce a package.bzl (#26488)
This lets Angular Bazel users install our transitive deps, rather than have to list them in their WORKSPACE file.
If they want a different version of one of these deps, they just need to install it before calling rules_angular_dependencies.

PR Close #26488
2018-10-19 20:59:29 -07:00
4c2ce4e8ba docs: update animations to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
bb0f95b6fb docs: update elements to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
853faf4c71 docs: update upgrade to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
00c7db02d1 docs: update service-worker to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
13143b850e docs: update router to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
c1724062f1 docs: update platform-webworker to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
7570f7222f docs: update platform-server to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
f1e3d5125d docs: update platform-browser-dynamic to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
3511f08a81 docs: update http with @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
982bc7f2aa docs: update forms with @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
3903e5ebe7 docs: update core to use @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
0918adf39d docs: common with @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
42c331bbf2 docs: update animations with @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:53 -07:00
0bae97a726 docs: update platform-browser with @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:52 -07:00
c5949f85ef build: update ts-api-guardian jsdoc tag requirements (#26595)
Now `@experimental` tags are banned; and `@publicApi`
tags are required on exports.

PR Close #26595
2018-10-19 14:35:52 -07:00
24521f549c docs: convert all @experimental tags to @publicApi tags (#26595)
PR Close #26595
2018-10-19 14:35:52 -07:00
4bd9f53e8f feat(docs-infra): rename tagdef: @experimental to @publicApi (#26595)
PR Close #26595
2018-10-19 14:35:52 -07:00
2a78dcbd5a feat(docs-infra): remove stable & experimental from status selector (#26595)
PR Close #26595
2018-10-19 14:35:52 -07:00
2ea57cdcc3 build: refactor ts-api-guardian jsdoc tag handling (#26595)
Allow the jsdoc tag processing to be configured by
type (export, member, param) and by action (required,
banned, toCopy).

This is a pre-requisite to moving over to using `@publicApi`
tags rather than `@stable` and `@experimental`.

PR Close #26595
2018-10-19 14:35:52 -07:00
31022cbecf feat(ivy): generate .ngsummary.js shims (#26495)
This commit adds generation of .ngsummary.js shims alongside .ngfactory.js
shims when generated files are enabled.

Generated .ngsummary shims contain a single, null export for every exported
class with decorators that exists in the original source files. Ivy code
does not depend on summaries, so these exist only as a placeholder to allow
them to be imported and their values passed to old APIs. This preserves
backwards compatibility.

Testing strategy: this commit adds a compiler test to verify the correct
shape and contents of the generated .ngsummary.js files.

PR Close #26495
2018-10-19 13:30:02 -07:00
ce8053103e refactor(ivy): make shim generation generic in ngtsc (#26495)
This commit refactors the shim host to be agnostic to the shims being
generated, and provides an API for generating additional shims besides
the .ngfactory.js. This will be used in a following commit to generate
.ngsummary.js shims.

Testing strategy: this refactor introduces no new behavior, so it's
sufficient that the existing tests for factory shim generation continue
to pass.

PR Close #26495
2018-10-19 13:30:01 -07:00
0b885ecaf7 refactor(ivy): rename ngtsc/factories to ngtsc/shims (#26495)
This simple refactor of the build rules renames the .ngfactory.js shim
generator to 'shims' instead of 'factories', in preparation for adding
.ngsummary.js shim generation.

Testing strategy: this commit does not introduce any new behavior and
merely moves files and symbols around. It's sufficient that the existing
ngtsc tests pass.

PR Close #26495
2018-10-19 13:30:01 -07:00
1700bd6f08 docs: fix release info navigation (#26558)
PR Close #26558
2018-10-19 11:30:39 -07:00
b89bc37170 fix(docs-infra): correct the version of @angular-devkit/build-angular (#26555)
This dependency has not been correctly updated and I had to update it manually.

I think the issue is related to https://github.com/angular/angular-cli/issues/12624 which was fixed between CLI RCs and final.

PR Close #26555
2018-10-19 11:30:11 -07:00
39df4dbde7 feat(docs-infra): update to @angular/* v7 (#26555)
PR Close #26555
2018-10-19 11:30:11 -07:00
716d887e51 docs: add Katerina Skroumpelou to GDE resources (#26547)
PR Close #26547
2018-10-19 11:29:13 -07:00
5b4cf38166 refactor(bazel): remove workaround for TS bug (#26516)
PR Close #26516
2018-10-19 11:14:24 -07:00
4c0ad5238e build(docs-infra): display github links in CLI API docs (#26515)
This commit includes the following changes:

* CLI version information is read from the CLI package from which
  we read the help files.
* CLI API pages now contain GH links
* line numbers are not shown in GH links, if the doc does not
  have a truthy `startingLine` value. This allows us to remove
  hard coded checks for `guide` pages
* content pages and CLI api docs no longer have a `startingLine`
* the hard-coded `packages` path segment has been removed from
  the templates; instead we now only use the `realProjectRelativePath`.
* the `realProjectRelativePath` has been updated accordingly for API
  and CLI API docs.

PR Close #26515
2018-10-19 11:12:54 -07:00
9e8903ada1 build(docs-infra): show github edit link on CLI overview (#26515)
PR Close #26515
2018-10-19 11:12:53 -07:00
aa55d88408 docs: forms overview copy edit (#26450)
PR Close #26450
2018-10-19 11:08:47 -07:00
07fc4c2464 docs(service-worker): updated browser support for Service Worker (#26408)
PR Close #26408
2018-10-19 11:08:00 -07:00
b9bd95b3b2 build(docs-infra): break long CLI options onto two lines (#26272)
PR Close #26272
2018-10-19 11:07:30 -07:00
3f89aeb80a build(docs-infra): update CLI option rendering (#26272)
PR Close #26272
2018-10-19 11:07:30 -07:00
6c530d3a85 build(docs-infra): render CLI arguments consistently (#26272)
In the command syntax, arguments are rendered as
`var`s enclosed in angle brackets. So this is now repeated
in the arguments table too.

PR Close #26272
2018-10-19 11:07:30 -07:00
03bf0d6b41 docs(ivy): update status for i18n (#26502)
PR Close #26502
2018-10-19 11:06:25 -07:00
d4cee514f6 refactor(ivy): obviate the Bazel component of the ivy_switch (#26550)
Originally, the ivy_switch mechanism used Bazel genrules to conditionally
compile one TS file or another depending on whether ngc or ngtsc was the
selected compiler. This was done because we wanted to avoid importing
certain modules (and thus pulling them into the build) if Ivy was on or
off. This mechanism had a major drawback: ivy_switch became a bottleneck
in the import graph, as it both imports from many places in the codebase
and is imported by many modules in the codebase. This frequently resulted
in cyclic imports which caused issues both with TS and Closure compilation.

It turns out ngcc needs both code paths in the bundle to perform the switch
during its operation anyway, so import switching was later abandoned. This
means that there's no real reason why the ivy_switch mechanism needed to
operate at the Bazel level, and for the ivy_switch file to be a bottleneck.

This commit removes the Bazel-level ivy_switch mechanism, and introduces
an additional TypeScript transform in ngtsc (and the pass-through tsc
compiler used for testing JIT) to perform the same operation that ngcc
does, and flip the switch during ngtsc compilation. This allows the
ivy_switch file to be removed, and the individual switches to be located
directly next to their consumers in the codebase, greatly mitigating the
circular import issues and making the mechanism much easier to use.

As part of this commit, the tag for marking switched variables was changed
from __PRE_NGCC__ to __PRE_R3__, since it's no longer just ngcc which
flips these tags. Most variables were renamed from R3_* to SWITCH_* as well,
since they're referenced mostly in render2 code.

Test strategy: existing test coverage is more than sufficient - if this
didn't work correctly it would break the hello world and todo apps.

PR Close #26550
2018-10-19 09:23:05 -07:00
331989cea3 docs: add release announcement URL 2018-10-18 13:29:04 -07:00
bbf96db2f2 feat(docs-infra): add v6 to the aio version picker 2018-10-18 12:38:29 -07:00
72c2578d14 docs: fix incomplete sentence in CHANGELOG.md 2018-10-18 12:02:19 -07:00
1a666dea61 ci: add forms-overview guide to forms approval list (#26549)
PR Close #26549
2018-10-18 12:01:15 -07:00
7634c1cb31 docs: fix links to browserlist (#26531)
PR Close #26531
2018-10-18 12:00:38 -07:00
95914a0fbf docs: update http to https where possible (#26509)
PR Close #26509
2018-10-18 11:57:57 -07:00
9c50891d6e docs: update links to Karma homepage (#26509)
PR Close #26509
2018-10-18 11:57:57 -07:00
624433c51d docs: removing errant double-quote (#26483)
PR Close #26483
2018-10-18 11:57:27 -07:00
09cc458bfc docs: type fix (#26386)
according to the source code and the doc https://angular.io/api/forms/NgModel#inherited-from-formsngcontrol-1, the method name should be "viewToModelUpdate" instead of "viewToModel"
PR Close #26386
2018-10-18 11:56:51 -07:00
efe0c5f371 release: cut the v7.0.0 release 2018-10-18 10:51:21 -07:00
d9d226087c build(docs-infra): allow "" as empty region in {@example} tags (#26514)
PR Close #26514
2018-10-18 09:54:17 -07:00
7bad1d356d build(docs-infra): only render code example content in one place (#26514)
PR Close #26514
2018-10-18 09:54:17 -07:00
0add00a743 build(docs-infra): throw error if using title on code snippets (#26514)
Since #26396, the `title` property is ignored and `header` should be
used instead for specifying a code snippet's header.

This commit ensures that we don't accidentally set `title` have it be
silently ignored.

PR Close #26514
2018-10-18 09:54:17 -07:00
d557f1d9de build(docs-infra): update git ref for cli command docs (#26545)
This is to get the latest changes done in https://github.com/angular/angular-cli/pull/12634

PR Close #26545
2018-10-18 09:54:00 -07:00
665627e254 fix(aio): add relative to app level routes section (#26504)
Added word *relative* to the **Routes at the app level** section description. This was not specified before. The routes in the *lazy-loading-ngmodules/src/app/app-routing.module.ts* also had `loadChildren` values starting with `app/...`.

The code for `app-routing.module.ts` is already fixed in [this commit](67ad9468d3)
PR Close #26504
2018-10-17 13:11:42 -07:00
a609bf50ed docs: fix formatting of PULL_REQUEST_TEMPLATE.md (#26512)
This change enables developers to check the checkboxes or update them
after they submitted a PR.

PR Close #26512
2018-10-17 13:09:45 -07:00
f8195e5e3d fix(ivy): stub TestBed.compileComponents implementation (#26506)
PR Close #26506
2018-10-17 13:08:14 -07:00
65b209359a build(docs-infra): update git ref for cli command docs (#26497)
Update for version 7 release

PR Close #26497
2018-10-17 11:24:19 -07:00
3a65c9ad4e docs: Update link to angular-cli repo (#26497)
PR Close #26497
2018-10-17 11:24:19 -07:00
77e58c6179 docs: update contributing page (#26497)
PR Close #26497
2018-10-17 11:24:19 -07:00
23d625172a docs: update continuous integration story (#26497)
PR Close #26497
2018-10-17 11:24:19 -07:00
c3643615fc docs: replace alert-is-helpful with alert is-helpful (#26497)
PR Close #26497
2018-10-17 11:24:19 -07:00
638aaecc7d docs: add missing backticks (#26497)
PR Close #26497
2018-10-17 11:24:19 -07:00
5a79decba4 docs: remove for example code (#26519)
PR Close #26519
2018-10-17 11:23:50 -07:00
225162aa6c docs: edit file structure guide (#26256)
PR Close #26256
2018-10-17 11:08:37 -07:00
a43b80a4c9 ci: add triage PRs config for the ngbot (#26477)
PR Close #26477
2018-10-17 11:07:36 -07:00
beebf7fe14 docs: change links to cli wiki to link to new aio docs (#26489)
PR Close #26489
2018-10-17 11:06:34 -07:00
0ef1f7ef0d docs: change links to cli wiki to link to new aio docs files m to z (#26492)
PR Close #26492
2018-10-17 11:06:07 -07:00
fc6dad40ac fix(docs-infra): rename "title" by "header" to avoid unwanted tooltips (#26396)
Closes #26174

PR Close #26396
2018-10-17 11:05:29 -07:00
ecd473bbce fix(docs-infra): don't hide contributor links on devices that cannot hover (#26410)
Fixes #16690

PR Close #26410
2018-10-17 11:04:35 -07:00
8a3fd58cad feat(ivy): i18n compiler support for i18nStart and i18nEnd instructions (#26442)
PR Close #26442
2018-10-17 11:03:52 -07:00
8024857d4c feat(ivy): i18n compiler support for element attributes (#26442)
PR Close #26442
2018-10-17 11:03:52 -07:00
3fa876c5e7 fix(docs-infra): fix top menu logo position (#26473)
Fixes #26468

PR Close #26473
2018-10-17 11:03:23 -07:00
516515d9e3 build(docs-infra): do not add extra space after links in tables (#26505)
Closes #26487

PR Close #26505
2018-10-17 11:02:56 -07:00
948f507ba0 docs(forms): change headings (#25900)
Update heading level so it will appear in the TOC.
PR Close #25900
2018-10-16 20:39:45 -07:00
81a8ee1ddb docs(forms): change headings (#25900)
Remove "Form" sub-heading & move intro to template-driven form heading.
PR Close #25900
2018-10-16 20:39:45 -07:00
5e58da14f0 docs(forms): change headings (#25900)
Change the headings of the template-driven forms guide page.

This makes the first heading consistent with other guide pages and the menu label reducing confusion to users browsing the guide.
PR Close #25900
2018-10-16 20:39:45 -07:00
fa8e633be5 feat(ivy): enhance [style] and [class] bindings to be animation aware (#26096)
PR Close #26096
2018-10-16 20:39:19 -07:00
be337a2e52 refactor(ivy): move styling files around (#26096)
PR Close #26096
2018-10-16 20:39:18 -07:00
4d164b6ca4 fix(ivy): make defineComponent tree shakable by Closure Compiler (#26425)
PR Close #26425
2018-10-16 20:37:35 -07:00
371ffef4ce test(ivy): enable unit tests for @angular/animations (#26470)
PR Close #26470
2018-10-16 20:31:56 -07:00
fdfedceeec feat(router): add prioritizedGuardValue operator optimization and allowing UrlTree return from guard (#26478)
* If all guards return `true`, operator returns `true`
* `false` and `UrlTree` are now both valid returns from a guard
* Both these values wait for higher priority guards to resolve
* Highest priority `false` or `UrlTree` value will be returned

PR Close #26478
2018-10-16 20:31:32 -07:00
9e5d440a0b refactor(ivy): handle animation metadata normalization in the compiler (#26481)
PR Close #26481
2018-10-16 20:31:04 -07:00
0f7d2ca7a8 build: add more labels to review-pr script (#26493)
PR Close #26493
2018-10-16 14:36:28 -07:00
81c9720acb docs: fix links to setup and cli docs (#26463)
PR Close #26463
2018-10-16 14:14:19 -07:00
ea2cfbbd2e docs: remove setup for local dev and anatomy of setup docs from nav (#26380)
PR Close #26380
2018-10-16 14:14:00 -07:00
2326b9c294 fix(service-worker): clean up caches from old SW versions (#26319)
Since the SW immediately takes over all clients, it is safe to delete
caches used by older (e.g. beta) `@angular/service-worker` versions to
avoid running into browser storage quota limitations.

PR Close #26319
2018-10-16 14:12:07 -07:00
41de0e0d98 docs: overview for cli reference section (#26043)
PR Close #26043
2018-10-16 14:11:26 -07:00
f6a2dbf4f5 docs: updated text to match the Getting started guide (#26421)
PR Close #26421
2018-10-16 14:11:12 -07:00
b115374601 build: fix deps for running modules/benchmarks/src/largetable/render3:perf (#26482)
PR Close #26482
2018-10-16 14:10:55 -07:00
7d82053117 docs(ivy): i18n design (#26091)
PR Close #26091
2018-10-16 14:08:01 -07:00
283 changed files with 10910 additions and 7041 deletions

View File

@ -13,7 +13,7 @@ a GitHub token that enables publishing snapshots.
To create the github_token file, we take this approach:
- Find the angular-builds:token in http://valentine
- Go inside the CircleCI default docker image so you use the same version of openssl as we will at runtime: `docker run --rm -it circleci/node:10.12`
- Go inside the ngcontainer docker image so you use the same version of openssl as we will at runtime: `docker run --rm -it angular/ngcontainer`
- echo "https://[token]:@github.com" > credentials
- openssl aes-256-cbc -e -in credentials -out .circleci/github_token -k $KEY
- If needed, base64-encode the result so you can copy-paste it out of docker: `base64 github_token`

View File

@ -7,20 +7,40 @@
# To validate changes, use an online parser, eg.
# http://yaml-online-parser.appspot.com/
# Note that the browser docker image comes with Chrome and Firefox preinstalled. This is just
# needed for jobs that run tests without Bazel. Bazel runs tests with browsers that will be
# fetched by the Webtesting rules. Therefore for jobs that run tests with Bazel, we don't need a
# docker image with browsers pre-installed.
# **NOTE**: If you change the version of the docker images, also change the `cache_key` suffix.
var_1: &default_docker_image circleci/node:10.12
var_2: &browsers_docker_image circleci/node:10.12-browsers
var_3: &cache_key v2-angular-{{ .Branch }}-{{ checksum "yarn.lock" }}-node-10.12
# Variables
## IMPORTANT
# If you change the `docker_image` version, also change the `cache_key` suffix and the version of
# `com_github_bazelbuild_buildtools` in the `/WORKSPACE` file.
var_1: &docker_image angular/ngcontainer:0.7.0
var_2: &cache_key v2-angular-{{ .Branch }}-{{ checksum "yarn.lock" }}-0.7.0
# Define common ENV vars
var_4: &define_env_vars
var_3: &define_env_vars
run:
name: Define environment variables
command: ./.circleci/env.sh
command: |
echo "export PROJECT_ROOT=$(pwd)" | tee -a $BASH_ENV
echo "export CI_AIO_MIN_PWA_SCORE=95" | tee -a $BASH_ENV
# This is the branch being built; e.g. `pull/12345` for PR builds.
echo "export CI_BRANCH=$CIRCLE_BRANCH" | tee -a $BASH_ENV
echo "export CI_COMMIT=$CIRCLE_SHA1" | tee -a $BASH_ENV
# `CI_COMMIT_RANGE` will only be available when `CIRCLE_COMPARE_URL` is also available,
# i.e. on push builds (a.k.a. non-PR builds). That is fine, since we only need it in push builds.
echo "export CI_COMMIT_RANGE=$(sed -r 's|^.*/([0-9a-f]+\.\.\.[0-9a-f]+)$|\1|i' <<< ${CIRCLE_COMPARE_URL:-})" | tee -a $BASH_ENV
echo "export CI_PULL_REQUEST=${CIRCLE_PR_NUMBER:-false}" | tee -a $BASH_ENV
echo "export CI_REPO_NAME=$CIRCLE_PROJECT_REPONAME" | tee -a $BASH_ENV
echo "export CI_REPO_OWNER=$CIRCLE_PROJECT_USERNAME" | tee -a $BASH_ENV
# WARNING: Secrets (do not print).
echo "export CI_SECRET_AIO_DEPLOY_FIREBASE_TOKEN=$AIO_DEPLOY_TOKEN" >> $BASH_ENV
echo "export CI_SECRET_PAYLOAD_FIREBASE_TOKEN=$ANGULAR_PAYLOAD_TOKEN" >> $BASH_ENV
# See remote cache documentation in /docs/BAZEL.md
var_4: &setup-bazel-remote-cache
run:
name: Start up bazel remote cache proxy
command: ~/bazel-remote-proxy -backend circleci://
background: true
var_5: &setup_bazel_remote_execution
run:
@ -28,73 +48,59 @@ var_5: &setup_bazel_remote_execution
command: openssl aes-256-cbc -d -in .circleci/gcp_token -k "$CI_REPO_NAME" -out /home/circleci/.gcp_credentials && echo "export GOOGLE_APPLICATION_CREDENTIALS=/home/circleci/.gcp_credentials" >> $BASH_ENV && sudo bash -c "cat .circleci/rbe-bazel.rc >> /etc/bazel.bazelrc"
# Settings common to each job
var_6: &job_defaults
anchor_1: &job_defaults
working_directory: ~/ng
docker:
- image: *default_docker_image
var_7: &start-xvfb
run:
name: Running X virtual framebuffer
command: Xvfb :99 -screen 0 1280x1024x24
background: true
- image: *docker_image
# After checkout, rebase on top of master.
# Similar to travis behavior, but not quite the same.
# See https://discuss.circleci.com/t/1662
var_8: &post_checkout
anchor_2: &post_checkout
post: git pull --ff-only origin "refs/pull/${CI_PULL_REQUEST//*pull\//}/merge"
var_9: &yarn_install
run:
name: Running Yarn install
command: yarn install --frozen-lockfile --non-interactive
var_10: &setup_circleci_bazel_config
run:
name: Setting up CircleCI bazel configuration
command: sudo cp .circleci/bazel.rc /etc/bazel.bazelrc
version: 2
jobs:
lint:
<<: *job_defaults
resource_class: xlarge
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *setup_circleci_bazel_config
- *yarn_install
- run: sudo cp .circleci/bazel.rc /etc/bazel.bazelrc
# Check BUILD.bazel formatting before we have a node_modules directory
# Then we don't need any exclude pattern to avoid checking those files
- run: 'yarn buildifier -mode=check ||
(echo "BUILD files not formatted. Please run ''yarn buildifier''" ; exit 1)'
# Run the skylark linter to check our Bazel rules
- run: 'yarn skylint ||
(echo -e "\n.bzl files have lint errors. Please run ''yarn skylint''"; exit 1)'
- restore_cache:
key: *cache_key
- run: yarn install --frozen-lockfile --non-interactive
- run: ./node_modules/.bin/gulp lint
test:
<<: *job_defaults
resource_class: xlarge
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *setup_circleci_bazel_config
- *yarn_install
- run: sudo cp .circleci/bazel.rc /etc/bazel.bazelrc
- run: bazel info release
- run: bazel run @nodejs//:yarn
# Setup remote execution and run RBE-compatible tests.
- *setup_bazel_remote_execution
- run: yarn bazel test //... --build_tag_filters=-ivy-only --test_tag_filters=-ivy-only,-local
- run: bazel test //... --build_tag_filters=-ivy-only --test_tag_filters=-ivy-only,-local
# Now run RBE incompatible tests locally.
- run: sudo cp .circleci/bazel.rc /etc/bazel.bazelrc
- run: yarn bazel test //... --build_tag_filters=-ivy-only,local --test_tag_filters=-ivy-only,local
- run: bazel test //... --build_tag_filters=-ivy-only,local --test_tag_filters=-ivy-only,local
# CircleCI will allow us to go back and view/download these artifacts from past builds.
# Also we can use a service like https://buildsize.org/ to automatically track binary size of these artifacts.
@ -126,115 +132,90 @@ jobs:
<<: *job_defaults
resource_class: xlarge
steps:
# don't run this job on the patch branch (to preserve resources)
- run: circleci step halt
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *setup_circleci_bazel_config
- *yarn_install
- *setup_bazel_remote_execution
- run: sudo cp .circleci/bazel.rc /etc/bazel.bazelrc
- run: yarn test-ivy-jit //...
- run: bazel run @yarn//:yarn
- *setup_bazel_remote_execution
- run: bazel test //... --define=compile=jit --build_tag_filters=ivy-jit --test_tag_filters=ivy-jit
test_ivy_aot:
<<: *job_defaults
resource_class: xlarge
steps:
# don't run this job on the patch branch (to preserve resources)
- run: circleci step halt
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *setup_circleci_bazel_config
- *yarn_install
- run: sudo cp .circleci/bazel.rc /etc/bazel.bazelrc
- run: bazel run @yarn//:yarn
- *setup_bazel_remote_execution
- run: bazel test //... --define=compile=aot --build_tag_filters=ivy-aot --test_tag_filters=ivy-aot
- run: yarn test-ivy-aot //...
test_aio:
test_and_deploy_aio:
<<: *job_defaults
docker:
# Needed because the AIO tests and the PWA score test depend on Chrome being available.
- image: *browsers_docker_image
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *start-xvfb
# Build aio
- run: yarn --cwd aio build --progress=false
# Lint the code
- run: yarn --cwd aio lint
# Run PWA-score tests
# (Run before unit and e2e tests, which destroy the `dist/` directory.)
- run: yarn --cwd aio test-pwa-score-localhost $CI_AIO_MIN_PWA_SCORE
- run:
name: Run PWA-score tests
command: xvfb-run --auto-servernum yarn --cwd aio test-pwa-score-localhost $CI_AIO_MIN_PWA_SCORE
# Check the bundle sizes.
# (Run before unit and e2e tests, which destroy the `dist/` directory.)
- run: yarn --cwd aio payload-size
# Run unit tests
- run: yarn --cwd aio test --watch=false
- run: xvfb-run --auto-servernum yarn --cwd aio test --watch=false
# Run e2e tests
- run: yarn --cwd aio e2e
- run: xvfb-run --auto-servernum yarn --cwd aio e2e
# Run unit tests for Firebase redirects
- run: yarn --cwd aio redirects-test
deploy_aio:
<<: *job_defaults
docker:
# Needed because before deploying the deploy-production script runs the PWA score tests.
- image: *browsers_docker_image
steps:
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *start-xvfb
# Deploy angular.io to production (if necessary)
- run: setPublicVar CI_STABLE_BRANCH "$(npm info @angular/core dist-tags.latest | sed -r 's/^\s*([0-9]+\.[0-9]+)\.[0-9]+.*$/\1.x/')"
- run: yarn --cwd aio deploy-production
- run: echo "export CI_STABLE_BRANCH=$(npm info @angular/core dist-tags.latest | sed -r 's/^\s*([0-9]+\.[0-9]+)\.[0-9]+.*$/\1.x/')" | tee -a $BASH_ENV
- run: xvfb-run --auto-servernum yarn --cwd aio deploy-production
test_aio_local:
<<: *job_defaults
docker:
# Needed because the AIO tests and the PWA score test depend on Chrome being available.
- image: *browsers_docker_image
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- attach_workspace:
at: dist
- *define_env_vars
- *start-xvfb
- restore_cache:
key: *cache_key
# Build aio (with local Angular packages)
- run: yarn --cwd aio build-local --progress=false
# Run PWA-score tests
# (Run before unit and e2e tests, which destroy the `dist/` directory.)
- run: yarn --cwd aio test-pwa-score-localhost $CI_AIO_MIN_PWA_SCORE
- run:
name: Run PWA-score tests
command: xvfb-run --auto-servernum yarn --cwd aio test-pwa-score-localhost $CI_AIO_MIN_PWA_SCORE
# Run unit tests
- run: yarn --cwd aio test --watch=false
- run: xvfb-run --auto-servernum yarn --cwd aio test --watch=false
# Run e2e tests
- run: yarn --cwd aio e2e
- run: xvfb-run --auto-servernum yarn --cwd aio e2e
test_aio_tools:
<<: *job_defaults
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- attach_workspace:
at: dist
- *define_env_vars
- restore_cache:
key: *cache_key
# Install
- run: yarn --cwd aio install --frozen-lockfile --non-interactive
- run: yarn --cwd aio extract-cli-command-docs
@ -244,45 +225,37 @@ jobs:
test_docs_examples_0:
<<: *job_defaults
docker:
# Needed because the example e2e tests depend on Chrome.
- image: *browsers_docker_image
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- attach_workspace:
at: dist
- *define_env_vars
- *start-xvfb
- restore_cache:
key: *cache_key
# Install root
- *yarn_install
- run: yarn install --frozen-lockfile --non-interactive
# Install aio
- run: yarn --cwd aio install --frozen-lockfile --non-interactive
# Run examples tests
- run: yarn --cwd aio example-e2e --setup --local --shard=0/2
- run: xvfb-run --auto-servernum yarn --cwd aio example-e2e --setup --local --shard=0/2
test_docs_examples_1:
<<: *job_defaults
docker:
# Needed because the example e2e tests depend on Chrome.
- image: *browsers_docker_image
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- attach_workspace:
at: dist
- *define_env_vars
- *start-xvfb
- restore_cache:
key: *cache_key
# Install root
- *yarn_install
- run: yarn install --frozen-lockfile --non-interactive
# Install aio
- run: yarn --cwd aio install --frozen-lockfile --non-interactive
# Run examples tests
- run: yarn --cwd aio example-e2e --setup --local --shard=1/2
- run: xvfb-run --auto-servernum yarn --cwd aio example-e2e --setup --local --shard=1/2
# This job should only be run on PR builds, where `CI_PULL_REQUEST` is not `false`.
aio_preview:
@ -290,12 +263,12 @@ jobs:
environment:
AIO_SNAPSHOT_ARTIFACT_PATH: &aio_preview_artifact_path 'aio/tmp/snapshot.tgz'
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *yarn_install
- run: yarn install --frozen-lockfile --non-interactive
- run: ./aio/scripts/build-artifacts.sh $AIO_SNAPSHOT_ARTIFACT_PATH $CI_PULL_REQUEST $CI_COMMIT
- store_artifacts:
path: *aio_preview_artifact_path
@ -306,20 +279,16 @@ jobs:
# This job should only be run on PR builds, where `CI_PULL_REQUEST` is not `false`.
test_aio_preview:
<<: *job_defaults
docker:
# Needed because the test-preview script runs e2e tests and the PWA score test with Chrome.
- image: *browsers_docker_image
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *start-xvfb
- run: yarn install --cwd aio --frozen-lockfile --non-interactive
- run:
name: Wait for preview and run tests
command: node aio/scripts/test-preview.js $CI_PULL_REQUEST $CI_COMMIT $CI_AIO_MIN_PWA_SCORE
command: xvfb-run --auto-servernum node aio/scripts/test-preview.js $CI_PULL_REQUEST $CI_COMMIT $CI_AIO_MIN_PWA_SCORE
# This job exists only for backwards-compatibility with old scripts and tests
# that rely on the pre-Bazel dist/packages-dist layout.
@ -332,15 +301,12 @@ jobs:
<<: *job_defaults
resource_class: xlarge
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *setup_circleci_bazel_config
- *yarn_install
- run: sudo cp .circleci/bazel.rc /etc/bazel.bazelrc
- run: bazel run @nodejs//:yarn
- *setup_bazel_remote_execution
- run: scripts/build-packages-dist.sh
# Save the npm packages from //packages/... for other workflow jobs to read
@ -360,31 +326,23 @@ jobs:
# See comments inside the integration/run_tests.sh script.
integration_test:
<<: *job_defaults
docker:
# Needed because the integration tests expect Chrome to be installed (e.g cli-hello-world)
- image: *browsers_docker_image
# Note: we run Bazel in one of the integration tests, and it can consume >2G
# of memory. Together with the system under test, this can exhaust the RAM
# on a 4G worker so we use a larger machine here too.
resource_class: xlarge
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- attach_workspace:
at: dist
- *define_env_vars
- *start-xvfb
- run: ./integration/run_tests.sh
- run: xvfb-run --auto-servernum ./integration/run_tests.sh
# This job updates the content of repos like github.com/angular/core-builds
# for every green build on angular/angular.
publish_snapshot:
<<: *job_defaults
steps:
- checkout:
<<: *post_checkout
- *define_env_vars
# See below - ideally this job should not trigger for non-upstream builds.
# But since it does, we have to check this condition.
@ -396,6 +354,8 @@ jobs:
|| "$CI_REPO_OWNER" != "angular"
|| "$CI_REPO_NAME" != "angular"
]] && circleci step halt || true'
- checkout:
<<: *post_checkout
- attach_workspace:
at: dist
# CircleCI has a config setting to force SSH for all github connections
@ -409,24 +369,15 @@ jobs:
aio_monitoring:
<<: *job_defaults
docker:
# This job needs Chrome to be globally installed because the tests run with Protractor
# which does not load the browser through the Bazel webtesting rules.
- image: *browsers_docker_image
steps:
- *define_env_vars
- checkout:
<<: *post_checkout
- restore_cache:
key: *cache_key
- *define_env_vars
- *start-xvfb
- run:
name: Run tests against the deployed apps
command: ./aio/scripts/test-production.sh $CI_AIO_MIN_PWA_SCORE
- run:
name: Notify caretaker about failure
command: 'curl --request POST --header "Content-Type: application/json" --data "{\"text\":\":x: \`$CIRCLE_JOB\` job failed on build $CIRCLE_BUILD_NUM: $CIRCLE_BUILD_URL :scream:\"}" $CI_SECRET_SLACK_CARETAKER_WEBHOOK_URL'
when: on_fail
command: xvfb-run --auto-servernum ./aio/scripts/test-production.sh $CI_AIO_MIN_PWA_SCORE
workflows:
version: 2
@ -437,10 +388,7 @@ workflows:
- test_ivy_jit
- test_ivy_aot
- build-packages-dist
- test_aio
- deploy_aio:
requires:
- test_aio
- test_and_deploy_aio
- test_aio_local:
requires:
- build-packages-dist

View File

@ -1,38 +0,0 @@
####################################################################################################
# Helpers for defining environment variables for CircleCI.
#
# In CircleCI, each step runs in a new shell. The way to share ENV variables across steps is to
# export them from `$BASH_ENV`, which is automatically sourced at the beginning of every step (for
# the default `bash` shell).
#
# See also https://circleci.com/docs/2.0/env-vars/#using-bash_env-to-set-environment-variables.
####################################################################################################
# Set and print an environment variable.
#
# Use this function for setting environment variables that are public, i.e. it is OK for them to be
# visible to anyone through the CI logs.
#
# Usage: `setPublicVar <name> <value>`
function setPublicVar() {
setSecretVar $1 $2;
echo "$1=$2";
}
# Set (without printing) an environment variable.
#
# Use this function for setting environment variables that are secret, i.e. should not be visible to
# everyone through the CI logs.
#
# Usage: `setSecretVar <name> <value>`
function setSecretVar() {
# WARNING: Secrets (e.g. passwords, access tokens) should NOT be printed.
# (Keep original shell options to restore at the end.)
local -r originalShellOptions=$(set +o);
set +x -eu -o pipefail;
echo "export $1=\"${2:-}\";" >> $BASH_ENV;
# Restore original shell options.
eval "$originalShellOptions";
}

View File

@ -1,35 +0,0 @@
#!/usr/bin/env bash
# Load helpers and make them available everywhere (through `$BASH_ENV`).
readonly envHelpersPath="`dirname $0`/env-helpers.inc.sh";
source $envHelpersPath;
echo "source $envHelpersPath;" >> $BASH_ENV;
####################################################################################################
# Define PUBLIC environment variables for CircleCI.
####################################################################################################
setPublicVar PROJECT_ROOT "$(pwd)";
setPublicVar CI_AIO_MIN_PWA_SCORE "95";
# This is the branch being built; e.g. `pull/12345` for PR builds.
setPublicVar CI_BRANCH "$CIRCLE_BRANCH";
setPublicVar CI_COMMIT "$CIRCLE_SHA1";
# `CI_COMMIT_RANGE` will only be available when `CIRCLE_COMPARE_URL` is also available,
# i.e. on push builds (a.k.a. non-PR builds). That is fine, since we only need it in push builds.
setPublicVar CI_COMMIT_RANGE "$(sed -r 's|^.*/([0-9a-f]+\.\.\.[0-9a-f]+)$|\1|i' <<< ${CIRCLE_COMPARE_URL:-})";
setPublicVar CI_PULL_REQUEST "${CIRCLE_PR_NUMBER:-false}";
setPublicVar CI_REPO_NAME "$CIRCLE_PROJECT_REPONAME";
setPublicVar CI_REPO_OWNER "$CIRCLE_PROJECT_USERNAME";
####################################################################################################
# Define SECRET environment variables for CircleCI.
####################################################################################################
setSecretVar CI_SECRET_AIO_DEPLOY_FIREBASE_TOKEN "$AIO_DEPLOY_TOKEN";
setSecretVar CI_SECRET_PAYLOAD_FIREBASE_TOKEN "$ANGULAR_PAYLOAD_TOKEN";
# Defined in https://angular-team.slack.com/apps/A0F7VRE7N-circleci.
setSecretVar CI_SECRET_SLACK_CARETAKER_WEBHOOK_URL "$SLACK_CARETAKER_WEBHOOK_URL";
# Source `$BASH_ENV` to make the variables available immediately.
source $BASH_ENV;

View File

@ -8,6 +8,13 @@ exports_files([
"protractor-perf.conf.js",
])
# Developers should always run `bazel run :install`
# This ensures that package.json in subdirectories get installed as well.
alias(
name = "install",
actual = "@nodejs//:yarn",
)
filegroup(
name = "web_test_bootstrap_scripts",
# do not sort

View File

@ -1,12 +1,18 @@
<a name="7.0.2"></a>
## [7.0.2](https://github.com/angular/angular/compare/7.0.1...7.0.2) (2018-10-31)
<a name="7.1.0-beta.0"></a>
# [7.1.0-beta.0](https://github.com/angular/angular/compare/7.0.0-rc.1...7.1.0-beta.0) (2018-10-24)
### Bug Fixes
* **compiler:** generate relative paths only in summary file errors ([#26759](https://github.com/angular/angular/issues/26759)) ([c01f340](https://github.com/angular/angular/commit/c01f340))
* **core:** Remove static dependency from [@angular](https://github.com/angular)/core to [@angular](https://github.com/angular)/compiler ([#26734](https://github.com/angular/angular/issues/26734)) ([#26879](https://github.com/angular/angular/issues/26879)) ([257ac83](https://github.com/angular/angular/commit/257ac83))
* **core:** support computed base class in metadata inheritance ([#24014](https://github.com/angular/angular/issues/24014)) ([b3c6409](https://github.com/angular/angular/commit/b3c6409))
* **core:** allow null value for renderer setElement(…) ([#17065](https://github.com/angular/angular/issues/17065)) ([ff15043](https://github.com/angular/angular/commit/ff15043)), closes [#13686](https://github.com/angular/angular/issues/13686)
* **router:** fix regression where navigateByUrl promise didn't resolve on CanLoad failure ([#26455](https://github.com/angular/angular/issues/26455)) ([1c9b065](https://github.com/angular/angular/commit/1c9b065)), closes [#26284](https://github.com/angular/angular/issues/26284)
* **service-worker:** clean up caches from old SW versions ([#26319](https://github.com/angular/angular/issues/26319)) ([2326b9c](https://github.com/angular/angular/commit/2326b9c))
* **upgrade:** properly destroy upgraded component elements and descendants ([#26209](https://github.com/angular/angular/issues/26209)) ([071934e](https://github.com/angular/angular/commit/071934e)), closes [#26208](https://github.com/angular/angular/issues/26208)
### Features
* **router:** add prioritizedGuardValue operator optimization and allowing UrlTree return from guard ([#26478](https://github.com/angular/angular/issues/26478)) ([fdfedce](https://github.com/angular/angular/commit/fdfedce))
@ -91,6 +97,7 @@ To learn about the release highlights and our new CLI-powered update workflow fo
### Bug Fixes
* **platform-browser:** fix [#22155](https://github.com/angular/angular/issues/22155), destroy hammer manager when `HammerInstance.off()` is run ([#22156](https://github.com/angular/angular/issues/22156)) ([3b4d9dc](https://github.com/angular/angular/commit/3b4d9dc))
* **upgrade:** properly destroy upgraded component elements and descendants ([#26209](https://github.com/angular/angular/issues/26209)) ([623adbb](https://github.com/angular/angular/commit/623adbb)), closes [#26208](https://github.com/angular/angular/issues/26208)

View File

@ -6,16 +6,6 @@ load(
"rules_angular_dev_dependencies",
)
# Uncomment for local bazel rules development
#local_repository(
# name = "build_bazel_rules_nodejs",
# path = "../rules_nodejs",
#)
#local_repository(
# name = "build_bazel_rules_typescript",
# path = "../rules_typescript",
#)
# Angular Bazel users will call this function
rules_angular_dependencies()
# These are the dependencies only for us

View File

@ -49,6 +49,8 @@ You can edit the generated files directly, or add to and modify them using CLI c
Use the [ng generate](cli/generate) command to add new files for additional components and services, and code for new pipes, directives, and so on.
Commands such as [add](cli/add) and [generate](cli/generate), which create or operate on apps and libraries, must be executed from within a workspace or project folder.
When you use the [ng serve](cli/serve) command to build an app and serve it locally, the server automatically rebuilds the app and reloads the page when you change any of the source files.
* See more about the [Workspace file structure](guide/file-structure).
When you use the [ng serve](cli/serve) command to build an app and serve it locally, the server automatically rebuilds the app and reloads the page when you change any of the source files.

View File

@ -12,7 +12,7 @@ h2, h3 {
body {
margin: 2em;
}
body, input[type="text"], button {
body, input[text], button {
color: #888;
font-family: Cambria, Georgia;
}

View File

@ -40,7 +40,7 @@ export class HeroService {
// #enddocregion getHeroes-1
.pipe(
// #enddocregion getHeroes-2
tap(_ => this.log('fetched heroes')),
tap(heroes => this.log('fetched heroes')),
// #docregion getHeroes-2
catchError(this.handleError('getHeroes', []))
);

View File

@ -1,19 +1,19 @@
# Deployment
When you are ready to deploy your Angular application to a remote server, you have various options for
deployment.
deployment.
{@a dev-deploy}
{@a copy-files}
## Simplest deployment possible
For the simplest deployment, create a production build and copy the output directory to a web server.
For the simplest deployment, build for development and copy the output directory to a web server.
1. Start with the production build:
1. Start with the development build:
<code-example language="none" class="code-shell">
ng build --prod
ng build
</code-example>
@ -22,7 +22,8 @@ For the simplest deployment, create a production build and copy the output direc
3. Configure the server to redirect requests for missing files to `index.html`.
Learn more about server-side redirects [below](#fallback).
This is the simplest production-ready deployment of your application.
This is _not_ a production deployment. It's not optimized, and it won't be fast for users.
It might be good enough for sharing your progress and ideas internally with managers, teammates, and other stakeholders. For the next steps in deployment, see [Optimize for production](#optimize).
{@a deploy-to-github}
@ -30,7 +31,7 @@ This is the simplest production-ready deployment of your application.
Another simple way to deploy your Angular app is to use [GitHub Pages](https://help.github.com/articles/what-is-github-pages/).
1. You need to [create a GitHub account](https://github.com/join) if you don't have one, and then [create a repository](https://help.github.com/articles/create-a-repo/) for your project.
1. You need to [create a GitHub account](https://github.com/join) if you don't have one, and then [create a repository](https://help.github.com/articles/create-a-repo/) for your project.
Make a note of the user name and project name in GitHub.
1. Build your project using Github project name, with the Angular CLI command [`ng build`](cli/build) and the options shown here:
@ -38,9 +39,9 @@ Make a note of the user name and project name in GitHub.
ng build --prod --output-path docs --base-href <project_name>
</code-example>
1. When the build is complete, make a copy of `docs/index.html` and name it `docs/404.html`.
1. When the build is complete, make a copy of `docs/index.html` and name it `docs/404.html`.
1. Commit your changes and push.
1. Commit your changes and push.
1. On the GitHub project page, configure it to [publish from the docs folder](https://help.github.com/articles/configuring-a-publishing-source-for-github-pages/#publishing-your-github-pages-site-from-a-docs-folder-on-your-master-branch).
@ -96,6 +97,51 @@ There is no single configuration that works for every server.
The following sections describe configurations for some of the most popular servers.
The list is by no means exhaustive, but should provide you with a good starting point.
#### Development servers
During development, the [`ng serve`](cli/serve) CLI command lets you run your app in a local browser.
The CLI recompiles the application each time you save a file,
and reloads the browser with the newly compiled application.
The app is hosted in local memory and served on `http://localhost:4200/`, using [webpack-dev-server](https://webpack.js.org/guides/development/#webpack-dev-server).
{@a serve-from-disk}
Later in development, you might want a closer approximation of how your app will behave when deployed.
You can output your distribution folder (`dist`) to disk, but you need to install a different web server.
Try installing [lite-server](https://github.com/johnpapa/lite-server); like `webpack-dev-server`, it can automatically reload your browser when you write new files.
To get the live-reload experience, you will need to run two terminals.
The first runs the build in a watch mode and compiles the application to the `dist` folder.
The second runs the web server against the `dist` folder.
The combination of these two processes provides the same behavior as `ng serve`.
1. Start the build in terminal A:
<code-example language="none" class="code-shell">
ng build --watch
</code-example>
1. Start the web server in terminal B:
<code-example language="none" class="code-shell">
lite-server --baseDir="dist"
</code-example>
The default browser opens to the appropriate URL.
* [Lite-Server](https://github.com/johnpapa/lite-server): the default dev server installed with the
[Quickstart repo](https://github.com/angular/quickstart) is pre-configured to fallback to `index.html`.
* [Webpack-Dev-Server](https://github.com/webpack/webpack-dev-server): setup the
`historyApiFallback` entry in the dev server options as follows:
<code-example>
historyApiFallback: {
disableDotRule: true,
htmlAcceptHeaders: ['text/html', 'application/xhtml+xml']
}
</code-example>
#### Production servers
* [Apache](https://httpd.apache.org/): add a
[rewrite rule](http://httpd.apache.org/docs/current/mod/mod_rewrite.html) to the `.htaccess` file as shown
(https://ngmilk.rocks/2015/03/09/angularjs-html5-mode-or-pretty-urls-on-apache-using-htaccess/):
@ -184,9 +230,19 @@ Read about how to enable CORS for specific servers at
{@a optimize}
## Production optimizations
## Optimize for production
The `--prod` _meta-flag_ engages the following build optimization features.
Although deploying directly from the development environment works,
you can generate an optimized build with additional CLI command line flags,
starting with `--prod`.
### Build with _--prod_
<code-example language="none" class="code-shell">
ng build --prod
</code-example>
The `--prod` _meta-flag_ engages the following optimization features.
* [Ahead-of-Time (AOT) Compilation](guide/aot-compiler): pre-compiles Angular component templates.
* [Production mode](#enable-prod-mode): deploys the production environment which enables _production mode_.
@ -195,22 +251,25 @@ The `--prod` _meta-flag_ engages the following build optimization features.
* Uglification: rewrites code to use short, cryptic variable and function names.
* Dead code elimination: removes unreferenced modules and much unused code.
See [`ng build`](cli/build) for more about CLI build options and what they do.
The remaining [copy deployment steps](#copy-files) are the same as before.
See [`ng build`](cli/build) for more about CLI build options and what they do.
{@a enable-prod-mode}
### Enable runtime production mode
### Enable production mode
In addition to build optimizations, Angular also has a runtime production mode. Angular apps run in development mode by default, as you can see by the following message on the browser console:
Angular apps run in development mode by default, as you can see by the following message on the browser
console:
<code-example format="nocode">
Angular is running in the development mode. Call enableProdMode() to enable the production mode.
</code-example>
Switching to _production mode_ makes it run faster by disabling development specific checks such as the dual change detection cycles.
Switching to _production mode_ can make it run faster by disabling development specific checks such as the dual change detection cycles.
When you enable production builds via `--prod` command line flag, the runtime production mode is enabled as well.
Building for production (or appending the `--environment=prod` flag) enables _production mode_
Look at the CLI-generated `main.ts` to see how this works.
{@a lazy-loading}
@ -234,7 +293,7 @@ If you do that, the module will be loaded immediately.
The bundling configuration must take lazy loading into consideration.
Because lazy-loaded modules aren't imported in JavaScript, bundlers exclude them by default.
Bundlers don't know about the router configuration and can't create separate bundles for lazy-loaded modules.
Bundlers don't know about the router configuration and can't create separate bundles for lazy-loaded modules.
You would have to create these bundles manually.
The CLI runs the
@ -329,7 +388,7 @@ for the missing files. Look at where it _tried_ to find those files and adjust t
## Building and serving for deployment
When you are designing and developing applications, you typically use `ng serve` to build your app for fast, local, iterative development.
When you are designing and developing applications, you typically use `ng serve` to build your app for fast, local, iterative development.
When you are ready to deploy, however, you must use the `ng build` command to build the app and deploy the build artifacts elsewhere.
Both `ng build` and `ng serve` clear the output folder before they build the project, but only the `ng build` command writes the generated build artifacts to the output folder.
@ -342,12 +401,12 @@ To output to a different folder, change the `outputPath` in `angular.json`.
</div>
The `ng serve` command builds, watches, and serves the application from local memory, using a local development server.
When you have deployed your app to another server, however, you might still want to serve the app so that you can continue to see changes that you make in it.
When you have deployed your app to another server, however, you might still want to serve the app so that you can continue to see changes that you make in it.
You can do this by adding the `--watch` option to the `ng build` command.
```
ng build --watch
```
Like the `ng serve` command, this regenerates output files when source files change.
Like the `ng serve` command, this regenerates output files when source files change.
For complete details of the CLI commands, see the [CLI command reference](cli).

View File

@ -98,7 +98,7 @@ When the CLI generated the `CustomerDashboardComponent` for the feature module,
</code-example>
To see this HTML in the `AppComponent`, you first have to export the `CustomerDashboardComponent` in the `CustomerDashboardModule`. In `customer-dashboard.module.ts`, just beneath the `declarations` array, add an `exports` array containing `CustomerDashboardComponent`:
To see this HTML in the `AppComponent`, you first have to export the `CustomerDashboardComponent` in the `CustomerDashboardModule`. In `customer-dashboard.module.ts`, just beneath the `declarations` array, add an `exports` array containing `CustomerDashboardModule`:
<code-example path="feature-modules/src/app/customer-dashboard/customer-dashboard.module.ts" region="component-exports" header="src/app/customer-dashboard/customer-dashboard.module.ts" linenums="false">
</code-example>

View File

@ -672,7 +672,7 @@ format that Angular understands, such as `.xtb`.
How you provide this information depends upon whether you compile with
the JIT compiler or the AOT compiler.
* With [AOT](guide/i18n#merge-aot), you pass the information as configuration settings.
* With [AOT](guide/i18n#merge-aot), you pass the information as a configuration
* With [JIT](guide/i18n#merge-jit), you provide the information at bootstrap time.

View File

@ -1,6 +1,6 @@
# Workspace npm dependencies
The Angular Framework, Angular CLI, and components used by Angular applications are packaged as [npm packages](https://docs.npmjs.com/getting-started/what-is-npm "What is npm?") and distributed via the [npm registry](https://docs.npmjs.com/).
The Angular Framework, Angular CLI, and components used by Angular applicatins are packaged as [npm packages](https://docs.npmjs.com/getting-started/what-is-npm "What is npm?") and distributed via the [npm registry](https://docs.npmjs.com/).
You can download and install these npm packages by using the [npm CLI client](https://docs.npmjs.com/cli/install), which is installed with and runs as a [Node.js®](https://nodejs.org "Nodejs.org") application. By default, the Angular CLI uses the npm client.
@ -138,4 +138,4 @@ Package name | Description
For information about how the Angular CLI handles packages see the following guides:
* [Building and serving](guide/build) describes how packages come together to create a development build.
* [Deployment](guide/deployment) describes how packages come together to create a production build.
* [Deployment](guide/deployment) describes how packages come together to create a production build.

View File

@ -1,135 +0,0 @@
# Angular Workspace Configuration
A file named `angular.json` at the root level of an Angular [workspace](guide/glossary#workspace) provides workspace-wide and project-specific configuration defaults for build and development tools provided by the Angular CLI.
Path values given in the configuration are relative to the root workspace folder.
## Overall JSON structure
At the top level of `angular.json`, a few properties configure the workspace, and a `projects` section contains the remaining per-project configuration options.
* `version`: The configuration-file version.
* `newProjectRoot`: Path where new projects are created. Absolute or relative to the workspace folder.
* `defaultProject`: Default project name to use in commands, where not provided as an argument. When you use `ng new` to create a new app in a new workspace, that app is the default project for the workspace until you change it here.
* `projects` : Contains a subsection for each project (library, app, e2e test app) in the workspace, with the per-project configuration options.
The initial app that you create with `ng new app_name` is listed under "projects", along with its corresponding end-to-end test app:
<code-example format="." language="none" linenums="false">
projects
app_name
...
app_name-e2e
...
</code-example>
Each additional app that you create with `ng generate application` has a corresponding end-to-end test project, with its own configuration section.
When you create a library project with `ng generate library`, the library project is also added to the `projects` section.
<div class="alert is-helpful">
Note that the `projects` section of the configuration file does not correspond exactly to the workspace file structure.
* The initial app created by `ng new` is at the top level of the workspace file structure, along with its e2e app.
* Additional apps, e2e apps, and libraries go into a `projects` folder in the workspace.
For more information, see [Workspace and project file structure](guide/file-structure).
</div>
## Project configuration options
The following top-level configuration properties are available for each project, under `projects:<project_name>`.
<code-example format="." language="json" linenums="false">
"my-v7-app": {
"root": "",
"sourceRoot": "src",
"projectType": "application",
"prefix": "app",
"schematics": {},
"architect": {}
}
</code-example>
| PROPERTY | DESCRIPTION |
| :-------------- | :---------------------------- |
| `root` | The root folder for this project's files, relative to the workspace folder. Empty for the initial app, which resides at the top level of the workspace. |
| `sourceRoot` | The root folder for this project's source files. |
| `projectType` | One of "application" or "library". An application can run independently in a browser, while a library cannot. Both an app and its e2e test app are of type "application".|
| `prefix` | A string that Angular prepends to generated selectors. Can be customized to identify an app or feature area. |
| `schematics` | An object containing schematics that customize CLI commands for this project. |
| `architect` | An object containing configuration defaults for Architect builder targets for this project. |
## Project tool configuration options
Architect is the tool that the CLI uses to perform complex tasks such as compilation and test running, according to provided configurations. The `architect` section contains a set of Architect *targets*. Many of the targets correspond to the CLI commands that run them. Some additional predefined targets can be run using the `ng run` command, and you can define your own targets.
Each target object specifies the `builder` for that target, which is the npm package for the tool that Architect runs. In addition, each target has an `options` section that configure default options for the target, and a `configurations` section that names and specifies alternative configurations for the target. See the example in [Build target](#build-target) below.
<code-example format="." language="json" linenums="false">
"architect": {
"build": { },
"serve": { },
"e2e" : { },
"test": { },
"lint": { },
"extract-i18n": { },
"server": { },
"app-shell": { }
}
</code-example>
* The `architect/build` section configures defaults for options of the `ng build` command. See [Build target]{#build-target} below for more information.
* The `architect/serve` section overrides build defaults and supplies additional serve defaults for the `ng serve` command. In addition to the options available for the `ng build` command, it adds options related to serving the app.
* The `architect/e2e` section overrides build-option defaults for building end-to-end testing apps using the `ng e2e` command.
* The `architect/test` section overrides build-option defaults for test builds and supplies additional test-running defaults for the `ng test` command.
* The `architect/lint` section configures defaults for options of the `ng lint` command, which performs code analysis on project source files. The default linting tool for Angular is [TSLint](https://palantir.github.io/tslint/).
* The `architect/extract-i18n` section configures defaults for options of the `ng-xi18n` tool used by the `ng xi18n` command, which extracts marked message strings from source code and outputs translation files.
* The `architect/server` section configures defaults for creating a Universal app with server-side rendering, using the `ng run <project>:server` command.
* The `architect/app-shell` section configures defaults for creating an app shell for a progressive web app (PWA), using the `ng run <project>:app-shell` command.
In general, the options for which you can configure defaults correspond to the command options listed in the [CLI reference page](cli) for each command.
Note that all options in the configuration file must use [camelCase](guide/glossary#case-conventions), rather than dash-case.
{@a build-target}
## Build target
The `architect/build` section configures defaults for options of the `ng build` command. It has the following top-level properties.
| PROPERTY | DESCRIPTION |
| :-------------- | :---------------------------- |
| `builder` | The npm package for the build tool used to create this target. The default is `@angular-devkit/build-angular:browser`, which uses the [webpack](https://webpack.js.org/) package bundler. |
| `options` | This section contains defaults for build options, used when no named alternative configuration is specified. See [Default build options](#build-props) below. |
| `configurations`| This section defines and names alternative configurations for different intended destinations. It contains a section for each named configuration, which sets the default options for that intended environment. See [Alternate build configurations](#build-configs) below. |
{@a build-configs}
### Alternate build configurations
By default, a `production` configuration is defined, and the `ng build` command has `--prod` option that builds using this configuration. The `production` configuration sets defaults that optimize the app in a number of ways, such bundling files, minimizing excess whitespace, removing comments and dead code, and rewriting code to use short, cryptic names ("minification").
You can define and name additional alternate configurations (such as `stage`, for instance) appropriate to your development process. Some examples of different build configurations are `stable`, `archive` and `next` used by AIO itself, and the individual locale-specific configurations required for building localized versions of an app. For details, see [Internationalization (i18n)](guide/i18n#merge-aot).
{@a build-props}
### Additional build and test options
The configurable options for a default or targeted build generally correspond to the options available for the [`ng build`](cli/build), [`ng serve`](cli/serve), and [`ng test`](cli/test) commands. For details of those options and their possible values, see the [CLI Reference](cli).
Some additional options (listed below) can only be set through the configuration file, either by direct editing or with the `ng config` command.
| OPTIONS PROPERTIES | DESCRIPTION |
| :------------------------- | :---------------------------- |
| `fileReplacements` | An object containing files and their compile-time replacements. |
| `stylePreprocessorOptions` | An object containing option-value pairs to pass to style preprocessors. |
| `assets` | An object containing paths to static assets to add to the global context of the project. The default paths point to the project's icon file and its `assets` folder. |
| `styles` | An object containing style files to add to the global context of the project. Angular CLI supports CSS imports and all major CSS preprocessors: [sass/scss](http://sass-lang.com/), [less](http://lesscss.org/), and [stylus](http://stylus-lang.com/). |
| `scripts` | An object containing JavaScript script files to add to the global context of the project. The scripts are loaded exactly as if you had added them in a `<script>` tag inside `index.html`. |
| `budgets` | Default size-budget type and threshholds for all or parts of your app. You can configure the builder to report a warning or an error when the output reaches or exceeds a threshold size. See [Configure size budgets](guide/build#configure-size-budgets). (Not available in `test` section.) |

File diff suppressed because it is too large Load Diff

View File

@ -211,7 +211,7 @@
"logo": "https://cloud.githubusercontent.com/assets/1016365/10639063/138338bc-7806-11e5-8057-d34c75f3cafc.png",
"rev": true,
"title": "Angular Universal",
"url": "https://angular.io/guide/universal"
"url": "https://github.com/angular/universal"
},
"c1": {
"desc": "Lightweight development only Node.js® server",
@ -273,13 +273,6 @@
"rev": true,
"title": "UI-jar - Test Driven Style Guide Development",
"url": "https://github.com/ui-jar/ui-jar"
},
"protactor": {
"desc": "The official end to end testing framework for Angular apps",
"logo": "",
"rev": true,
"title": "Protractor",
"url": "https://protractor.angular.io/"
}
}
},
@ -369,7 +362,7 @@
"logo": "",
"rev": true,
"title": "Angular Material",
"url": "https://material.angular.io/"
"url": "https://github.com/angular/material2"
},
"mcc": {
"desc": "Material components made by the community",
@ -384,12 +377,6 @@
"title": "Ant Design of Angular (ng-zorro-antd)",
"url": "https://ng.ant.design/docs/introduce/en"
},
"ngzorromobile": {
"desc": "A set of enterprise-class mobile UI components based on Ant Design Mobile and Angular",
"rev": true,
"title": "Ant Design Mobile of Angular (ng-zorro-antd-mobile)",
"url": "http://ng.mobile.ant.design/#/docs/introduce/en"
},
"aggrid": {
"desc": "A datagrid for Angular with enterprise style features such as sorting, filtering, custom rendering, editing, grouping, aggregation and pivoting.",
"rev": true,

View File

@ -513,14 +513,8 @@
{
"url": "guide/file-structure",
"title": "Project File Structure",
"tooltip": "How your Angular workspace looks on your filesystem."
"tooltip": "How your Angular workspace looks in your filesystem."
},
{
"url": "guide/workspace-config",
"title": "Workspace Configuration",
"tooltip": "The \"angular.json\" file contains workspace and project configuration defaults for Angular CLI commands."
},
{
"url": "guide/npm-packages",
"title": "npm Dependencies",

View File

@ -18,7 +18,7 @@
"build-for": "yarn ~~build --configuration",
"prebuild-local": "yarn setup-local",
"build-local": "yarn ~~build --configuration=stable",
"extract-cli-command-docs": "node tools/transforms/cli-docs-package/extract-cli-commands.js 4faa81e25",
"extract-cli-command-docs": "node tools/transforms/cli-docs-package/extract-cli-commands.js a2129510d7d57d1c02bec563872adf0204e11a2f",
"lint": "yarn check-env && yarn docs-lint && ng lint && yarn example-lint && yarn tools-lint",
"test": "yarn check-env && ng test",
"pree2e": "yarn check-env && yarn update-webdriver",
@ -30,8 +30,6 @@
"setup-local": "yarn aio-use-local && yarn example-use-local",
"postsetup-local": "yarn postsetup",
"set-opensearch-url": "node --eval \"const sh = require('shelljs'); sh.set('-e'); sh.sed('-i', /PLACEHOLDER_URL/g, process.argv[1], 'dist/assets/opensearch.xml');\"",
"presmoke-tests": "yarn update-webdriver",
"smoke-tests": "protractor tests/deployment/e2e/protractor.conf.js --suite smoke --baseUrl",
"test-pwa-score": "node scripts/test-pwa-score",
"test-pwa-score-localhost": "run-p --race \"~~http-server dist -p 4200 --silent\" \"test-pwa-score http://localhost:4200 {1} {2}\" --",
"example-e2e": "yarn example-check-local && node ./tools/examples/run-example-e2e",
@ -115,7 +113,7 @@
"entities": "^1.1.1",
"eslint": "^3.19.0",
"eslint-plugin-jasmine": "^2.2.0",
"firebase-tools": "^5.1.1",
"firebase-tools": "^3.2.1",
"fs-extra": "^2.1.2",
"globby": "^6.1.0",
"hast-util-is-element": "^1.0.0",

View File

@ -13,7 +13,7 @@ readonly deployedUrl=https://pr${prNumber}-${prLastSha:0:7}.ngbuilds.io/
cd $PROJECT_ROOT/aio
# Build and store the app
yarn build --progress=false
yarn build
# Set deployedUrl as parameter in the opensearch description
# deployedUrl must end with /

View File

@ -93,7 +93,7 @@ fi
cd "`dirname $0`/.."
# Build the app
yarn build-for $deployEnv --progress=false
yarn build-for $deployEnv
# Include any mode-specific files
cp -rf src/extra-files/$deployEnv/. dist/
@ -106,8 +106,8 @@ fi
yarn payload-size
# Deploy to Firebase
yarn firebase use "$projectId" --token "$firebaseToken"
yarn firebase deploy --message "Commit: $CI_COMMIT" --non-interactive --token "$firebaseToken"
firebase use "$projectId" --token "$firebaseToken"
firebase deploy --message "Commit: $CI_COMMIT" --non-interactive --token "$firebaseToken"
# Run PWA-score tests
yarn test-pwa-score "$deployedUrl" "$CI_AIO_MIN_PWA_SCORE"

View File

@ -45,9 +45,8 @@ get(previewabilityCheckUrl).
const totalSecs = Math.round((previewCheckInterval * previewCheckAttempts) / 1000);
throw new Error(`Preview still not available after ${totalSecs}s.`);
}).
// The preview is now available. Run the tests.
then(() => yarnRun('smoke-tests', previewUrl)).
then(() => yarnRun('test-pwa-score', previewUrl, minPwaScore));
// The preview is now available. Run the PWA tests.
then(() => runPwaTests());
}).
catch(onError);
@ -94,6 +93,15 @@ function reportNoPreview(reason) {
console.log(`No (public) preview available. (Reason: ${reason})`);
}
function runPwaTests() {
return new Promise((resolve, reject) => {
const spawnOptions = {cwd: __dirname, stdio: 'inherit'};
spawn('yarn', ['test-pwa-score', previewUrl, minPwaScore], spawnOptions).
on('error', reject).
on('exit', code => (code === 0 ? resolve : reject)());
});
}
function validateArgs(args) {
if (args.length !== 3) {
const relativeScriptPath = relative('.', __filename.replace(/\.js$/, ''));
@ -111,12 +119,3 @@ function wait(delay) {
console.log(`Waiting ${delay}ms...`);
return new Promise(resolve => setTimeout(resolve, delay));
}
function yarnRun(script, ...args) {
return new Promise((resolve, reject) => {
const spawnOptions = {cwd: __dirname, stdio: 'inherit'};
spawn('yarn', [script, ...args], spawnOptions).
on('error', reject).
on('exit', code => (code === 0 ? resolve : reject)());
});
}

View File

@ -16,7 +16,7 @@ set +x -eu -o pipefail
# Install dependencies.
echo -e "\nInstalling dependencies in '$aioDir'...\n-----"
yarn install --frozen-lockfile --non-interactive
yarn install --frozen-lockfile
yarn update-webdriver
# Run checks for all URLs.

View File

@ -3,11 +3,9 @@
exports.config = {
allScriptsTimeout: 11000,
suites: {
full: './*.e2e-spec.ts',
smoke: './smoke-tests.e2e-spec.ts',
},
suite: 'full',
specs: [
'./*.e2e-spec.ts'
],
capabilities: {
browserName: 'chrome',
// For Travis

View File

@ -59,9 +59,7 @@ describe(browser.baseUrl, () => {
it('should serve `index.html` for unknown pages', async () => {
const aioShell = element(by.css('aio-shell'));
const heading = aioShell.element(by.css('h1'));
await page.goTo(unknownPagePath);
await browser.wait(() => page.getDocViewerText(), 5000); // Wait for the document to be loaded.
expect(aioShell.isPresent()).toBe(true);
expect(heading.getText()).toMatch(/page not found/i);

View File

@ -29,8 +29,6 @@ describe(browser.baseUrl, () => {
Object.keys(textPerUrl).forEach(url => {
it(`should show the page at '${url}'`, () => {
page.goTo(url);
browser.wait(() => page.getDocViewerText(), 5000); // Wait for the document to be loaded.
expect(page.getDocViewerText()).toContain(textPerUrl[url]);
});
});
@ -41,7 +39,7 @@ describe(browser.baseUrl, () => {
api: 'api list',
'guide/architecture': 'architecture',
'guide/http': 'httpclient',
'guide/quickstart': 'getting started',
'guide/quickstart': 'quickstart',
'guide/security': 'security',
tutorial: 'tutorial',
};
@ -49,8 +47,6 @@ describe(browser.baseUrl, () => {
Object.keys(textPerUrl).forEach(url => {
it(`should show the page at '${url}'`, () => {
page.goTo(url);
browser.wait(() => page.getDocViewerText(), 5000); // Wait for the document to be loaded.
expect(page.getDocViewerText()).toContain(textPerUrl[url]);
});
});
@ -72,8 +68,6 @@ describe(browser.baseUrl, () => {
Object.keys(textPerUrl).forEach(url => {
it(`should show the page at '${url}'`, () => {
page.goTo(url);
browser.wait(() => page.getDocViewerText(), 5000); // Wait for the document to be loaded.
expect(page.getDocViewerText()).toContain(textPerUrl[url]);
});
});

View File

@ -12,15 +12,15 @@
},
"private": true,
"dependencies": {
"@angular/animations": "^7.0.0",
"@angular/common": "^7.0.0",
"@angular/compiler": "^7.0.0",
"@angular/core": "^7.0.0",
"@angular/forms": "^7.0.0",
"@angular/http": "^7.0.0",
"@angular/platform-browser": "^7.0.0",
"@angular/platform-browser-dynamic": "^7.0.0",
"@angular/router": "^7.0.0",
"@angular/animations": "~7.0.0-rc.0",
"@angular/common": "~7.0.0-rc.0",
"@angular/compiler": "~7.0.0-rc.0",
"@angular/core": "~7.0.0-rc.0",
"@angular/forms": "~7.0.0-rc.0",
"@angular/http": "~7.0.0-rc.0",
"@angular/platform-browser": "~7.0.0-rc.0",
"@angular/platform-browser-dynamic": "~7.0.0-rc.0",
"@angular/router": "~7.0.0-rc.0",
"angular-in-memory-web-api": "^0.6.0",
"core-js": "^2.5.4",
"rxjs": "^6.3.0",
@ -28,10 +28,10 @@
"zone.js": "~0.8.26"
},
"devDependencies": {
"@angular-devkit/build-angular": "^0.10.0",
"@angular/cli": "^7.0.0",
"@angular/compiler-cli": "^7.0.0",
"@angular/language-service": "^7.0.0",
"@angular-devkit/build-angular": "~0.9.0-rc.2",
"@angular/cli": "~7.0.0-rc.2",
"@angular/compiler-cli": "~7.0.0-rc.0",
"@angular/language-service": "~7.0.0-rc.0",
"@types/jasmine": "~2.8.8",
"@types/jasminewd2": "~2.0.3",
"@types/node": "~8.9.4",

View File

@ -15,15 +15,15 @@
},
"private": true,
"dependencies": {
"@angular/animations": "^7.0.0",
"@angular/common": "^7.0.0",
"@angular/compiler": "^7.0.0",
"@angular/core": "^7.0.0",
"@angular/forms": "^7.0.0",
"@angular/http": "^7.0.0",
"@angular/platform-browser": "^7.0.0",
"@angular/platform-browser-dynamic": "^7.0.0",
"@angular/router": "^7.0.0",
"@angular/animations": "~7.0.0-rc.0",
"@angular/common": "~7.0.0-rc.0",
"@angular/compiler": "~7.0.0-rc.0",
"@angular/core": "~7.0.0-rc.0",
"@angular/forms": "~7.0.0-rc.0",
"@angular/http": "~7.0.0-rc.0",
"@angular/platform-browser": "~7.0.0-rc.0",
"@angular/platform-browser-dynamic": "~7.0.0-rc.0",
"@angular/router": "~7.0.0-rc.0",
"angular-in-memory-web-api": "^0.6.0",
"core-js": "^2.5.4",
"rxjs": "^6.3.0",
@ -31,10 +31,10 @@
"zone.js": "~0.8.26"
},
"devDependencies": {
"@angular-devkit/build-angular": "^0.10.0",
"@angular/cli": "^7.0.0",
"@angular/compiler-cli": "^7.0.0",
"@angular/language-service": "^7.0.0",
"@angular-devkit/build-angular": "~0.9.0-rc.2",
"@angular/cli": "~7.0.0-rc.2",
"@angular/compiler-cli": "~7.0.0-rc.0",
"@angular/language-service": "~7.0.0-rc.0",
"@types/jasmine": "~2.8.8",
"@types/jasminewd2": "~2.0.3",
"@types/node": "~8.9.4",

View File

@ -16,18 +16,18 @@
},
"private": true,
"dependencies": {
"@angular/animations": "^7.0.0",
"@angular/common": "^7.0.0",
"@angular/compiler": "^7.0.0",
"@angular/core": "^7.0.0",
"@angular/forms": "^7.0.0",
"@angular/http": "^7.0.0",
"@angular/platform-browser": "^7.0.0",
"@angular/platform-browser-dynamic": "^7.0.0",
"@angular/router": "^7.0.0",
"@nguniversal/common": "^7.0.0",
"@nguniversal/express-engine": "^7.0.0",
"@nguniversal/module-map-ngfactory-loader": "^7.0.0",
"@angular/animations": "~7.0.0-rc.0",
"@angular/common": "~7.0.0-rc.0",
"@angular/compiler": "~7.0.0-rc.0",
"@angular/core": "~7.0.0-rc.0",
"@angular/forms": "~7.0.0-rc.0",
"@angular/http": "~7.0.0-rc.0",
"@angular/platform-browser": "~7.0.0-rc.0",
"@angular/platform-browser-dynamic": "~7.0.0-rc.0",
"@angular/router": "~7.0.0-rc.0",
"@nguniversal/common": "^6.1.0",
"@nguniversal/express-engine": "^6.1.0",
"@nguniversal/module-map-ngfactory-loader": "^6.1.0",
"angular-in-memory-web-api": "^0.6.0",
"core-js": "^2.5.4",
"rxjs": "^6.3.0",
@ -35,11 +35,11 @@
"zone.js": "~0.8.26"
},
"devDependencies": {
"@angular-devkit/build-angular": "^0.10.0",
"@angular/cli": "^7.0.0",
"@angular/compiler-cli": "^7.0.0",
"@angular/language-service": "^7.0.0",
"@angular/platform-server": "^7.0.0",
"@angular-devkit/build-angular": "~0.9.0-rc.2",
"@angular/cli": "~7.0.0-rc.2",
"@angular/compiler-cli": "~7.0.0-rc.0",
"@angular/language-service": "~7.0.0-rc.0",
"@angular/platform-server": "~7.0.0-rc.0",
"@types/jasmine": "~2.8.8",
"@types/jasminewd2": "~2.0.3",
"@types/node": "~8.9.4",

View File

@ -18,21 +18,21 @@
"author": "",
"license": "MIT",
"dependencies": {
"@angular/animations": "^7.0.0",
"@angular/common": "^7.0.0",
"@angular/compiler": "^7.0.0",
"@angular/core": "^7.0.0",
"@angular/elements": "^7.0.0",
"@angular/forms": "^7.0.0",
"@angular/http": "^7.0.0",
"@angular/platform-browser": "^7.0.0",
"@angular/platform-browser-dynamic": "^7.0.0",
"@angular/router": "^7.0.0",
"@angular/service-worker": "^7.0.0",
"@angular/upgrade": "^7.0.0",
"@nguniversal/common": "^7.0.0",
"@nguniversal/express-engine": "^7.0.0",
"@nguniversal/module-map-ngfactory-loader": "^7.0.0",
"@angular/animations": "~7.0.0-rc.0",
"@angular/common": "~7.0.0-rc.0",
"@angular/compiler": "~7.0.0-rc.0",
"@angular/core": "~7.0.0-rc.0",
"@angular/elements": "~7.0.0-rc.0",
"@angular/forms": "~7.0.0-rc.0",
"@angular/http": "~7.0.0-rc.0",
"@angular/platform-browser": "~7.0.0-rc.0",
"@angular/platform-browser-dynamic": "~7.0.0-rc.0",
"@angular/router": "~7.0.0-rc.0",
"@angular/service-worker": "~7.0.0-rc.0",
"@angular/upgrade": "~7.0.0-rc.0",
"@nguniversal/common": "^6.1.0",
"@nguniversal/express-engine": "^6.1.0",
"@nguniversal/module-map-ngfactory-loader": "^6.1.0",
"angular-in-memory-web-api": "^0.6.0",
"core-js": "^2.5.4",
"express": "^4.14.1",
@ -42,11 +42,11 @@
"zone.js": "~0.8.26"
},
"devDependencies": {
"@angular-devkit/build-angular": "^0.10.0",
"@angular/cli": "^7.0.0",
"@angular/compiler-cli": "^7.0.0",
"@angular/language-service": "^7.0.0",
"@angular/platform-server": "^7.0.0",
"@angular-devkit/build-angular": "~0.9.0-rc.2",
"@angular/cli": "^7.0.0-rc.2",
"@angular/compiler-cli": "~7.0.0-rc.0",
"@angular/language-service": "~7.0.0-rc.0",
"@angular/platform-server": "~7.0.0-rc.0",
"@types/angular": "^1.6.47",
"@types/angular-animate": "^1.5.10",
"@types/angular-mocks": "^1.6.0",

File diff suppressed because it is too large Load Diff

View File

@ -30,9 +30,7 @@ module.exports = function autoLinkCode(getDocFromAlias) {
return (ast) => {
visit(ast, 'element', (node, ancestors) => {
// Only interested in code elements that are not inside links
if (autoLinkCodeImpl.codeElements.some(elementType =>
is(node, elementType)) &&
(!node.properties.className || node.properties.className.indexOf('no-auto-link') === -1) &&
if (autoLinkCodeImpl.codeElements.some(elementType => is(node, elementType)) &&
ancestors.every(ancestor => !is(ancestor, 'a'))) {
visit(node, 'text', (node, ancestors) => {
// Only interested in text nodes that are not inside links

View File

@ -109,11 +109,4 @@ describe('autoLinkCode post-processor', () => {
processor.$process([doc]);
expect(doc.renderedContent).toEqual('<code-example><a href="a/b/myclass" class="code-anchor">MyClass</a></code-example>');
});
it('should ignore code blocks that are marked with a `no-auto-link` class', () => {
aliasMap.addDoc({ docType: 'class', id: 'MyClass', aliases: ['MyClass'], path: 'a/b/myclass' });
const doc = { docType: 'test-doc', renderedContent: '<code class="no-auto-link">MyClass</code>' };
processor.$process([doc]);
expect(doc.renderedContent).toEqual('<code class="no-auto-link">MyClass</code>');
});
});

View File

@ -47,6 +47,40 @@ module.exports = function generateKeywordsProcessor(log, readFilesProcessor) {
var ignoreWordsMap = convertToMap(wordsToIgnore);
// If the heading contains a name starting with ng, e.g. "ngController", then add the
// name without the ng to the text, e.g. "controller".
function tokenize(text) {
const rawTokens = text.split(/[\s\/]+/mg);
const tokens = [];
rawTokens.forEach(token => {
// Strip off unwanted trivial characters
token = token
.trim()
.replace(/^[_\-"'`({[<$*)}\]>.]+/, '')
.replace(/[_\-"'`({[<$*)}\]>.]+$/, '');
// Ignore tokens that contain weird characters
if (/^[\w.\-]+$/.test(token)) {
tokens.push(token.toLowerCase());
const ngTokenMatch = /^[nN]g([A-Z]\w*)/.exec(token);
if (ngTokenMatch) {
tokens.push(ngTokenMatch[1].toLowerCase());
}
}
});
return tokens;
}
function extractWords(text, words, keywordMap) {
var tokens = tokenize(text);
tokens.forEach(function(token) {
if (!keywordMap[token]) {
words.push(token);
keywordMap[token] = true;
}
});
}
const filteredDocs = docs
// We are not interested in some docTypes
.filter(function(doc) { return !docTypesToIgnore[doc.docType]; })
@ -70,9 +104,13 @@ module.exports = function generateKeywordsProcessor(log, readFilesProcessor) {
if (isString(value) && !propertiesToIgnore[key]) {
extractWords(value, words, keywordMap);
}
});
extractMemberWords(doc, members, membersMap);
// Special case properties that contain content relating to "members"
// of a doc that represents, say, a class or interface
if (key === 'members' || key === 'statics') {
value.forEach(function(member) { extractWords(member.name, members, membersMap); });
}
});
// Extract all the keywords from the headings
if (doc.vFile && doc.vFile.headings) {
@ -128,54 +166,4 @@ function convertToMap(collection) {
const obj = {};
collection.forEach(key => { obj[key] = true; });
return obj;
}
// If the heading contains a name starting with ng, e.g. "ngController", then add the
// name without the ng to the text, e.g. "controller".
function tokenize(text) {
const rawTokens = text.split(/[\s\/]+/mg);
const tokens = [];
rawTokens.forEach(token => {
// Strip off unwanted trivial characters
token = token
.trim()
.replace(/^[_\-"'`({[<$*)}\]>.]+/, '')
.replace(/[_\-"'`({[<$*)}\]>.]+$/, '');
// Ignore tokens that contain weird characters
if (/^[\w.\-]+$/.test(token)) {
tokens.push(token.toLowerCase());
const ngTokenMatch = /^[nN]g([A-Z]\w*)/.exec(token);
if (ngTokenMatch) {
tokens.push(ngTokenMatch[1].toLowerCase());
}
}
});
return tokens;
}
function extractWords(text, words, keywordMap) {
var tokens = tokenize(text);
tokens.forEach(function(token) {
if (!keywordMap[token]) {
words.push(token);
keywordMap[token] = true;
}
});
}
function extractMemberWords(doc, members, membersMap) {
if (!doc) return;
if (doc.members) {
doc.members.forEach(member => extractWords(member.name, members, membersMap));
}
if (doc.statics) {
doc.statics.forEach(member => extractWords(member.name, members, membersMap));
}
if (doc.extendsClauses) {
doc.extendsClauses.forEach(clause => extractMemberWords(clause.doc, members, membersMap));
}
if (doc.implementsClauses) {
doc.implementsClauses.forEach(clause => extractMemberWords(clause.doc, members, membersMap));
}
}

View File

@ -128,46 +128,6 @@ describe('generateKeywords processor', () => {
);
});
it('should add inherited member doc properties to the search terms', () => {
const processor = processorFactory(mockLogger, mockReadFilesProcessor);
const parentClass = {
docType: 'class',
name: 'ParentClass',
members: [
{ name: 'parentMember1' },
],
statics: [
{ name: 'parentMember2' },
],
};
const parentInterface = {
docType: 'interface',
name: 'ParentInterface',
members: [
{ name: 'parentMember3' },
]
};
const childClass = {
docType: 'class',
name: 'Child',
members: [
{ name: 'childMember1' }
],
statics: [
{ name: 'childMember2' }
],
extendsClauses: [{ doc: parentClass }],
implementsClauses: [{ doc: parentInterface }]
};
const docs = [childClass, parentClass, parentInterface];
processor.$process(docs);
const keywordsDoc = docs[docs.length - 1];
expect(keywordsDoc.data[0].members.split(' ').sort().join(' ')).toEqual(
'childmember1 childmember2 parentmember1 parentmember2 parentmember3'
);
});
it('should process terms prefixed with "ng" to include the term stripped of "ng"', () => {
const processor = processorFactory(mockLogger, mockReadFilesProcessor);
const docs = [

View File

@ -12,14 +12,9 @@
{$ doc.shortDescription | marked $}
{$ doc.description | marked $}
{$ cli.renderSyntax(doc) $}
{% if doc.longDescription.length %}
<h2 class="no-anchor">Description</h2>
{$ doc.longDescription | marked $}
{% endif%}
{$ cli.renderArguments(doc.positionalOptions, 2) $}
{$ cli.renderNamedOptions(doc.namedOptions, 2) $}
{$ cli.renderSubcommands(doc) $}
{$ doc.longDescription | marked $}
</div>
</article>

View File

@ -17,8 +17,8 @@
<tbody>
{% for command in doc.commands %}
<tr>
<td><a class="code-anchor" href="{$ command.path $}"><code class="no-auto-link">{$ command.name $}</code></a></td>
<td>{% for alias in command.commandAliases %}<code class="no-auto-link">{$ alias $} </code>{% endfor %}</td>
<td><a class="code-anchor" href="{$ command.path $}"><code>{$ command.name $}</code></a></td>
<td>{% for alias in command.commandAliases %}<code>{$ alias $} </code>{% endfor %}</td>
<td>{$ command.description | marked $}</td>
</tr>
{% endfor %}

View File

@ -1,6 +1,6 @@
{% macro renderSyntax(container, prefix) -%}
{% for name in container.names %}
<code-example hideCopy="true" class="no-box api-heading no-auto-link">ng {%if prefix %}{$ prefix $} {% endif %}<span class="cli-name">{$ name $}</span>
<code-example hideCopy="true" class="no-box api-heading">ng {%if prefix %}{$ prefix $} {% endif %}<span class="cli-name">{$ name $}</span>
{%- for arg in container.positionalOptions %} &lt;<var>{$ arg.name $}</var>&gt;{% endfor %}
{%- if container.namedOptions.length %} [<var>options</var>]{% endif -%}
</code-example>
@ -20,14 +20,14 @@
<tbody>
{% for option in arguments %}
<tr class="cli-option">
<td><code class="no-auto-link">&lt;<var>{$ option.name $}</var>&gt;</code></td>
<td><code>&lt;<var>{$ option.name $}</var>&gt;</code></td>
<td>
{$ option.description | marked $}
{% if option.subcommands.length -%}
<p>This option can take one of the following <a href="#{$ option.name $}-commands">sub-commands</a>:<p>
<ul>
{% for subcommand in option.subcommands %}
<li><code class="no-auto-link"><a class="code-anchor" href="#{$ subcommand.name $}-command">{$ subcommand.name $}</a></code></li>
<li><code><a class="code-anchor" href="#{$ subcommand.name $}-command">{$ subcommand.name $}</a></code></li>
{% endfor %}
</ul>
{%- endif %}
@ -53,11 +53,11 @@
{% for option in options %}
<tr class="cli-option">
<td>
<code class="cli-option-syntax no-auto-link">{$ renderOption(option.name, option.type, option.default, option.enum) $}</code>
<code class="cli-option-syntax">{$ renderOption(option.name, option.type, option.default, option.enum) $}</code>
</td>
<td>
{$ option.description | marked $}
{% if option.default !== undefined %}<p><span class="cli-default">Default:</span> <code class="no-auto-link">{$ option.default $}</code></p>{% endif %}
{% if option.default !== undefined %}<p><span class="cli-default">Default:</span> <code>{$ option.default $}</code></p>{% endif %}
{% if option.aliases.length %}<p><span class="cli-aliases">Aliases:</span> {% for alias in option.aliases %}{$ renderOptionName(alias) $}{% if not loop.last %}, {% endif %}{% endfor %}</p>{% endif %}
</td>
</tr>
@ -92,7 +92,7 @@
{% for command in container.positionalOptions %}{% if command.subcommands.length %}
<h2><a id="{$ command.name $}-commands"></a>{$ command.name | title $} commands</h2>
{% for subcommand in command.subcommands %}
<h3><code class="no-auto-link"><a id="{$ subcommand.name $}-command"></a>{$ subcommand.name $}</code></h3>
<h3><code><a id="{$ subcommand.name $}-command"></a>{$ subcommand.name $}</code></h3>
{% for name in container.names %}
{$ renderSyntax(subcommand, name) $}
{% endfor %}

File diff suppressed because it is too large Load Diff

View File

@ -9,14 +9,21 @@ Bazel.
## Installation
In order to ensure that everyone builds Angular in a _consistent_ way, Bazel
will be installed through NPM and therefore it's not necessary to install Bazel
manually.
Install Bazel from the distribution, see [install] instructions.
On Mac, just `brew install bazel`.
The binaries for Bazel will be provided by the [`@bazel/bazel`](https://github.com/bazelbuild/rules_nodejs/tree/master/packages)
NPM package and its platform-specific dependencies.
Bazel will install a hermetic version of Node, npm, and Yarn when
you run the first build.
You can access Bazel with the `yarn bazel` command
[install]: https://bazel.build/versions/master/docs/install.html
### Installation of ibazel
Install interactive bazel runner / fs watcher via:
```
yarn global add @bazel/ibazel
```
## Configuration
@ -26,6 +33,12 @@ use to execute build steps, from `build_bazel_rules_typescript`.
The sources on [GitHub] are published from Google's internal
repository (google3).
That repository defines dependencies on specific versions of
all the tools. You can run the tools Bazel installed, for
example rather than `yarn install` (which depends on whatever
version you have installed on your machine), you can
`bazel run @nodejs//:yarn`.
Bazel accepts a lot of options. We check in some options in the
`.bazelrc` file. See the [bazelrc doc]. For example, if you don't
want Bazel to create several symlinks in your project directory
@ -37,8 +50,8 @@ want Bazel to create several symlinks in your project directory
## Building Angular
- Build a package: `yarn bazel build packages/core`
- Build all packages: `yarn bazel build packages/...`
- Build a package: `bazel build packages/core`
- Build all packages: `bazel build packages/...`
You can use [ibazel] to get a "watch mode" that continuously
keeps the outputs up-to-date as you save sources. Note this is
@ -48,9 +61,9 @@ new as of May 2017 and not very stable yet.
## Testing Angular
- Test package in node: `yarn bazel test packages/core/test:test`
- Test package in karma: `yarn bazel test packages/core/test:test_web`
- Test all packages: `yarn bazel test packages/...`
- Test package in node: `bazel test packages/core/test:test`
- Test package in karma: `bazel test packages/core/test:test_web`
- Test all packages: `bazel test packages/...`
You can use [ibazel] to get a "watch mode" that continuously
keeps the outputs up-to-date as you save sources.
@ -59,20 +72,19 @@ keeps the outputs up-to-date as you save sources.
If you're experiencing problems with seemingly unrelated tests failing, it may be because you're not using the proper flags with your Bazel test runs in Angular.
See also: [`//.bazelrc`](https://github.com/angular/angular/blob/master/.bazelrc) where `--define=compile=legacy` is defined as default.
See also: [`//.bazelrc`](https://github.com/angular/angular/blob/master/.bazelrc) where `--define=ivy=false` is defined as default.
- `--config=debug`: build and launch in debug mode (see [debugging](#debugging) instructions below)
- `--test_arg=--node_options=--inspect=9228`: change the inspector port.
- `--define=compile=<option>` Controls if ivy or legacy mode is enabled. This is done by generating the [`src/ivy_switch.ts`](https://github.com/angular/angular/blob/master/packages/core/src/ivy_switch.ts) file from [`ivy_switch_legacy.ts`](https://github.com/angular/angular/blob/master/packages/core/src/ivy_switch_legacy.ts) (default), [`ivy_switch_jit.ts`](https://github.com/angular/angular/blob/master/packages/core/src/ivy_switch_jit.ts), or [`ivy_switch_local.ts`](https://github.com/angular/angular/blob/master/packages/core/src/ivy_switch_local.ts).
- `--define=compile=<option>` Controls if ivy or legacy mode is enabled. This switches which compiler is used (ngc, ngtsc, or a tsc pass-through mode).
- `legacy`: (default behavior) compile against View Engine, e.g. `--define=compile=legacy`
- `jit`: Compile in ivy JIT mode, e.g. `--define=compile=jit`
- `aot`: Compile in ivy AOT move, e.g. `--define=compile=aot`
- `--test_tag_filters=<tag>`: filter tests down to tags defined in the `tag` config of your rules in any given `BUILD.bazel`.
- `no-ivy-aot`: Useful for excluding build and test targets that are not meant to be executed in Ivy AOT mode (`--define=compile=aot`).
- `no-ivy-jit`: Useful for excluding build and test targets that are not meant to be executed in Ivy JIT mode (`--define=compile=jit`).
- `ivy-only`: Useful for excluding all Ivy build and tests targets with `--define=compile=legacy`.
- `fixme-ivy-aot`: Useful for including/excluding build and test targets that are currently broken in Ivy AOT mode (`--define=compile=aot`).
- `fixme-ivy-jit`: Useful for including/excluding build and test targets that are currently broken in Ivy JIT mode (`--define=compile=jit`).
- `local`: Compile in ivy AOT move, e.g. `--define=compile=local`
- `--test_tag_filters=<tag>`: filter tests down to tags defined in the `tag` config
of your rules in any given `BUILD.bazel`.
- `ivy-jit`: This flag should be set for tests that should be excuted with ivy JIT, e.g. `--test_tag_filters=ivy-jit`. For this, you may have to include `--define=compile=jit`.
- `ivy-local`: Only run tests that have to do with ivy AOT. For this, you may have to include `--define=compile=local`, e.g. `--test_tag_filters=ivy-local`..
- `ivy-only`: Only run ivy related tests, e.g. `--test_tag_filters=ivy-only`.
### Debugging a Node Test
@ -80,7 +92,7 @@ See also: [`//.bazelrc`](https://github.com/angular/angular/blob/master/.bazelrc
- Open chrome at: [chrome://inspect](chrome://inspect)
- Click on `Open dedicated DevTools for Node` to launch a debugger.
- Run test: `yarn bazel test packages/core/test:test --config=debug`
- Run test: `bazel test packages/core/test:test --config=debug`
The process should automatically connect to the debugger. For additional info and testing options, see the [nodejs_test documentation](https://bazelbuild.github.io/rules_nodejs/node/node.html#nodejs_test).
@ -117,7 +129,7 @@ First time setup:
**Setting breakpoints directly in your code files may not work in VSCode**. This is because the files you're actually debugging are built files that exist in a `./private/...` folder.
The easiest way to debug a test for now is to add a `debugger` statement in the code
and launch the bazel corresponding test (`yarn bazel test <target> --config=debug`).
and launch the bazel corresponding test (`bazel test <target> --config=debug`).
Bazel will wait on a connection. Go to the debug view (by clicking on the sidebar or
Apple+Shift+D on Mac) and click on the green play icon next to the configuration name
@ -125,7 +137,7 @@ Apple+Shift+D on Mac) and click on the green play icon next to the configuration
### Debugging a Karma Test
- Run test: `yarn bazel run packages/core/test:test_web`
- Run test: `bazel run packages/core/test:test_web`
- Open chrome at: [http://localhost:9876/debug.html](http://localhost:9876/debug.html)
- Open chrome inspector
@ -138,7 +150,7 @@ open $(bazel info output_base)/external
See subcommands that bazel executes (helpful for debugging):
```sh
yarn bazel build //packages/core:package -s
bazel build //packages/core:package -s
```
To debug nodejs_binary executable paths uncomment `find . -name rollup 1>&2` (~ line 96) in
@ -155,7 +167,7 @@ In our repo, here is how it's configured:
1) In `tools/bazel_stamp_vars.sh` we run the `git` commands to generate our versioning info.
1) In `.bazelrc` we register this script as the value for the `workspace_status_command` flag. Bazel will run the script when it needs to stamp a binary.
Note that Bazel has a `--stamp` argument to `yarn bazel build`, but this has no effect since our stamping takes place in Skylark rules. See https://github.com/bazelbuild/bazel/issues/1054
Note that Bazel has a `--stamp` argument to `bazel build`, but this has no effect since our stamping takes place in Skylark rules. See https://github.com/bazelbuild/bazel/issues/1054
## Remote cache
@ -193,7 +205,7 @@ See [bazelbuild/intellij#246](https://github.com/bazelbuild/intellij/issues/246)
If you see the following error:
```
$ yarn bazel build packages/...
$ bazel build packages/...
ERROR: /private/var/tmp/[...]/external/local_config_cc/BUILD:50:5: in apple_cc_toolchain rule @local_config_cc//:cc-compiler-darwin_x86_64: Xcode version must be specified to use an Apple CROSSTOOL
ERROR: Analysis of target '//packages/core/test/render3:render3' failed; build aborted: Analysis of target '@local_config_cc//:cc-compiler-darwin_x86_64' failed; build aborted
```
@ -215,7 +227,7 @@ If VSCode is not the root cause, you might try:
bazel clean --expunge
sudo xcode-select -s /Applications/Xcode.app/Contents/Developer
sudo xcodebuild -license
yarn bazel build //packages/core # Run a build outside VSCode to pre-build the xcode; then safe to run VSCode
bazel build //packages/core # Run a build outside VSCode to pre-build the xcode; then safe to run VSCode
```
Source: https://stackoverflow.com/questions/45276830/xcode-version-must-be-specified-to-use-an-apple-crosstool

View File

@ -5,9 +5,6 @@
"license": "MIT",
"dependencies": {
},
"devDependencies": {
"@bazel/bazel": "file:../../node_modules/@bazel/bazel"
},
"scripts": {
"//": "deps are listed in src/package.json which is used by yarn_install",
"//": "this package.json file is only here so that `yarn test` can be called by /integration/run_tests.sh",

View File

@ -2,24 +2,3 @@
# yarn lockfile v1
"@bazel/bazel-darwin_x64@0.18.0":
version "0.18.0"
resolved "https://registry.yarnpkg.com/@bazel/bazel-darwin_x64/-/bazel-darwin_x64-0.18.0.tgz#bab437605a702279d42f59caa4741bb327eb7dbc"
integrity sha512-um2OzgLL2Gd/W6joOpvrSTcqpnupliPNpwe/uE7sB0huBSJ/4Im0w2IlCTI6C7OfgMcbpUj4YxgUa9T6u6WY6w==
"@bazel/bazel-linux_x64@0.18.0":
version "0.18.0"
resolved "https://registry.yarnpkg.com/@bazel/bazel-linux_x64/-/bazel-linux_x64-0.18.0.tgz#0c02b2404ec95c180e17615cc7079ee07df48a69"
integrity sha512-Rq8X8bL6SgQvbOHnfPhSgF6hp+f6Fbt2w6pRmBlFvV1J+CeUyrSrrRXfnnO1bjIuq05Ur3mV8ULA0qK6rtA5lQ==
"@bazel/bazel-win32_x64@0.18.0":
version "0.18.0"
resolved "https://registry.yarnpkg.com/@bazel/bazel-win32_x64/-/bazel-win32_x64-0.18.0.tgz#aa4575fb00066dcf59a6d464971774dea6a0bafd"
integrity sha512-U2TbfK8B7dc3JqXSFwj2oXCQrxEaSzCCUkAHjAOIGOKzx/HLKIKs+NJj9IQkLLr7BsMU+Qqzo8aqo11E+Vs+aA==
"@bazel/bazel@file:../../node_modules/@bazel/bazel":
version "0.18.0"
optionalDependencies:
"@bazel/bazel-darwin_x64" "0.18.0"
"@bazel/bazel-linux_x64" "0.18.0"
"@bazel/bazel-win32_x64" "0.18.0"

View File

@ -17,10 +17,10 @@ ivy-ngcc
ls node_modules/@angular/common | grep __modified_by_ngcc_for_esm2015
if [[ $? != 0 ]]; then exit 1; fi
# Did it replace the NGCC_PRE markers correctly?
grep "= R3_COMPILE_COMPONENT__POST_NGCC__" node_modules/@angular/core/fesm2015/core.js
# Did it replace the PRE_R3 markers correctly?
grep "= SWITCH_COMPILE_COMPONENT__POST_R3__" node_modules/@angular/core/fesm2015/core.js
if [[ $? != 0 ]]; then exit 1; fi
grep "= R3_COMPILE_COMPONENT__POST_NGCC__" node_modules/@angular/core/fesm5/core.js
grep "= SWITCH_COMPILE_COMPONENT__POST_R3__" node_modules/@angular/core/fesm5/core.js
if [[ $? != 0 ]]; then exit 1; fi
# Did it compile @angular/core/ApplicationModule correctly?

View File

@ -56,15 +56,6 @@ describe('largetable benchmark perf', () => {
}).then(done, done.fail);
});
it('should run for render3', done => {
runTableBenchmark({
id: `largeTable.render3.${worker.id}`,
url: 'all/benchmarks/src/largetable/render3/index.html',
ignoreBrowserSynchronization: true,
worker: worker
}).then(done, done.fail);
});
it('should run for iv', done => {
runTableBenchmark({
id: `largeTable.iv.${worker.id}`,

View File

@ -25,13 +25,6 @@ describe('largetable benchmark spec', () => {
});
});
it('should work for render3', () => {
testTableBenchmark({
url: 'all/benchmarks/src/largetable/render3/index.html',
ignoreBrowserSynchronization: true,
});
});
it('should work for iv', () => {
testTableBenchmark({
url: 'all/benchmarks/src/largetable/iv/index.html',

View File

@ -49,12 +49,6 @@ export const Benchmarks: Benchmark[] = [
url: 'all/benchmarks/src/tree/ng2_switch/index.html',
buttons: CreateDestroyButtons,
},
{
id: `deepTree.ng2.render3`,
url: 'all/benchmarks/src/tree/render3/index.html',
buttons: CreateDestroyDetectChangesButtons,
ignoreBrowserSynchronization: true,
},
{
id: `deepTree.ng2.render3_function`,
url: 'all/benchmarks/src/tree/render3_function/index.html',

View File

@ -8,6 +8,7 @@
import {$} from 'protractor';
import {openBrowser} from '../../../e2e_util/e2e_util';
import {runBenchmark, verifyNoBrowserErrors} from '../../../e2e_util/perf_util';
interface Worker {
@ -39,9 +40,23 @@ describe('largetable benchmark perf', () => {
afterEach(verifyNoBrowserErrors);
it('should render the table for render3', () => {
openBrowser({
url: '',
ignoreBrowserSynchronization: true,
params: [{name: 'cols', value: 5}, {name: 'rows', value: 5}],
});
$('#createDom').click();
expect($('#root').getText()).toContain('0/0');
$('#createDom').click();
expect($('#root').getText()).toContain('A/A');
$('#destroyDom').click();
expect($('#root').getText() as any).toEqual('');
});
[CreateOnlyWorker, CreateAndDestroyWorker, UpdateWorker].forEach((worker) => {
describe(worker.id, () => {
it('should run for render3', done => {
it('should run benchmark for render3', done => {
runTableBenchmark({
id: `largeTable.render3.${worker.id}`,
url: 'index.html',

View File

@ -1,10 +1,10 @@
package(default_visibility = ["//visibility:public"])
load("//tools:defaults.bzl", "ng_rollup_bundle", "ts_library")
load("//tools:defaults.bzl", "ng_module", "ng_rollup_bundle")
load("//packages/bazel:index.bzl", "protractor_web_test")
load("@build_bazel_rules_typescript//:defs.bzl", "ts_devserver")
ts_library(
ng_module(
name = "largetable_lib",
srcs = glob(
[
@ -12,18 +12,20 @@ ts_library(
],
exclude = ["protractor.on-prepare.ts"],
),
tags = ["ivy-only"],
deps = [
"//modules/benchmarks/src:util_lib",
"//modules/benchmarks/src/largetable:util_lib",
"//packages:types",
"//packages/common",
"//packages/core",
"@ngdeps//reflect-metadata",
],
)
ng_rollup_bundle(
name = "bundle",
entry_point = "modules/benchmarks/src/largetable/render3/index.js",
tags = ["ivy-only"],
deps = [
":largetable_lib",
],
@ -44,6 +46,7 @@ ts_devserver(
"index.html",
":favicon",
],
tags = ["ivy-only"],
)
protractor_web_test(
@ -57,13 +60,9 @@ protractor_web_test(
"@ngdeps//reflect-metadata",
"@ngdeps//yargs",
],
on_prepare = ":protractor.on-prepare.js",
on_prepare = ":protractor.on_prepare.js",
server = ":devserver",
tags = [
"fixme-ivy-aot",
"fixme-ivy-jit",
"ivy-only",
],
tags = ["ivy-only"],
deps = [
"//modules/benchmarks/src/largetable:perf_lib",
],

View File

@ -28,15 +28,9 @@
<script>
// TODO(mlaval): remove once we have a proper solution
ngDevMode = false;
var isBazel = location.pathname.indexOf('/all/') !== 0;
// isBazel needed while 'scripts/ci/test-e2e.sh test.e2e.protractor-e2e' is run
// on Travis
// TODO: port remaining protractor e2e tests to bazel protractor_web_test_suite rule
var bazelBundle = document.location.search.endsWith('debug') ? 'bundle.min_debug.js' : 'bundle.min.js';
var mainUrl = window.location.search.split(/[?&]main=([^&]+)/)[1]
|| '../../bootstrap_ng2.js';
document.write('<script src="' + (isBazel ? bazelBundle : mainUrl) + '">\u003c/script>');
document.write('<script src="' + bazelBundle + '">\u003c/script>');
</script>
</body>
</html>
</html>

View File

@ -5,7 +5,7 @@
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import 'reflect-metadata';
import {ɵrenderComponent as renderComponent} from '@angular/core';
import {bindAction, profile} from '../../util';

View File

@ -1,21 +0,0 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
const protractorUtils = require('@angular/bazel/protractor-utils');
const protractor = require('protractor');
module.exports = function(config) {
return protractorUtils.runServer(config.workspace, config.server, '-port', [])
.then(serverSpec => {
const serverUrl = `http://localhost:${serverSpec.port}`;
// Since the browser restarts in this benchmark we need to set both the browser.baseUrl
// for the first test and the protractor config.baseUrl for the subsequent tests
protractor.browser.baseUrl = serverUrl;
return protractor.browser.getProcessedConfig().then((config) => config.baseUrl = serverUrl);
});
};

View File

@ -0,0 +1,22 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
const protractorUtils = require('@angular/bazel/protractor-utils');
const protractor = require('protractor');
module.exports = async function(config) {
const serverSpec = await protractorUtils.runServer(config.workspace, config.server, '-port', []);
const serverUrl = `http://localhost:${serverSpec.port}`;
// Since the browser restarts in this benchmark we need to set both the browser.baseUrl
// for the first test and the protractor config.baseUrl for the subsequent tests
protractor.browser.baseUrl = serverUrl;
const processedConfig = await protractor.browser.getProcessedConfig();
return processedConfig.baseUrl = serverUrl;
};

View File

@ -6,76 +6,39 @@
* found in the LICENSE file at https://angular.io/license
*/
import {ɵRenderFlags, ɵbind, ɵcontainer, ɵcontainerRefreshEnd, ɵcontainerRefreshStart, ɵdefineComponent, ɵdetectChanges, ɵelementEnd, ɵelementStart, ɵelementStyleProp, ɵelementStyling, ɵembeddedViewEnd, ɵembeddedViewStart, ɵtext, ɵtextBinding as ɵtextBinding} from '@angular/core';
import {ComponentDef} from '@angular/core/src/render3/interfaces/definition';
import {CommonModule} from '@angular/common';
import {Component, Input, NgModule, ɵdetectChanges} from '@angular/core';
import {TableCell, buildTable, emptyTable} from '../util';
const c0 = ['background-color'];
@Component({
selector: 'largetable',
template: `
<table>
<tbody>
<tr *ngFor="let row of data; trackBy: trackByIndex">
<td *ngFor="let cell of row; trackBy: trackByIndex" [style.background-color]="getColor(cell.row)">
{{cell.value}}
</td>
</tr>
</tbody>
</table>
`,
})
export class LargeTableComponent {
@Input()
data: TableCell[][] = emptyTable;
/** @nocollapse */
static ngComponentDef: ComponentDef<LargeTableComponent> = ɵdefineComponent({
type: LargeTableComponent,
selectors: [['largetable']],
consts: 3,
vars: 0,
template: function(rf: ɵRenderFlags, ctx: LargeTableComponent) {
if (rf & ɵRenderFlags.Create) {
ɵelementStart(0, 'table');
{
ɵelementStart(1, 'tbody');
{ ɵcontainer(2); }
ɵelementEnd();
}
ɵelementEnd();
}
if (rf & ɵRenderFlags.Update) {
ɵcontainerRefreshStart(2);
{
for (let row of ctx.data) {
let rf1 = ɵembeddedViewStart(1, 2, 0);
{
if (rf1 & ɵRenderFlags.Create) {
ɵelementStart(0, 'tr');
ɵcontainer(1);
ɵelementEnd();
}
if (rf1 & ɵRenderFlags.Update) {
ɵcontainerRefreshStart(1);
{
for (let cell of row) {
let rf2 = ɵembeddedViewStart(2, 2, 1);
{
if (rf2 & ɵRenderFlags.Create) {
ɵelementStart(0, 'td');
ɵelementStyling(null, c0);
{ ɵtext(1); }
ɵelementEnd();
}
if (rf2 & ɵRenderFlags.Update) {
ɵelementStyleProp(0, 0, null, cell.row % 2 ? '' : 'grey');
ɵtextBinding(1, ɵbind(cell.value));
}
}
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
}
}
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
}
},
factory: () => new LargeTableComponent(),
inputs: {data: 'data'}
});
trackByIndex(index: number, item: any) { return index; }
getColor(row: number) { return row % 2 ? '' : 'grey'; }
}
@NgModule({declarations: [LargeTableComponent], imports: [CommonModule]})
class TableModule {
}
export function destroyDom(component: LargeTableComponent) {
component.data = emptyTable;
ɵdetectChanges(component);

View File

@ -13,3 +13,16 @@ ts_library(
"//packages/core",
],
)
ts_library(
name = "perf_lib",
testonly = 1,
srcs = [
"tree_perf.spec.ts",
],
deps = [
"//modules/e2e_util:lib",
"//packages:types",
"@ngdeps//protractor",
],
)

View File

@ -5,17 +5,18 @@ load("//packages/bazel:index.bzl", "protractor_web_test")
load("@build_bazel_rules_typescript//:defs.bzl", "ts_devserver")
ng_module(
name = "render3_lib",
name = "tree_lib",
srcs = glob(
[
"**/*.ts",
],
),
tags = ["ivy-only"],
deps = [
"//modules/benchmarks/src/tree:util_lib",
"//packages:types",
"//packages/common",
"//packages/core",
"@ngdeps//reflect-metadata",
],
)
@ -55,14 +56,12 @@ protractor_web_test(
],
on_prepare = ":protractor.on_prepare.js",
server = ":devserver",
tags = [
"fixme-ivy-aot",
"fixme-ivy-jit",
"ivy-only",
],
tags = ["ivy-only"],
deps = [
"//modules/benchmarks/src/tree:perf_lib",
"@ngdeps//node-uuid",
"@ngdeps//protractor",
"@ngdeps//reflect-metadata",
"@ngdeps//yargs",
],
)

View File

@ -30,9 +30,8 @@
<script>
// TODO(mlaval): remove once we have a proper solution
ngDevMode = false;
var mainUrl = window.location.search.split(/[?&]main=([^&]+)/)[1]
|| '../../bootstrap_ng2.js';
document.write('<script src="' + mainUrl + '">\u003c/script>');
var bazelBundle = document.location.search.endsWith('debug') ? 'bundle.min_debug.js' : 'bundle.min.js';
document.write('<script src="' + bazelBundle + '">\u003c/script>');
</script>
</body>
</html>

View File

@ -6,6 +6,7 @@
* found in the LICENSE file at https://angular.io/license
*/
import 'reflect-metadata';
import {ɵrenderComponent as renderComponent} from '@angular/core';
import {bindAction, profile} from '../../util';
import {TreeComponent, createDom, destroyDom, detectChanges} from './tree';
@ -27,3 +28,5 @@ export function main() {
profile(() => createDom(component), () => destroyDom(component), 'create'));
}
}
main();

View File

@ -0,0 +1,22 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
const protractorUtils = require('@angular/bazel/protractor-utils');
const protractor = require('protractor');
module.exports = async function(config) {
const serverSpec = await protractorUtils.runServer(config.workspace, config.server, '-port', []);
const serverUrl = `http://localhost:${serverSpec.port}`;
// Since the browser restarts in this benchmark we need to set both the browser.baseUrl
// for the first test and the protractor config.baseUrl for the subsequent tests
protractor.browser.baseUrl = serverUrl;
const processedConfig = await protractor.browser.getProcessedConfig();
return processedConfig.baseUrl = serverUrl;
};

View File

@ -6,7 +6,8 @@
* found in the LICENSE file at https://angular.io/license
*/
import {ɵRenderFlags, ɵbind, ɵcontainer, ɵcontainerRefreshEnd, ɵcontainerRefreshStart, ɵdefineComponent, ɵdetectChanges, ɵelementEnd, ɵelementProperty, ɵelementStart, ɵelementStyleProp, ɵelementStyling as s, ɵembeddedViewEnd, ɵembeddedViewStart, ɵinterpolation1, ɵtext, ɵtextBinding as ɵtextBinding} from '@angular/core';
import {CommonModule} from '@angular/common';
import {Component, NgModule, ɵdetectChanges} from '@angular/core';
import {TreeNode, buildTree, emptyTree} from '../util';
@ -30,122 +31,17 @@ export function detectChanges(component: TreeComponent) {
numberOfChecksEl.textContent = `${detectChangesRuns}`;
}
const c0 = ['background-color'];
@Component({
selector: 'tree',
inputs: ['data'],
template:
`<span [style.backgroundColor]="bgColor"> {{data.value}} </span><tree *ngIf='data.right != null' [data]='data.right'></tree><tree *ngIf='data.left != null' [data]='data.left'></tree>`
})
export class TreeComponent {
data: TreeNode = emptyTree;
/** @nocollapse */
static ngComponentDef = ɵdefineComponent({
type: TreeComponent,
selectors: [['tree']],
consts: 4,
vars: 1,
template: function(rf: ɵRenderFlags, ctx: TreeComponent) {
if (rf & ɵRenderFlags.Create) {
ɵelementStart(0, 'span');
s(null, c0);
{ ɵtext(1); }
ɵelementEnd();
ɵcontainer(2);
ɵcontainer(3);
}
if (rf & ɵRenderFlags.Update) {
ɵelementStyleProp(0, 0, ctx.data.depth % 2 ? '' : 'grey');
ɵtextBinding(1, ɵinterpolation1(' ', ctx.data.value, ' '));
ɵcontainerRefreshStart(2);
{
if (ctx.data.left != null) {
let rf0 = ɵembeddedViewStart(0, 1, 1);
{
if (rf0 & ɵRenderFlags.Create) {
ɵelementStart(0, 'tree');
ɵelementEnd();
}
if (rf0 & ɵRenderFlags.Update) {
ɵelementProperty(0, 'data', ɵbind(ctx.data.left));
}
}
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
ɵcontainerRefreshStart(3);
{
if (ctx.data.right != null) {
let rf0 = ɵembeddedViewStart(0, 1, 1);
{
if (rf0 & ɵRenderFlags.Create) {
ɵelementStart(0, 'tree');
ɵelementEnd();
}
if (rf0 & ɵRenderFlags.Update) {
ɵelementProperty(0, 'data', ɵbind(ctx.data.right));
}
}
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
}
},
factory: () => new TreeComponent,
inputs: {data: 'data'},
directives: () => [TreeComponent]
});
data: any = emptyTree;
get bgColor() { return this.data.depth % 2 ? '' : 'grey'; }
}
export class TreeFunction {
data: TreeNode = emptyTree;
/** @nocollapse */
static ngComponentDef = ɵdefineComponent({
type: TreeFunction,
selectors: [['tree']],
consts: 5,
vars: 1,
template: function(rf: ɵRenderFlags, ctx: TreeFunction) {
// bit of a hack
TreeTpl(rf, ctx.data);
},
factory: () => new TreeFunction,
inputs: {data: 'data'}
});
}
const c1 = ['background-color'];
export function TreeTpl(rf: ɵRenderFlags, ctx: TreeNode) {
if (rf & ɵRenderFlags.Create) {
ɵelementStart(0, 'tree');
{
ɵelementStart(1, 'span');
s(null, c1);
{ ɵtext(2); }
ɵelementEnd();
ɵcontainer(3);
ɵcontainer(4);
}
ɵelementEnd();
}
if (rf & ɵRenderFlags.Update) {
ɵelementStyleProp(1, 0, ctx.depth % 2 ? '' : 'grey');
ɵtextBinding(2, ɵinterpolation1(' ', ctx.value, ' '));
ɵcontainerRefreshStart(3);
{
if (ctx.left != null) {
let rf0 = ɵembeddedViewStart(0, 5, 1);
{ TreeTpl(rf0, ctx.left); }
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
ɵcontainerRefreshStart(4);
{
if (ctx.right != null) {
let rf0 = ɵembeddedViewStart(0, 5, 1);
{ TreeTpl(rf0, ctx.right); }
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
}
@NgModule({declarations: [TreeComponent], imports: [CommonModule]})
export class TreeModule {
}

View File

@ -11,7 +11,7 @@ ng_module(
),
deps = [
"//modules/benchmarks/src/tree:util_lib",
"//modules/benchmarks/src/tree/render3:render3_lib",
"//modules/benchmarks/src/tree/render3:tree_lib",
"//packages:types",
"//packages/core",
"@rxjs",

View File

@ -6,9 +6,11 @@
* found in the LICENSE file at https://angular.io/license
*/
import {ɵrenderComponent as renderComponent} from '@angular/core';
import {ɵRenderFlags, ɵcontainer, ɵcontainerRefreshEnd, ɵcontainerRefreshStart, ɵdefineComponent, ɵelementEnd, ɵelementStart, ɵelementStyleProp, ɵelementStyling, ɵembeddedViewEnd, ɵembeddedViewStart, ɵinterpolation1, ɵrenderComponent as renderComponent, ɵtext, ɵtextBinding} from '@angular/core';
import {bindAction, profile} from '../../util';
import {TreeFunction, createDom, destroyDom, detectChanges} from '../render3/tree';
import {createDom, destroyDom, detectChanges} from '../render3/tree';
import {TreeNode, emptyTree} from '../util';
function noop() {}
@ -16,14 +18,71 @@ export function main() {
let component: TreeFunction;
if (typeof window !== 'undefined') {
component = renderComponent(TreeFunction);
bindAction('#createDom', () => createDom(component));
bindAction('#destroyDom', () => destroyDom(component));
bindAction('#detectChanges', () => detectChanges(component));
bindAction('#createDom', () => createDom(component as any));
bindAction('#destroyDom', () => destroyDom(component as any));
bindAction('#detectChanges', () => detectChanges(component as any));
bindAction(
'#detectChangesProfile', profile(() => detectChanges(component), noop, 'detectChanges'));
bindAction('#updateDomProfile', profile(() => createDom(component), noop, 'update'));
'#detectChangesProfile',
profile(() => detectChanges(component as any), noop, 'detectChanges'));
bindAction('#updateDomProfile', profile(() => createDom(component as any), noop, 'update'));
bindAction(
'#createDomProfile',
profile(() => createDom(component), () => destroyDom(component), 'create'));
profile(() => createDom(component as any), () => destroyDom(component as any), 'create'));
}
}
export class TreeFunction {
data: TreeNode = emptyTree;
/** @nocollapse */
static ngComponentDef = ɵdefineComponent({
type: TreeFunction,
selectors: [['tree']],
consts: 5,
vars: 1,
template: function(rf: ɵRenderFlags, ctx: TreeFunction) {
// bit of a hack
TreeTpl(rf, ctx.data);
},
factory: () => new TreeFunction,
inputs: {data: 'data'}
});
}
const c1 = ['background-color'];
export function TreeTpl(rf: ɵRenderFlags, ctx: TreeNode) {
if (rf & ɵRenderFlags.Create) {
ɵelementStart(0, 'tree');
{
ɵelementStart(1, 'span');
ɵelementStyling(null, c1);
{ ɵtext(2); }
ɵelementEnd();
ɵcontainer(3);
ɵcontainer(4);
}
ɵelementEnd();
}
if (rf & ɵRenderFlags.Update) {
ɵelementStyleProp(1, 0, ctx.depth % 2 ? '' : 'grey');
ɵtextBinding(2, ɵinterpolation1(' ', ctx.value, ' '));
ɵcontainerRefreshStart(3);
{
if (ctx.left != null) {
let rf0 = ɵembeddedViewStart(0, 5, 1);
{ TreeTpl(rf0, ctx.left); }
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
ɵcontainerRefreshStart(4);
{
if (ctx.right != null) {
let rf0 = ɵembeddedViewStart(0, 5, 1);
{ TreeTpl(rf0, ctx.right); }
ɵembeddedViewEnd();
}
}
ɵcontainerRefreshEnd();
}
}

View File

@ -0,0 +1,101 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import {$, browser} from 'protractor';
import {openBrowser} from '../../../e2e_util/e2e_util';
import {runBenchmark} from '../../../e2e_util/perf_util';
describe('benchmark render', () => {
it('should work for createDestroy', () => {
openTreeBenchmark();
$('#createDom').click();
expect($('#root').getText()).toContain('0');
$('#destroyDom').click();
expect($('#root').getText() as any).toEqual('');
});
it('should work for update', () => {
openTreeBenchmark();
$('#createDom').click();
$('#createDom').click();
expect($('#root').getText()).toContain('A');
});
it('should work for detectChanges', () => {
openTreeBenchmark();
$('#detectChanges').click();
expect($('#numberOfChecks').getText()).toContain('10');
});
});
describe('benchmarks', () => {
it('should work for createOnly', done => {
runTreeBenchmark({
id: 'createOnly',
prepare: () => $('#destroyDom').click(),
work: () => $('#createDom').click()
}).then(done, done.fail);
});
it('should work for destroy', done => {
runTreeBenchmark({
id: 'createOnly',
prepare: () => $('#createDom').click(),
work: () => $('#destroyDom').click()
}).then(done, done.fail);
});
it('should work for createDestroy', done => {
runTreeBenchmark({
id: 'createDestroy',
work: () => {
$('#destroyDom').click();
$('#createDom').click();
}
}).then(done, done.fail);
});
it('should work for update', done => {
runTreeBenchmark({id: 'update', work: () => $('#createDom').click()}).then(done, done.fail);
});
it('should work for detectChanges', done => {
runTreeBenchmark({
id: 'detectChanges',
work: () => $('#detectChanges').click(),
setup: () => $('#destroyDom').click()
}).then(done, done.fail);
});
});
function runTreeBenchmark({id, prepare, setup, work}:
{id: string; prepare ? () : void; setup ? () : void; work(): void;}) {
browser.rootEl = '#root';
return runBenchmark({
id: id,
url: '',
ignoreBrowserSynchronization: true,
params: [{name: 'depth', value: 11}],
work: work,
prepare: prepare,
setup: setup
});
}
function openTreeBenchmark() {
browser.rootEl = '#root';
openBrowser({
url: '',
ignoreBrowserSynchronization: true,
params: [{name: 'depth', value: 4}],
});
}

View File

@ -40,6 +40,7 @@ export function runBenchmark(config: {
if (config.setup) {
config.setup();
}
if (!cmdArgs) readCommandLine();
const description: {[key: string]: any} = {'bundles': cmdArgs.bundles};
config.params.forEach((param) => { description[param.name] = param.value; });
return runner.sample({

View File

@ -1,6 +1,6 @@
{
"name": "angular-srcs",
"version": "7.0.2",
"version": "7.1.0-beta.0",
"private": true,
"branchPattern": "2.0.*",
"description": "Angular - a web framework for modern web apps",
@ -26,28 +26,43 @@
"update-webdriver": "webdriver-manager update --gecko false $CHROMEDRIVER_VERSION_ARG",
"check-env": "gulp check-env",
"commitmsg": "node ./scripts/git/commit-msg.js",
"test-ivy-jit": "bazel test --define=compile=jit --build_tag_filters=-no-ivy-jit,-fixme-ivy-jit --test_tag_filters=-no-ivy-jit,-fixme-ivy-jit",
"test-fixme-ivy-jit": "bazel test --define=compile=jit --build_tag_filters=-no-ivy-jit --test_tag_filters=-no-ivy-jit",
"test-ivy-aot": "bazel test --define=compile=aot --build_tag_filters=-no-ivy-aot,-fixme-ivy-aot --test_tag_filters=-no-ivy-aot,-fixme-ivy-aot",
"test-fixme-ivy-aot": "bazel test --define=compile=aot --build_tag_filters=-no-ivy-aot --test_tag_filters=-no-ivy-aot",
"bazel": "bazel"
"test-ivy-jit": "bazel test --define=compile=jit --build_tag_filters=ivy-jit --test_tag_filters=ivy-jit",
"test-fixme-ivy-jit": "bazel test --define=compile=jit --build_tag_filters=-no-ivy --test_tag_filters=-no-ivy",
"test-ivy-aot": "bazel test --define=compile=aot --build_tag_filters=ivy-aot --test_tag_filters=ivy-aot",
"test-fixme-ivy-aot": "bazel test --define=compile=aot --build_tag_filters=-no-ivy --test_tag_filters=-no-ivy"
},
"// 1": "dependencies are used locally and by bazel",
"dependencies": {
"@angular-devkit/schematics": "^0.5.5",
"@bazel/typescript": "0.20.3",
"@schematics/angular": "^0.5.4",
"core-js": "^2.4.1",
"reflect-metadata": "^0.1.3",
"rxjs": "^6.3.0",
"tslib": "^1.7.1",
"zone.js": "^0.8.26"
},
"optionalDependencies": {
"fsevents": "1.1.2"
},
"devDependencies": {
"@bazel/ibazel": "^0.1.1",
"@bazel/karma": "0.20.3",
"@bazel/typescript": "0.20.3",
"@types/angular": "^1.6.47",
"@types/base64-js": "1.2.5",
"@types/chokidar": "1.7.3",
"@types/convert-source-map": "^1.5.1",
"@types/diff": "^3.2.2",
"@types/fs-extra": "4.0.2",
"@types/hammerjs": "2.0.35",
"@types/jasmine": "^2.8.8",
"@types/jasminewd2": "^2.0.4",
"@types/minimist": "^1.2.0",
"@types/mock-fs": "^3.6.30",
"@types/node": "^10.9.4",
"@types/selenium-webdriver": "3.0.7",
"@types/shelljs": "^0.7.8",
"@types/source-map": "^0.5.1",
"@types/systemjs": "0.19.32",
"@types/yargs": "^11.1.1",
"@webcomponents/custom-elements": "^1.0.4",
"angular": "npm:angular@1.7",
@ -57,57 +72,23 @@
"angular-mocks-1.5": "npm:angular-mocks@1.5",
"angular-mocks-1.6": "npm:angular-mocks@1.6",
"base64-js": "1.2.1",
"canonical-path": "0.0.2",
"chokidar": "1.7.0",
"convert-source-map": "^1.5.1",
"dependency-graph": "^0.7.2",
"domino": "2.1.0",
"fs-extra": "4.0.2",
"jasmine": "^3.1.0",
"jasmine-core": "^3.1.0",
"karma": "^2.0.4",
"magic-string": "^0.25.0",
"minimist": "1.2.0",
"mock-fs": "^4.5.0",
"node-uuid": "1.4.8",
"protractor": "5.1.2",
"reflect-metadata": "^0.1.3",
"selenium-webdriver": "3.5.0",
"shelljs": "^0.8.1",
"source-map": "^0.6.1",
"source-map-support": "0.4.18",
"tsickle": "0.32.1",
"tslib": "^1.7.1",
"typescript": "~3.1.1",
"xhr2": "0.1.4",
"yargs": "9.0.1",
"zone.js": "^0.8.26"
},
"optionalDependencies": {
"fsevents": "1.1.2"
},
"// 2": "devDependencies are not used under Bazel. Many can be removed after test.sh is deleted.",
"devDependencies": {
"@bazel/bazel": "^0.18.1",
"@bazel/ibazel": "^0.1.1",
"@bazel/karma": "0.20.3",
"@types/angular": "^1.6.47",
"@types/base64-js": "1.2.5",
"@types/jasminewd2": "^2.0.4",
"@types/minimist": "^1.2.0",
"@types/systemjs": "0.19.32",
"bower": "1.8.2",
"browserstacktunnel-wrapper": "2.0.1",
"canonical-path": "0.0.2",
"chokidar": "1.7.0",
"clang-format": "1.0.41",
"cldr": "4.10.0",
"cldr-data-downloader": "0.3.2",
"cldrjs": "0.5.0",
"conventional-changelog": "^2.0.3",
"core-js": "^2.4.1",
"convert-source-map": "^1.5.1",
"cors": "2.8.4",
"dependency-graph": "^0.7.2",
"diff": "^3.5.0",
"domino": "2.1.0",
"entities": "1.1.1",
"firefox-profile": "1.0.3",
"fs-extra": "4.0.2",
"glob": "7.1.2",
"gulp": "3.9.1",
"gulp-clang-format": "1.0.23",
@ -119,29 +100,44 @@
"hammerjs": "2.0.8",
"husky": "^0.14.3",
"incremental-dom": "0.4.1",
"jasmine": "^3.1.0",
"jasmine-core": "^3.1.0",
"jpm": "1.3.1",
"karma": "^2.0.4",
"karma-browserstack-launcher": "^1.3.0",
"karma-chrome-launcher": "^2.2.0",
"karma-jasmine": "^1.1.2",
"karma-sauce-launcher": "^1.2.0",
"karma-sourcemap-loader": "^0.3.7",
"madge": "0.5.0",
"magic-string": "^0.25.0",
"minimist": "1.2.0",
"mock-fs": "^4.5.0",
"mutation-observer": "^1.0.3",
"node-uuid": "1.4.8",
"protractor": "5.1.2",
"rewire": "2.5.2",
"rollup": "0.47.4",
"rollup-plugin-commonjs": "8.1.0",
"rollup-plugin-node-resolve": "3.0.0",
"rollup-plugin-sourcemaps": "0.4.2",
"rxjs": "^6.3.0",
"selenium-webdriver": "3.5.0",
"semver": "5.4.1",
"shelljs": "^0.8.1",
"source-map": "^0.6.1",
"source-map-support": "0.4.18",
"systemjs": "0.18.10",
"tsickle": "0.32.1",
"tslint": "5.7.0",
"tslint-eslint-rules": "4.1.1",
"tsutils": "2.27.2",
"typescript": "~3.1.1",
"uglify-es": "^3.3.9",
"universal-analytics": "0.4.15",
"vlq": "0.2.2",
"vrsource-tslint-rules": "5.1.1",
"webpack": "1.12.9"
"webpack": "1.12.9",
"xhr2": "0.1.4",
"yargs": "9.0.1"
}
}

View File

@ -22,4 +22,4 @@ protractor_web_test = _protractor_web_test
protractor_web_test_suite = _protractor_web_test_suite
ng_setup_workspace = _ng_setup_workspace
# DO NOT ADD PUBLIC API without including in the documentation generation
# Run `yarn bazel build //packages/bazel/docs` to verify
# Run `bazel build //packages/bazel/docs` to verify

View File

@ -22,13 +22,6 @@ def rules_angular_dependencies():
# Download Bazel toolchain dependencies as needed by build actions
#
# TODO(gmagolan): updated to next tagged rules_typescript release
_maybe(
http_archive,
name = "build_bazel_rules_nodejs",
url = "https://github.com/bazelbuild/rules_nodejs/archive/0.15.3.zip",
strip_prefix = "rules_nodejs-0.15.3",
)
_maybe(
http_archive,
name = "build_bazel_rules_typescript",
@ -87,11 +80,16 @@ def rules_angular_dev_dependencies():
url = "https://github.com/bazelbuild/bazel/archive/0.18.0.zip",
)
# This commit matches the version of buildifier in angular/ngcontainer
# If you change this, also check if it matches the version in the angular/ngcontainer
# version in /.circleci/config.yml
BAZEL_BUILDTOOLS_VERSION = "49a6c199e3fbf5d94534b2771868677d3f9c6de9"
http_archive(
name = "com_github_bazelbuild_buildtools",
sha256 = "a82d4b353942b10c1535528b02bff261d020827c9c57e112569eddcb1c93d7f6",
strip_prefix = "buildtools-0.17.2",
url = "https://github.com/bazelbuild/buildtools/archive/0.17.2.zip",
sha256 = "edf39af5fc257521e4af4c40829fffe8fba6d0ebff9f4dd69a6f8f1223ae047b",
strip_prefix = "buildtools-%s" % BAZEL_BUILDTOOLS_VERSION,
url = "https://github.com/bazelbuild/buildtools/archive/%s.zip" % BAZEL_BUILDTOOLS_VERSION,
)
#############################################

View File

@ -7,7 +7,7 @@
*/
import * as ng from '@angular/compiler-cli';
import {BazelOptions, CachedFileLoader, CompilerHost, FileCache, FileLoader, UncachedFileLoader, constructManifest, debug, fixUmdModuleDeclarations, parseTsconfig, resolveNormalizedPath, runAsWorker, runWorkerLoop} from '@bazel/typescript';
import {BazelOptions, CachedFileLoader, CompilerHost, FileCache, FileLoader, UncachedFileLoader, constructManifest, debug, parseTsconfig, resolveNormalizedPath, runAsWorker, runWorkerLoop} from '@bazel/typescript';
import * as fs from 'fs';
import * as path from 'path';
import * as tsickle from 'tsickle';
@ -209,20 +209,16 @@ export function compile({allowNonHermeticReads, allDepsCompiledWithBazel = true,
// compilationTargetSrc.
// However we still want to give it an AMD module name for devmode.
// We can't easily tell which file is the synthetic one, so we build up the path we expect
// it to have and compare against that.
// it to have
// and compare against that.
if (fileName ===
path.join(compilerOpts.baseUrl, bazelOpts.package, compilerOpts.flatModuleOutFile + '.ts'))
return true;
// Also handle the case the target is in an external repository.
// Pull the workspace name from the target which is formatted as `@wksp//package:target`
// if it the target is from an external workspace. If the target is from the local
// workspace then it will be formatted as `//package:target`.
const targetWorkspace = bazelOpts.target.split('/')[0].replace(/^@/, '');
if (targetWorkspace &&
fileName ===
path.join(
compilerOpts.baseUrl, 'external', targetWorkspace, bazelOpts.package,
compilerOpts.flatModuleOutFile + '.ts'))
// Also handle the case when angular is built from source as an external repository
if (fileName ===
path.join(
compilerOpts.baseUrl, 'external/angular', bazelOpts.package,
compilerOpts.flatModuleOutFile + '.ts'))
return true;
return origBazelHostShouldNameModule(fileName) || NGC_GEN_FILES.test(fileName);
};
@ -295,10 +291,7 @@ export function compile({allowNonHermeticReads, allDepsCompiledWithBazel = true,
program, bazelHost, bazelHost, compilerOpts, targetSourceFile, writeFile,
cancellationToken, emitOnlyDtsFiles, {
beforeTs: customTransformers.before,
afterTs: [
...(customTransformers.after || []),
fixUmdModuleDeclarations((sf: ts.SourceFile) => bazelHost.amdModuleName(sf)),
],
afterTs: customTransformers.after,
});
if (!gatherDiagnostics) {

View File

@ -101,7 +101,7 @@ function runPackageGoldTest(testPackage: TestPackage) {
` Diff:\n` +
` ${patch}\n\n` +
` To accept the new golden file, run:\n` +
` yarn bazel run ${process.env['BAZEL_TARGET']}.accept\n`;
` bazel run ${process.env['BAZEL_TARGET']}.accept\n`;
fail(failureMessage);
}

View File

@ -15,6 +15,5 @@ ts_library(
"//packages:types",
"//packages/core",
"@ngdeps//@types/node",
"@ngdeps//reflect-metadata",
],
)

View File

@ -26,8 +26,9 @@ ts_library(
"//packages/compiler",
"//packages/compiler-cli/src/ngtsc/annotations",
"//packages/compiler-cli/src/ngtsc/diagnostics",
"//packages/compiler-cli/src/ngtsc/factories",
"//packages/compiler-cli/src/ngtsc/metadata",
"//packages/compiler-cli/src/ngtsc/shims",
"//packages/compiler-cli/src/ngtsc/switch",
"//packages/compiler-cli/src/ngtsc/transform",
"//packages/compiler-cli/src/ngtsc/typecheck",
"@ngdeps//@bazel/typescript",

View File

@ -2,7 +2,6 @@ load("//packages/bazel:index.bzl", "ng_module")
ng_module(
name = "test_module",
testonly = True,
srcs = glob(["*.ts"]),
compiler = "//packages/bazel/src/ngc-wrapped",
entry_point = "index.ts",
@ -10,10 +9,6 @@ ng_module(
module_name = "some_npm_module",
ng_xi18n = "//packages/bazel/src/ngc-wrapped:xi18n",
node_modules = "@ngdeps//typescript:typescript__typings",
tags = [
"fixme-ivy-aot",
"no-ivy-jit",
],
deps = [
"//packages/core",
"@ngdeps//@types",
@ -24,7 +19,6 @@ load(":extract_flat_module_index.bzl", "extract_flat_module_index")
extract_flat_module_index(
name = "flat_module_index",
testonly = True,
deps = [":test_module"],
)

View File

@ -10,7 +10,7 @@ This conversion will allow such "legacy" packages to be used by the Ivy renderin
The project is built using Bazel:
```bash
yarn bazel build //packages/compiler-cli/src/ngcc
bazel build //packages/compiler-cli/src/ngcc
```
## Unit Testing
@ -18,7 +18,7 @@ yarn bazel build //packages/compiler-cli/src/ngcc
The unit tests are built and run using Bazel:
```bash
yarn bazel test //packages/compiler-cli/src/ngcc/test
bazel test //packages/compiler-cli/src/ngcc/test
```
## Integration Testing
@ -26,5 +26,5 @@ yarn bazel test //packages/compiler-cli/src/ngcc/test
There are tests that check the behaviour of the overall executable:
```bash
yarn bazel test //packages/compiler-cli/test/ngcc
bazel test //packages/compiler-cli/test/ngcc
```

View File

@ -9,8 +9,8 @@ import * as ts from 'typescript';
import {ReflectionHost} from '../../../ngtsc/host';
import {DecoratedFile} from './decorated_file';
export const PRE_NGCC_MARKER = '__PRE_NGCC__';
export const POST_NGCC_MARKER = '__POST_NGCC__';
export const PRE_NGCC_MARKER = '__PRE_R3__';
export const POST_NGCC_MARKER = '__POST_R3__';
export type SwitchableVariableDeclaration = ts.VariableDeclaration & {initializer: ts.Identifier};
export function isSwitchableVariableDeclaration(node: ts.Node):

View File

@ -30,15 +30,15 @@ const TEST_PROGRAM = [
name: 'b.js',
contents: `
export const b = 42;
var factoryB = factory__PRE_NGCC__;
var factoryB = factory__PRE_R3__;
`
},
{
name: 'c.js',
contents: `
export const c = 'So long, and thanks for all the fish!';
var factoryC = factory__PRE_NGCC__;
var factoryD = factory__PRE_NGCC__;
var factoryC = factory__PRE_R3__;
var factoryD = factory__PRE_R3__;
`
},
];
@ -62,14 +62,14 @@ describe('SwitchMarkerAnalyzer', () => {
expect(analysis.has(b)).toBe(true);
expect(analysis.get(b) !.sourceFile).toBe(b);
expect(analysis.get(b) !.declarations.map(decl => decl.getText())).toEqual([
'factoryB = factory__PRE_NGCC__'
'factoryB = factory__PRE_R3__'
]);
expect(analysis.has(c)).toBe(true);
expect(analysis.get(c) !.sourceFile).toBe(c);
expect(analysis.get(c) !.declarations.map(decl => decl.getText())).toEqual([
'factoryC = factory__PRE_NGCC__',
'factoryD = factory__PRE_NGCC__',
'factoryC = factory__PRE_R3__',
'factoryD = factory__PRE_R3__',
]);
});
});

View File

@ -35,15 +35,15 @@ const CLASSES = [
const MARKER_FILE = {
name: '/marker.js',
contents: `
let compileNgModuleFactory = compileNgModuleFactory__PRE_NGCC__;
let compileNgModuleFactory = compileNgModuleFactory__PRE_R3__;
function compileNgModuleFactory__PRE_NGCC__(injector, options, moduleType) {
function compileNgModuleFactory__PRE_R3__(injector, options, moduleType) {
const compilerFactory = injector.get(CompilerFactory);
const compiler = compilerFactory.createCompiler([options]);
return compiler.compileModuleAsync(moduleType);
}
function compileNgModuleFactory__POST_NGCC__(injector, options, moduleType) {
function compileNgModuleFactory__POST_R3__(injector, options, moduleType) {
ngDevMode && assertNgModuleType(moduleType);
return Promise.resolve(new R3NgModuleFactory(moduleType));
}
@ -113,7 +113,7 @@ describe('Esm2015ReflectionHost', () => {
const file = program.getSourceFile(MARKER_FILE.name) !;
const declarations = host.getSwitchableDeclarations(file);
expect(declarations.map(d => [d.name.getText(), d.initializer !.getText()])).toEqual([
['compileNgModuleFactory', 'compileNgModuleFactory__PRE_NGCC__']
['compileNgModuleFactory', 'compileNgModuleFactory__PRE_R3__']
]);
});
});

View File

@ -377,15 +377,15 @@ const FUNCTION_BODY_FILE = {
const MARKER_FILE = {
name: '/marker.js',
contents: `
var compileNgModuleFactory = compileNgModuleFactory__PRE_NGCC__;
var compileNgModuleFactory = compileNgModuleFactory__PRE_R3__;
function compileNgModuleFactory__PRE_NGCC__(injector, options, moduleType) {
function compileNgModuleFactory__PRE_R3__(injector, options, moduleType) {
var compilerFactory = injector.get(CompilerFactory);
var compiler = compilerFactory.createCompiler([options]);
return compiler.compileModuleAsync(moduleType);
}
function compileNgModuleFactory__POST_NGCC__(injector, options, moduleType) {
function compileNgModuleFactory__POST_R3__(injector, options, moduleType) {
ngDevMode && assertNgModuleType(moduleType);
return Promise.resolve(new R3NgModuleFactory(moduleType));
}
@ -1179,7 +1179,7 @@ describe('Fesm2015ReflectionHost', () => {
const file = program.getSourceFile(MARKER_FILE.name) !;
const declarations = host.getSwitchableDeclarations(file);
expect(declarations.map(d => [d.name.getText(), d.initializer !.getText()])).toEqual([
['compileNgModuleFactory', 'compileNgModuleFactory__PRE_NGCC__']
['compileNgModuleFactory', 'compileNgModuleFactory__PRE_R3__']
]);
});
});

View File

@ -48,16 +48,16 @@ export class C {}
C.decorators = [
{ type: Directive, args: [{ selector: '[c]' }] },
];
let compileNgModuleFactory = compileNgModuleFactory__PRE_NGCC__;
let badlyFormattedVariable = __PRE_NGCC__badlyFormattedVariable;
let compileNgModuleFactory = compileNgModuleFactory__PRE_R3__;
let badlyFormattedVariable = __PRE_R3__badlyFormattedVariable;
function compileNgModuleFactory__PRE_NGCC__(injector, options, moduleType) {
function compileNgModuleFactory__PRE_R3__(injector, options, moduleType) {
const compilerFactory = injector.get(CompilerFactory);
const compiler = compilerFactory.createCompiler([options]);
return compiler.compileModuleAsync(moduleType);
}
function compileNgModuleFactory__POST_NGCC__(injector, options, moduleType) {
function compileNgModuleFactory__POST_R3__(injector, options, moduleType) {
ngDevMode && assertNgModuleType(moduleType);
return Promise.resolve(new R3NgModuleFactory(moduleType));
}
@ -146,17 +146,15 @@ export class A {}`);
renderer.rewriteSwitchableDeclarations(
output, file, switchMarkerAnalyses.get(sourceFile) !.declarations);
expect(output.toString())
.not.toContain(`let compileNgModuleFactory = compileNgModuleFactory__PRE_NGCC__;`);
.not.toContain(`let compileNgModuleFactory = compileNgModuleFactory__PRE_R3__;`);
expect(output.toString())
.toContain(`let badlyFormattedVariable = __PRE_NGCC__badlyFormattedVariable;`);
.toContain(`let badlyFormattedVariable = __PRE_R3__badlyFormattedVariable;`);
expect(output.toString())
.toContain(`let compileNgModuleFactory = compileNgModuleFactory__POST_NGCC__;`);
.toContain(`let compileNgModuleFactory = compileNgModuleFactory__POST_R3__;`);
expect(output.toString())
.toContain(
`function compileNgModuleFactory__PRE_NGCC__(injector, options, moduleType) {`);
.toContain(`function compileNgModuleFactory__PRE_R3__(injector, options, moduleType) {`);
expect(output.toString())
.toContain(
`function compileNgModuleFactory__POST_NGCC__(injector, options, moduleType) {`);
.toContain(`function compileNgModuleFactory__POST_R3__(injector, options, moduleType) {`);
});
});

View File

@ -55,15 +55,15 @@ var C = (function() {
return C;
}());
var compileNgModuleFactory = compileNgModuleFactory__PRE_NGCC__;
var badlyFormattedVariable = __PRE_NGCC__badlyFormattedVariable;
function compileNgModuleFactory__PRE_NGCC__(injector, options, moduleType) {
var compileNgModuleFactory = compileNgModuleFactory__PRE_R3__;
var badlyFormattedVariable = __PRE_R3__badlyFormattedVariable;
function compileNgModuleFactory__PRE_R3__(injector, options, moduleType) {
const compilerFactory = injector.get(CompilerFactory);
const compiler = compilerFactory.createCompiler([options]);
return compiler.compileModuleAsync(moduleType);
}
function compileNgModuleFactory__POST_NGCC__(injector, options, moduleType) {
function compileNgModuleFactory__POST_R3__(injector, options, moduleType) {
ngDevMode && assertNgModuleType(moduleType);
return Promise.resolve(new R3NgModuleFactory(moduleType));
}
@ -166,17 +166,15 @@ var A = (function() {`);
renderer.rewriteSwitchableDeclarations(
output, file, switchMarkerAnalyses.get(sourceFile) !.declarations);
expect(output.toString())
.not.toContain(`var compileNgModuleFactory = compileNgModuleFactory__PRE_NGCC__;`);
.not.toContain(`var compileNgModuleFactory = compileNgModuleFactory__PRE_R3__;`);
expect(output.toString())
.toContain(`var badlyFormattedVariable = __PRE_NGCC__badlyFormattedVariable;`);
.toContain(`var badlyFormattedVariable = __PRE_R3__badlyFormattedVariable;`);
expect(output.toString())
.toContain(`var compileNgModuleFactory = compileNgModuleFactory__POST_NGCC__;`);
.toContain(`var compileNgModuleFactory = compileNgModuleFactory__POST_R3__;`);
expect(output.toString())
.toContain(
`function compileNgModuleFactory__PRE_NGCC__(injector, options, moduleType) {`);
.toContain(`function compileNgModuleFactory__PRE_R3__(injector, options, moduleType) {`);
expect(output.toString())
.toContain(
`function compileNgModuleFactory__POST_NGCC__(injector, options, moduleType) {`);
.toContain(`function compileNgModuleFactory__POST_R3__(injector, options, moduleType) {`);
});
});

View File

@ -128,7 +128,7 @@ describe('Renderer', () => {
}));
expect(addDefinitionsSpy.calls.first().args[2])
.toEqual(
`A.ngDirectiveDef = ɵngcc0.ɵdefineDirective({ type: A, selectors: [["", "a", ""]], factory: function A_Factory(t) { return new (t || A)(); }, features: [ɵngcc0.ɵPublicFeature] });`);
`A.ngDirectiveDef = ɵngcc0.ɵdefineDirective({ type: A, selectors: [["", "a", ""]], factory: function A_Factory(t) { return new (t || A)(); } });`);
});
it('should call removeDecorators with the source code, a map of class decorators that have been analyzed',

View File

@ -118,6 +118,10 @@ export class ComponentDecoratorHandler implements
preserveWhitespaces = value;
}
const viewProviders: Expression|null = component.has('viewProviders') ?
new WrappedNodeExpr(component.get('viewProviders') !) :
null;
// Go through the root directories for this project, and select the one with the smallest
// relative path representation.
const filePath = node.getSourceFile().fileName;
@ -202,7 +206,7 @@ export class ComponentDecoratorHandler implements
directives: EMPTY_MAP,
wrapDirectivesInClosure: false, //
animations,
viewProviders: null,
viewProviders
},
parsedTemplate: template.nodes,
},

View File

@ -146,6 +146,9 @@ export function extractDirectiveMetadata(
const host = extractHostBindings(directive, decoratedElements, reflector, checker, coreModule);
const providers: Expression|null =
directive.has('providers') ? new WrappedNodeExpr(directive.get('providers') !) : null;
// Determine if `ngOnChanges` is a lifecycle hook defined on the component.
const usesOnChanges = members.some(
member => !member.isStatic && member.kind === ClassMemberKind.Method &&
@ -176,8 +179,7 @@ export function extractDirectiveMetadata(
outputs: {...outputsFromMeta, ...outputsFromFields}, queries, selector,
type: new WrappedNodeExpr(clazz.name !),
typeArgumentCount: reflector.getGenericArityOfClass(clazz) || 0,
typeSourceSpan: null !, usesInheritance, exportAs,
providers: null,
typeSourceSpan: null !, usesInheritance, exportAs, providers
};
return {decoratedElements, decorator: directive, metadata};
}
@ -328,7 +330,7 @@ function parseFieldToPropertyMapping(
*/
function parseDecoratedFields(
fields: {member: ClassMember, decorators: Decorator[]}[], reflector: ReflectionHost,
checker: ts.TypeChecker) {
checker: ts.TypeChecker): {[field: string]: string} {
return fields.reduce(
(results, field) => {
const fieldName = field.member.name;
@ -354,14 +356,6 @@ function parseDecoratedFields(
{} as{[field: string]: string});
}
function resolveInput(publicName: string, internalName: string): [string, string] {
return [publicName, internalName];
}
function resolveOutput(publicName: string, internalName: string) {
return publicName;
}
export function queriesFromFields(
fields: {member: ClassMember, decorators: Decorator[]}[], reflector: ReflectionHost,
checker: ts.TypeChecker): R3QueryMetadata[] {

View File

@ -64,18 +64,6 @@ export function getConstructorDependencies(
ErrorCode.PARAM_MISSING_TOKEN, param.nameNode,
`No suitable token for parameter ${param.name || idx} of class ${clazz.name!.text}`);
}
if (ts.isIdentifier(tokenExpr)) {
const importedSymbol = reflector.getImportOfIdentifier(tokenExpr);
if (importedSymbol !== null && importedSymbol.from === '@angular/core') {
switch (importedSymbol.name) {
case 'Injector':
resolved = R3ResolvedDependencyType.Injector;
break;
default:
// Leave as a Token or Attribute.
}
}
}
const token = new WrappedNodeExpr(tokenExpr);
useType.push({token, optional, self, skipSelf, host, resolved});
});

View File

@ -1,63 +0,0 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import * as path from 'path';
import * as ts from 'typescript';
const TS_DTS_SUFFIX = /(\.d)?\.ts$/;
/**
* Generates ts.SourceFiles which contain variable declarations for NgFactories for every exported
* class of an input ts.SourceFile.
*/
export class FactoryGenerator {
factoryFor(original: ts.SourceFile, genFilePath: string): ts.SourceFile {
const relativePathToSource =
'./' + path.posix.basename(original.fileName).replace(TS_DTS_SUFFIX, '');
// Collect a list of classes that need to have factory types emitted for them.
const symbolNames = original
.statements
// Pick out top level class declarations...
.filter(ts.isClassDeclaration)
// which are named, exported, and have decorators.
.filter(
decl => isExported(decl) && decl.decorators !== undefined &&
decl.name !== undefined)
// Grab the symbol name.
.map(decl => decl.name !.text);
// For each symbol name, generate a constant export of the corresponding NgFactory.
// This will encompass a lot of symbols which don't need factories, but that's okay
// because it won't miss any that do.
const varLines = symbolNames.map(
name => `export const ${name}NgFactory = new i0.ɵNgModuleFactory(${name});`);
const sourceText = [
// This might be incorrect if the current package being compiled is Angular core, but it's
// okay to leave in at type checking time. TypeScript can handle this reference via its path
// mapping, but downstream bundlers can't. If the current package is core itself, this will be
// replaced in the factory transformer before emit.
`import * as i0 from '@angular/core';`,
`import {${symbolNames.join(', ')}} from '${relativePathToSource}';`,
...varLines,
].join('\n');
return ts.createSourceFile(
genFilePath, sourceText, original.languageVersion, true, ts.ScriptKind.TS);
}
computeFactoryFileMap(files: ReadonlyArray<string>): Map<string, string> {
const map = new Map<string, string>();
files.filter(sourceFile => !sourceFile.endsWith('.d.ts'))
.forEach(sourceFile => map.set(sourceFile.replace(/\.ts$/, '.ngfactory.ts'), sourceFile));
return map;
}
}
function isExported(decl: ts.Declaration): boolean {
return decl.modifiers !== undefined &&
decl.modifiers.some(mod => mod.kind == ts.SyntaxKind.ExportKeyword);
}

View File

@ -1,78 +0,0 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import * as ts from 'typescript';
import {relativePathBetween} from '../../util/src/path';
const STRIP_NG_FACTORY = /(.*)NgFactory$/;
export interface FactoryInfo {
sourceFilePath: string;
moduleSymbolNames: Set<string>;
}
export function generatedFactoryTransform(
factoryMap: Map<string, FactoryInfo>,
coreImportsFrom: ts.SourceFile | null): ts.TransformerFactory<ts.SourceFile> {
return (context: ts.TransformationContext): ts.Transformer<ts.SourceFile> => {
return (file: ts.SourceFile): ts.SourceFile => {
return transformFactorySourceFile(factoryMap, context, coreImportsFrom, file);
};
};
}
function transformFactorySourceFile(
factoryMap: Map<string, FactoryInfo>, context: ts.TransformationContext,
coreImportsFrom: ts.SourceFile | null, file: ts.SourceFile): ts.SourceFile {
// If this is not a generated file, it won't have factory info associated with it.
if (!factoryMap.has(file.fileName)) {
// Don't transform non-generated code.
return file;
}
const {moduleSymbolNames, sourceFilePath} = factoryMap.get(file.fileName) !;
const clone = ts.getMutableClone(file);
const transformedStatements = file.statements.map(stmt => {
if (coreImportsFrom !== null && ts.isImportDeclaration(stmt) &&
ts.isStringLiteral(stmt.moduleSpecifier) && stmt.moduleSpecifier.text === '@angular/core') {
const path = relativePathBetween(sourceFilePath, coreImportsFrom.fileName);
if (path !== null) {
return ts.updateImportDeclaration(
stmt, stmt.decorators, stmt.modifiers, stmt.importClause, ts.createStringLiteral(path));
} else {
return ts.createNotEmittedStatement(stmt);
}
} else if (ts.isVariableStatement(stmt) && stmt.declarationList.declarations.length === 1) {
const decl = stmt.declarationList.declarations[0];
if (ts.isIdentifier(decl.name)) {
const match = STRIP_NG_FACTORY.exec(decl.name.text);
if (match === null || !moduleSymbolNames.has(match[1])) {
// Remove the given factory as it wasn't actually for an NgModule.
return ts.createNotEmittedStatement(stmt);
}
}
return stmt;
} else {
return stmt;
}
});
if (!transformedStatements.some(ts.isVariableStatement)) {
// If the resulting file has no factories, include an empty export to
// satisfy closure compiler.
transformedStatements.push(ts.createVariableStatement(
[ts.createModifier(ts.SyntaxKind.ExportKeyword)],
ts.createVariableDeclarationList(
[ts.createVariableDeclaration('ɵNonEmptyModule', undefined, ts.createTrue())],
ts.NodeFlags.Const)));
}
clone.statements = ts.createNodeArray(transformedStatements);
return clone;
}

View File

@ -15,9 +15,10 @@ import {nocollapseHack} from '../transformers/nocollapse_hack';
import {ComponentDecoratorHandler, DirectiveDecoratorHandler, InjectableDecoratorHandler, NgModuleDecoratorHandler, PipeDecoratorHandler, ResourceLoader, SelectorScopeRegistry} from './annotations';
import {BaseDefDecoratorHandler} from './annotations/src/base_def';
import {FactoryGenerator, FactoryInfo, GeneratedFactoryHostWrapper, generatedFactoryTransform} from './factories';
import {TypeScriptReflectionHost} from './metadata';
import {FileResourceLoader, HostResourceLoader} from './resource_loader';
import {FactoryGenerator, FactoryInfo, GeneratedShimsHostWrapper, SummaryGenerator, generatedFactoryTransform} from './shims';
import {ivySwitchTransform} from './switch';
import {IvyCompilation, ivyTransformFactory} from './transform';
import {TypeCheckContext, TypeCheckProgramHost} from './typecheck';
@ -50,13 +51,16 @@ export class NgtscProgram implements api.Program {
this.resourceLoader = host.readResource !== undefined ?
new HostResourceLoader(host.readResource.bind(host)) :
new FileResourceLoader();
const shouldGenerateFactories = options.allowEmptyCodegenFiles || false;
const shouldGenerateShims = options.allowEmptyCodegenFiles || false;
this.host = host;
let rootFiles = [...rootNames];
if (shouldGenerateFactories) {
const generator = new FactoryGenerator();
const factoryFileMap = generator.computeFactoryFileMap(rootNames);
rootFiles.push(...Array.from(factoryFileMap.keys()));
if (shouldGenerateShims) {
// Summary generation.
const summaryGenerator = SummaryGenerator.forRootFiles(rootNames);
// Factory generation.
const factoryGenerator = FactoryGenerator.forRootFiles(rootNames);
const factoryFileMap = factoryGenerator.factoryFileMap;
this.factoryToSourceInfo = new Map<string, FactoryInfo>();
this.sourceToFactorySymbols = new Map<string, Set<string>>();
factoryFileMap.forEach((sourceFilePath, factoryPath) => {
@ -64,7 +68,10 @@ export class NgtscProgram implements api.Program {
this.sourceToFactorySymbols !.set(sourceFilePath, moduleSymbolNames);
this.factoryToSourceInfo !.set(factoryPath, {sourceFilePath, moduleSymbolNames});
});
this.host = new GeneratedFactoryHostWrapper(host, generator, factoryFileMap);
const factoryFileNames = Array.from(factoryFileMap.keys());
rootFiles.push(...factoryFileNames, ...summaryGenerator.getSummaryFileNames());
this.host = new GeneratedShimsHostWrapper(host, [summaryGenerator, factoryGenerator]);
}
this.tsProgram =
@ -177,6 +184,9 @@ export class NgtscProgram implements api.Program {
if (this.factoryToSourceInfo !== null) {
transforms.push(generatedFactoryTransform(this.factoryToSourceInfo, this.coreImportsFrom));
}
if (this.isCore) {
transforms.push(ivySwitchTransform);
}
// Run the emit, including a custom transformer that will downlevel the Ivy decorators in code.
const emitResult = emitCallback({
program: this.tsProgram,

View File

@ -3,12 +3,12 @@ package(default_visibility = ["//visibility:public"])
load("//tools:defaults.bzl", "ts_library")
ts_library(
name = "factories",
name = "shims",
srcs = glob([
"index.ts",
"src/**/*.ts",
]),
module_name = "@angular/compiler-cli/src/ngtsc/factories",
module_name = "@angular/compiler-cli/src/ngtsc/shims",
deps = [
"//packages/compiler",
"//packages/compiler-cli/src/ngtsc/host",

View File

@ -8,6 +8,6 @@
/// <reference types="node" />
export {FactoryGenerator} from './src/generator';
export {GeneratedFactoryHostWrapper} from './src/host';
export {FactoryInfo, generatedFactoryTransform} from './src/transform';
export {FactoryGenerator, FactoryInfo, generatedFactoryTransform} from './src/factory_generator';
export {GeneratedShimsHostWrapper} from './src/host';
export {SummaryGenerator} from './src/summary_generator';

View File

@ -0,0 +1,144 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import * as path from 'path';
import * as ts from 'typescript';
import {relativePathBetween} from '../../util/src/path';
import {ShimGenerator} from './host';
import {isNonDeclarationTsFile} from './util';
const TS_DTS_SUFFIX = /(\.d)?\.ts$/;
const STRIP_NG_FACTORY = /(.*)NgFactory$/;
/**
* Generates ts.SourceFiles which contain variable declarations for NgFactories for every exported
* class of an input ts.SourceFile.
*/
export class FactoryGenerator implements ShimGenerator {
private constructor(private map: Map<string, string>) {}
get factoryFileMap(): Map<string, string> { return this.map; }
getOriginalSourceOfShim(fileName: string): string|null { return this.map.get(fileName) || null; }
generate(original: ts.SourceFile, genFilePath: string): ts.SourceFile {
const relativePathToSource =
'./' + path.posix.basename(original.fileName).replace(TS_DTS_SUFFIX, '');
// Collect a list of classes that need to have factory types emitted for them. This list is
// overly broad as at this point the ts.TypeChecker hasn't been created, and can't be used to
// semantically understand which decorated types are actually decorated with Angular decorators.
//
// The exports generated here are pruned in the factory transform during emit.
const symbolNames = original
.statements
// Pick out top level class declarations...
.filter(ts.isClassDeclaration)
// which are named, exported, and have decorators.
.filter(
decl => isExported(decl) && decl.decorators !== undefined &&
decl.name !== undefined)
// Grab the symbol name.
.map(decl => decl.name !.text);
// For each symbol name, generate a constant export of the corresponding NgFactory.
// This will encompass a lot of symbols which don't need factories, but that's okay
// because it won't miss any that do.
const varLines = symbolNames.map(
name => `export const ${name}NgFactory = new i0.ɵNgModuleFactory(${name});`);
const sourceText = [
// This might be incorrect if the current package being compiled is Angular core, but it's
// okay to leave in at type checking time. TypeScript can handle this reference via its path
// mapping, but downstream bundlers can't. If the current package is core itself, this will be
// replaced in the factory transformer before emit.
`import * as i0 from '@angular/core';`,
`import {${symbolNames.join(', ')}} from '${relativePathToSource}';`,
...varLines,
].join('\n');
return ts.createSourceFile(
genFilePath, sourceText, original.languageVersion, true, ts.ScriptKind.TS);
}
static forRootFiles(files: ReadonlyArray<string>): FactoryGenerator {
const map = new Map<string, string>();
files.filter(sourceFile => isNonDeclarationTsFile(sourceFile))
.forEach(sourceFile => map.set(sourceFile.replace(/\.ts$/, '.ngfactory.ts'), sourceFile));
return new FactoryGenerator(map);
}
}
function isExported(decl: ts.Declaration): boolean {
return decl.modifiers !== undefined &&
decl.modifiers.some(mod => mod.kind == ts.SyntaxKind.ExportKeyword);
}
export interface FactoryInfo {
sourceFilePath: string;
moduleSymbolNames: Set<string>;
}
export function generatedFactoryTransform(
factoryMap: Map<string, FactoryInfo>,
coreImportsFrom: ts.SourceFile | null): ts.TransformerFactory<ts.SourceFile> {
return (context: ts.TransformationContext): ts.Transformer<ts.SourceFile> => {
return (file: ts.SourceFile): ts.SourceFile => {
return transformFactorySourceFile(factoryMap, context, coreImportsFrom, file);
};
};
}
function transformFactorySourceFile(
factoryMap: Map<string, FactoryInfo>, context: ts.TransformationContext,
coreImportsFrom: ts.SourceFile | null, file: ts.SourceFile): ts.SourceFile {
// If this is not a generated file, it won't have factory info associated with it.
if (!factoryMap.has(file.fileName)) {
// Don't transform non-generated code.
return file;
}
const {moduleSymbolNames, sourceFilePath} = factoryMap.get(file.fileName) !;
const clone = ts.getMutableClone(file);
const transformedStatements = file.statements.map(stmt => {
if (coreImportsFrom !== null && ts.isImportDeclaration(stmt) &&
ts.isStringLiteral(stmt.moduleSpecifier) && stmt.moduleSpecifier.text === '@angular/core') {
const path = relativePathBetween(sourceFilePath, coreImportsFrom.fileName);
if (path !== null) {
return ts.updateImportDeclaration(
stmt, stmt.decorators, stmt.modifiers, stmt.importClause, ts.createStringLiteral(path));
} else {
return ts.createNotEmittedStatement(stmt);
}
} else if (ts.isVariableStatement(stmt) && stmt.declarationList.declarations.length === 1) {
const decl = stmt.declarationList.declarations[0];
if (ts.isIdentifier(decl.name)) {
const match = STRIP_NG_FACTORY.exec(decl.name.text);
if (match === null || !moduleSymbolNames.has(match[1])) {
// Remove the given factory as it wasn't actually for an NgModule.
return ts.createNotEmittedStatement(stmt);
}
}
return stmt;
} else {
return stmt;
}
});
if (!transformedStatements.some(ts.isVariableStatement)) {
// If the resulting file has no factories, include an empty export to
// satisfy closure compiler.
transformedStatements.push(ts.createVariableStatement(
[ts.createModifier(ts.SyntaxKind.ExportKeyword)],
ts.createVariableDeclarationList(
[ts.createVariableDeclaration('ɵNonEmptyModule', undefined, ts.createTrue())],
ts.NodeFlags.Const)));
}
clone.statements = ts.createNodeArray(transformedStatements);
return clone;
}

View File

@ -9,15 +9,26 @@
import * as path from 'path';
import * as ts from 'typescript';
import {FactoryGenerator} from './generator';
export interface ShimGenerator {
/**
* Get the original source file for the given shim path, the contents of which determine the
* contents of the shim file.
*
* If this returns `null` then the given file was not a shim file handled by this generator.
*/
getOriginalSourceOfShim(fileName: string): string|null;
/**
* Generate a shim's `ts.SourceFile` for the given original file.
*/
generate(original: ts.SourceFile, genFileName: string): ts.SourceFile;
}
/**
* A wrapper around a `ts.CompilerHost` which supports generated files.
*/
export class GeneratedFactoryHostWrapper implements ts.CompilerHost {
constructor(
private delegate: ts.CompilerHost, private generator: FactoryGenerator,
private factoryToSourceMap: Map<string, string>) {
export class GeneratedShimsHostWrapper implements ts.CompilerHost {
constructor(private delegate: ts.CompilerHost, private shimGenerators: ShimGenerator[]) {
if (delegate.resolveTypeReferenceDirectives) {
// Backward compatibility with TypeScript 2.9 and older since return
// type has changed from (ts.ResolvedTypeReferenceDirective | undefined)[]
@ -38,14 +49,20 @@ export class GeneratedFactoryHostWrapper implements ts.CompilerHost {
onError?: ((message: string) => void)|undefined,
shouldCreateNewSourceFile?: boolean|undefined): ts.SourceFile|undefined {
const canonical = this.getCanonicalFileName(fileName);
if (this.factoryToSourceMap.has(canonical)) {
const sourceFileName = this.getCanonicalFileName(this.factoryToSourceMap.get(canonical) !);
const sourceFile = this.delegate.getSourceFile(
sourceFileName, languageVersion, onError, shouldCreateNewSourceFile);
if (sourceFile === undefined) {
return undefined;
for (let i = 0; i < this.shimGenerators.length; i++) {
const generator = this.shimGenerators[i];
const originalFile = generator.getOriginalSourceOfShim(canonical);
if (originalFile !== null) {
// This shim generator has recognized the filename being requested, and is now responsible
// for generating its contents, based on the contents of the original file it has requested.
const originalSource = this.delegate.getSourceFile(
originalFile, languageVersion, onError, shouldCreateNewSourceFile);
if (originalSource === undefined) {
// The original requested file doesn't exist, so the shim cannot exist either.
return undefined;
}
return generator.generate(originalSource, fileName);
}
return this.generator.factoryFor(sourceFile, fileName);
}
return this.delegate.getSourceFile(
fileName, languageVersion, onError, shouldCreateNewSourceFile);
@ -75,7 +92,11 @@ export class GeneratedFactoryHostWrapper implements ts.CompilerHost {
getNewLine(): string { return this.delegate.getNewLine(); }
fileExists(fileName: string): boolean {
return this.factoryToSourceMap.has(fileName) || this.delegate.fileExists(fileName);
const canonical = this.getCanonicalFileName(fileName);
// Consider the file as existing whenever 1) it really does exist in the delegate host, or
// 2) at least one of the shim generators recognizes it.
return this.delegate.fileExists(fileName) ||
this.shimGenerators.some(gen => gen.getOriginalSourceOfShim(canonical) !== null);
}
readFile(fileName: string): string|undefined { return this.delegate.readFile(fileName); }

View File

@ -0,0 +1,61 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import * as ts from 'typescript';
import {ShimGenerator} from './host';
import {isNonDeclarationTsFile} from './util';
export class SummaryGenerator implements ShimGenerator {
private constructor(private map: Map<string, string>) {}
getSummaryFileNames(): string[] { return Array.from(this.map.keys()); }
getOriginalSourceOfShim(fileName: string): string|null { return this.map.get(fileName) || null; }
generate(original: ts.SourceFile, genFilePath: string): ts.SourceFile {
// Collect a list of classes that need to have factory types emitted for them. This list is
// overly broad as at this point the ts.TypeChecker has not been created and so it can't be used
// to semantically understand which decorators are Angular decorators. It's okay to output an
// overly broad set of summary exports as the exports are no-ops anyway, and summaries are a
// compatibility layer which will be removed after Ivy is enabled.
const symbolNames = original
.statements
// Pick out top level class declarations...
.filter(ts.isClassDeclaration)
// which are named, exported, and have decorators.
.filter(
decl => isExported(decl) && decl.decorators !== undefined &&
decl.name !== undefined)
// Grab the symbol name.
.map(decl => decl.name !.text);
const varLines = symbolNames.map(name => `export const ${name}NgSummary: any = null;`);
if (varLines.length === 0) {
// In the event there are no other exports, add an empty export to ensure the generated
// summary file is still an ES module.
varLines.push(`export const ɵempty = null;`);
}
const sourceText = varLines.join('\n');
return ts.createSourceFile(
genFilePath, sourceText, original.languageVersion, true, ts.ScriptKind.TS);
}
static forRootFiles(files: ReadonlyArray<string>): SummaryGenerator {
const map = new Map<string, string>();
files.filter(sourceFile => isNonDeclarationTsFile(sourceFile))
.forEach(sourceFile => map.set(sourceFile.replace(/\.ts$/, '.ngsummary.ts'), sourceFile));
return new SummaryGenerator(map);
}
}
function isExported(decl: ts.Declaration): boolean {
return decl.modifiers !== undefined &&
decl.modifiers.some(mod => mod.kind == ts.SyntaxKind.ExportKeyword);
}

View File

@ -1,4 +1,3 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
@ -7,4 +6,9 @@
* found in the LICENSE file at https://angular.io/license
*/
export * from './ivy_switch_on';
const TS_FILE = /\.tsx?$/;
const D_TS_FILE = /\.d\.ts$/;
export function isNonDeclarationTsFile(file: string): boolean {
return TS_FILE.exec(file) !== null && D_TS_FILE.exec(file) === null;
}

View File

@ -0,0 +1,19 @@
package(default_visibility = ["//visibility:public"])
load("//tools:defaults.bzl", "ts_library")
ts_library(
name = "switch",
srcs = glob([
"index.ts",
"src/**/*.ts",
]),
module_name = "@angular/compiler-cli/src/ngtsc/switch",
deps = [
"//packages/compiler",
"//packages/compiler-cli/src/ngtsc/host",
"//packages/compiler-cli/src/ngtsc/metadata",
"//packages/compiler-cli/src/ngtsc/util",
"@ngdeps//typescript",
],
)

View File

@ -1,4 +1,3 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
@ -7,4 +6,4 @@
* found in the LICENSE file at https://angular.io/license
*/
export * from './ivy_switch_on';
export {ivySwitchTransform} from './src/switch';

View File

@ -0,0 +1,152 @@
/**
* @license
* Copyright Google Inc. All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import * as ts from 'typescript';
const IVY_SWITCH_PRE_SUFFIX = '__PRE_R3__';
const IVY_SWITCH_POST_SUFFIX = '__POST_R3__';
export function ivySwitchTransform(_: ts.TransformationContext): ts.Transformer<ts.SourceFile> {
return flipIvySwitchInFile;
}
function flipIvySwitchInFile(sf: ts.SourceFile): ts.SourceFile {
// To replace the statements array, it must be copied. This only needs to happen if a statement
// must actually be replaced within the array, so the newStatements array is lazily initialized.
let newStatements: ts.Statement[]|undefined = undefined;
// Iterate over the statements in the file.
for (let i = 0; i < sf.statements.length; i++) {
const statement = sf.statements[i];
// Skip over everything that isn't a variable statement.
if (!ts.isVariableStatement(statement) || !hasIvySwitches(statement)) {
continue;
}
// This statement needs to be replaced. Check if the newStatements array needs to be lazily
// initialized to a copy of the original statements.
if (newStatements === undefined) {
newStatements = [...sf.statements];
}
// Flip any switches in the VariableStatement. If there were any, a new statement will be
// returned; otherwise the old statement will be.
newStatements[i] = flipIvySwitchesInVariableStatement(statement, sf.statements);
}
// Only update the statements in the SourceFile if any have changed.
if (newStatements !== undefined) {
sf.statements = ts.createNodeArray(newStatements);
}
return sf;
}
/**
* Look for the ts.Identifier of a ts.Declaration with this name.
*
* The real identifier is needed (rather than fabricating one) as TypeScript decides how to
* reference this identifier based on information stored against its node in the AST, which a
* synthetic node would not have. In particular, since the post-switch variable is often exported,
* TypeScript needs to know this so it can write `exports.VAR` instead of just `VAR` when emitting
* code.
*
* Only variable, function, and class declarations are currently searched.
*/
function findPostSwitchIdentifier(
statements: ReadonlyArray<ts.Statement>, name: string): ts.Identifier|null {
for (const stmt of statements) {
if (ts.isVariableStatement(stmt)) {
const decl = stmt.declarationList.declarations.find(
decl => ts.isIdentifier(decl.name) && decl.name.text === name);
if (decl !== undefined) {
return decl.name as ts.Identifier;
}
} else if (ts.isFunctionDeclaration(stmt) || ts.isClassDeclaration(stmt)) {
if (stmt.name !== undefined && ts.isIdentifier(stmt.name) && stmt.name.text === name) {
return stmt.name;
}
}
}
return null;
}
/**
* Flip any Ivy switches which are discovered in the given ts.VariableStatement.
*/
function flipIvySwitchesInVariableStatement(
stmt: ts.VariableStatement, statements: ReadonlyArray<ts.Statement>): ts.VariableStatement {
// Build a new list of variable declarations. Specific declarations that are initialized to a
// pre-switch identifier will be replaced with a declaration initialized to the post-switch
// identifier.
const newDeclarations = [...stmt.declarationList.declarations];
for (let i = 0; i < newDeclarations.length; i++) {
const decl = newDeclarations[i];
// Skip declarations that aren't initialized to an identifier.
if (decl.initializer === undefined || !ts.isIdentifier(decl.initializer)) {
continue;
}
// Skip declarations that aren't Ivy switches.
if (!decl.initializer.text.endsWith(IVY_SWITCH_PRE_SUFFIX)) {
continue;
}
// Determine the name of the post-switch variable.
const postSwitchName =
decl.initializer.text.replace(IVY_SWITCH_PRE_SUFFIX, IVY_SWITCH_POST_SUFFIX);
// Find the post-switch variable identifier. If one can't be found, it's an error. This is
// reported as a thrown error and not a diagnostic as transformers cannot output diagnostics.
let newIdentifier = findPostSwitchIdentifier(statements, postSwitchName);
if (newIdentifier === null) {
throw new Error(
`Unable to find identifier ${postSwitchName} in ${stmt.getSourceFile().fileName} for the Ivy switch.`);
}
// Copy the identifier with updateIdentifier(). This copies the internal information which
// allows TS to write a correct reference to the identifier.
newIdentifier = ts.updateIdentifier(newIdentifier);
newDeclarations[i] = ts.updateVariableDeclaration(
/* node */ decl,
/* name */ decl.name,
/* type */ decl.type,
/* initializer */ newIdentifier);
// Keeping parent pointers up to date is important for emit.
newIdentifier.parent = newDeclarations[i];
}
const newDeclList = ts.updateVariableDeclarationList(
/* declarationList */ stmt.declarationList,
/* declarations */ newDeclarations);
const newStmt = ts.updateVariableStatement(
/* statement */ stmt,
/* modifiers */ stmt.modifiers,
/* declarationList */ newDeclList);
// Keeping parent pointers up to date is important for emit.
for (const decl of newDeclarations) {
decl.parent = newDeclList;
}
newDeclList.parent = newStmt;
newStmt.parent = stmt.parent;
return newStmt;
}
/**
* Check whether the given VariableStatement has any Ivy switch variables.
*/
function hasIvySwitches(stmt: ts.VariableStatement) {
return stmt.declarationList.declarations.some(
decl => decl.initializer !== undefined && ts.isIdentifier(decl.initializer) &&
decl.initializer.text.endsWith(IVY_SWITCH_PRE_SUFFIX));
}

View File

@ -518,7 +518,7 @@ function tcbGetInputBindingExpressions(
// is desired. Invert `dir.inputs` into `propMatch` to create this map.
const propMatch = new Map<string, string>();
const inputs = dir.inputs;
Object.keys(inputs).forEach(key => propMatch.set(inputs[key] as string, key));
Object.keys(inputs).forEach(key => propMatch.set(inputs[key], key));
// Add a binding expression to the map for each input of the directive that has a
// matching binding.

View File

@ -10,11 +10,15 @@ import {GeneratedFile} from '@angular/compiler';
import * as path from 'path';
import * as ts from 'typescript';
import {ivySwitchTransform} from '../ngtsc/switch';
import * as api from '../transformers/api';
/**
* An implementation of the `Program` API which behaves like plain `tsc` and does not include any
* Angular-specific behavior whatsoever.
* An implementation of the `Program` API which behaves similarly to plain `tsc`.
*
* The only Angular specific behavior included in this `Program` is the operation of the Ivy
* switch to turn on render3 behavior.
*
* This allows `ngc` to behave like `tsc` in cases where JIT code needs to be tested.
*/
@ -95,6 +99,7 @@ export class TscPassThroughProgram implements api.Program {
host: this.host,
options: this.options,
emitOnlyDtsFiles: false,
customTransformers: {before: [ivySwitchTransform]},
});
return emitResult;
}

View File

@ -1,5 +1,3 @@
Tests in this directory should be run with:
```
yarn bazel test --define=compile=aot packages/compiler-cli/test/compliance:compliance
```
bazel test --define=compile=aot packages/compiler-cli/test/compliance:compliance

View File

@ -415,7 +415,6 @@ describe('compiler compliance', () => {
factory: function MyComponent_Factory(t){
return new (t || MyComponent)();
},
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 0,
template: function MyComponent_Template(rf,ctx){
@ -470,7 +469,6 @@ describe('compiler compliance', () => {
type: ChildComponent,
selectors: [["child"]],
factory: function ChildComponent_Factory(t) { return new (t || ChildComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 0,
template: function ChildComponent_Template(rf, ctx) {
@ -485,8 +483,7 @@ describe('compiler compliance', () => {
SomeDirective.ngDirectiveDef = $r3$.ɵdefineDirective({
type: SomeDirective,
selectors: [["", "some-directive", ""]],
factory: function SomeDirective_Factory(t) {return new (t || SomeDirective)(); },
features: [$r3$.ɵPublicFeature]
factory: function SomeDirective_Factory(t) {return new (t || SomeDirective)(); }
});
`;
@ -498,7 +495,6 @@ describe('compiler compliance', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 2,
vars: 0,
template: function MyComponent_Template(rf, ctx) {
@ -543,8 +539,7 @@ describe('compiler compliance', () => {
SomeDirective.ngDirectiveDef = $r3$.ɵdefineDirective({
type: SomeDirective,
selectors: [["div", "some-directive", "", 8, "foo", 3, "title", "", 9, "baz"]],
factory: function SomeDirective_Factory(t) {return new (t || SomeDirective)(); },
features: [$r3$.ɵPublicFeature]
factory: function SomeDirective_Factory(t) {return new (t || SomeDirective)(); }
});
`;
@ -553,8 +548,7 @@ describe('compiler compliance', () => {
OtherDirective.ngDirectiveDef = $r3$.ɵdefineDirective({
type: OtherDirective,
selectors: [["", 5, "span", "title", "", 9, "baz"]],
factory: function OtherDirective_Factory(t) {return new (t || OtherDirective)(); },
features: [$r3$.ɵPublicFeature]
factory: function OtherDirective_Factory(t) {return new (t || OtherDirective)(); }
});
`;
@ -590,8 +584,7 @@ describe('compiler compliance', () => {
hostBindings: function HostBindingDir_HostBindings(dirIndex, elIndex) {
$r3$.ɵelementProperty(elIndex, "id", $r3$.ɵbind($r3$.ɵload(dirIndex).dirId));
},
hostVars: 1,
features: [$r3$.ɵPublicFeature]
hostVars: 1
});
`;
@ -635,7 +628,6 @@ describe('compiler compliance', () => {
$r3$.ɵelementProperty(elIndex, "id", $r3$.ɵbind($r3$.ɵpureFunction1(1, $ff$, $r3$.ɵload(dirIndex).id)));
},
hostVars: 3,
features: [$r3$.ɵPublicFeature],
consts: 0,
vars: 0,
template: function HostBindingComp_Template(rf, ctx) {}
@ -679,7 +671,6 @@ describe('compiler compliance', () => {
$r3$.ɵdirectiveInject(ElementRef), $r3$.ɵdirectiveInject(ViewContainerRef),
$r3$.ɵdirectiveInject(ChangeDetectorRef));
},
features: [$r3$.ɵPublicFeature],
consts: 0,
vars: 0,
template: function MyComponent_Template(rf, ctx) {}
@ -720,8 +711,7 @@ describe('compiler compliance', () => {
IfDirective.ngDirectiveDef = $r3$.ɵdefineDirective({
type: IfDirective,
selectors: [["", "if", ""]],
factory: function IfDirective_Factory(t) { return new (t || IfDirective)($r3$.ɵdirectiveInject(TemplateRef)); },
features: [$r3$.ɵPublicFeature]
factory: function IfDirective_Factory(t) { return new (t || IfDirective)($r3$.ɵdirectiveInject(TemplateRef)); }
});`;
const MyComponentDefinition = `
const $c1$ = ["foo", ""];
@ -743,7 +733,6 @@ describe('compiler compliance', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 3,
vars: 0,
template: function MyComponent_Template(rf, ctx) {
@ -806,7 +795,6 @@ describe('compiler compliance', () => {
type: MyApp,
selectors: [["my-app"]],
factory: function MyApp_Factory(t) { return new (t || MyApp)(); },
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 3,
template: function MyApp_Template(rf, ctx) {
@ -888,7 +876,6 @@ describe('compiler compliance', () => {
type: MyApp,
selectors: [["my-app"]],
factory: function MyApp_Factory(t) { return new (t || MyApp)(); },
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 11,
template: function MyApp_Template(rf, ctx) {
@ -952,7 +939,6 @@ describe('compiler compliance', () => {
type: MyApp,
selectors: [["my-app"]],
factory: function MyApp_Factory(t) { return new (t || MyApp)(); },
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 3,
template: function MyApp_Template(rf, ctx) {
@ -1020,7 +1006,6 @@ describe('compiler compliance', () => {
type: MyApp,
selectors: [["my-app"]],
factory: function MyApp_Factory(t) { return new (t || MyApp)(); },
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 8,
template: function MyApp_Template(rf, ctx) {
@ -1079,7 +1064,6 @@ describe('compiler compliance', () => {
type: SimpleComponent,
selectors: [["simple"]],
factory: function SimpleComponent_Factory(t) { return new (t || SimpleComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 2,
vars: 0,
template: function SimpleComponent_Template(rf, ctx) {
@ -1102,7 +1086,6 @@ describe('compiler compliance', () => {
type: ComplexComponent,
selectors: [["complex"]],
factory: function ComplexComponent_Factory(t) { return new (t || ComplexComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 4,
vars: 0,
template: function ComplexComponent_Template(rf, ctx) {
@ -1171,7 +1154,6 @@ describe('compiler compliance', () => {
type: ViewQueryComponent,
selectors: [["view-query-component"]],
factory: function ViewQueryComponent_Factory(t) { return new (t || ViewQueryComponent)(); },
features: [$r3$.ɵPublicFeature],
viewQuery: function ViewQueryComponent_Query(rf, ctx) {
if (rf & 1) {
$r3$.ɵquery(0, SomeDirective, true);
@ -1348,9 +1330,9 @@ describe('compiler compliance', () => {
factory: function ContentQueryComponent_Factory(t) {
return new (t || ContentQueryComponent)();
},
contentQueries: function ContentQueryComponent_ContentQueries() {
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, true));
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, false));
contentQueries: function ContentQueryComponent_ContentQueries(dirIndex) {
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, true), dirIndex);
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, false), dirIndex);
},
contentQueriesRefresh: function ContentQueryComponent_ContentQueriesRefresh(dirIndex, queryStartIndex) {
const instance = $r3$.ɵload(dirIndex);
@ -1358,7 +1340,6 @@ describe('compiler compliance', () => {
($r3$.ɵqueryRefresh(($tmp$ = $r3$.ɵloadQueryList(queryStartIndex))) && ($instance$.someDir = $tmp$.first));
($r3$.ɵqueryRefresh(($tmp$ = $r3$.ɵloadQueryList((queryStartIndex + 1)))) && ($instance$.someDirList = $tmp$));
},
features: [$r3$.ɵPublicFeature],
consts: 2,
vars: 0,
template: function ContentQueryComponent_Template(rf, ctx) {
@ -1406,9 +1387,9 @@ describe('compiler compliance', () => {
ContentQueryComponent.ngComponentDef = $r3$.ɵdefineComponent({
contentQueries: function ContentQueryComponent_ContentQueries() {
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e0_attrs$, true));
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e1_attrs$, false));
contentQueries: function ContentQueryComponent_ContentQueries(dirIndex) {
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e0_attrs$, true), dirIndex);
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e1_attrs$, false), dirIndex);
},
contentQueriesRefresh: function ContentQueryComponent_ContentQueriesRefresh(dirIndex, queryStartIndex) {
const instance = $r3$.ɵload(dirIndex);
@ -1459,11 +1440,11 @@ describe('compiler compliance', () => {
ContentQueryComponent.ngComponentDef = $r3$.ɵdefineComponent({
contentQueries: function ContentQueryComponent_ContentQueries() {
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e0_attrs$ , true, TemplateRef));
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, true, ElementRef));
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e1_attrs$, false, ElementRef));
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, false, TemplateRef));
contentQueries: function ContentQueryComponent_ContentQueries(dirIndex) {
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e0_attrs$ , true, TemplateRef), dirIndex);
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, true, ElementRef), dirIndex);
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, $e1_attrs$, false, ElementRef), dirIndex);
$r3$.ɵregisterContentQuery($r3$.ɵquery(null, SomeDirective, false, TemplateRef), dirIndex);
},
contentQueriesRefresh: function ContentQueryComponent_ContentQueriesRefresh(dirIndex, queryStartIndex) {
const instance = $r3$.ɵload(dirIndex);
@ -1552,7 +1533,6 @@ describe('compiler compliance', () => {
type: MyApp,
selectors: [["my-app"]],
factory: function MyApp_Factory(t) { return new (t || MyApp)(); },
features: [$r3$.ɵPublicFeature],
consts: 6,
vars: 17,
template: function MyApp_Template(rf, ctx) {
@ -1616,7 +1596,6 @@ describe('compiler compliance', () => {
type: MyApp,
selectors: [["my-app"]],
factory: function MyApp_Factory(t) { return new (t || MyApp)(); },
features: [$r3$.ɵPublicFeature],
consts: 6,
vars: 27,
template: function MyApp_Template(rf, ctx) {
@ -1671,7 +1650,6 @@ describe('compiler compliance', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 3,
vars: 1,
template: function MyComponent_Template(rf, ctx) {
@ -1765,7 +1743,6 @@ describe('compiler compliance', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 6,
vars: 1,
template: function MyComponent_Template(rf, ctx) {
@ -1911,7 +1888,7 @@ describe('compiler compliance', () => {
selectors: [["lifecycle-comp"]],
factory: function LifecycleComp_Factory(t) { return new (t || LifecycleComp)(); },
inputs: {nameMin: "name"},
features: [$r3$PublicFeature, $r3$NgOnChangesFeature],
features: [$r3$.ɵNgOnChangesFeature],
consts: 0,
vars: 0,
template: function LifecycleComp_Template(rf, ctx) {}
@ -1922,7 +1899,6 @@ describe('compiler compliance', () => {
type: SimpleLayout,
selectors: [["simple-layout"]],
factory: function SimpleLayout_Factory(t) { return new (t || SimpleLayout)(); },
features: [$r3$.ɵPublicFeature],
consts: 2,
vars: 2,
template: function SimpleLayout_Template(rf, ctx) {
@ -2032,7 +2008,7 @@ describe('compiler compliance', () => {
factory: function ForOfDirective_Factory(t) {
return new (t || ForOfDirective)($r3$.ɵdirectiveInject(ViewContainerRef), $r3$.ɵdirectiveInject(TemplateRef));
},
features: [$r3$PublicFeature, $r3$NgOnChangesFeature],
features: [$r3$.ɵNgOnChangesFeature],
inputs: {forOf: "forOf"}
});
`;
@ -2052,7 +2028,6 @@ describe('compiler compliance', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 2,
vars: 1,
template: function MyComponent_Template(rf, ctx){
@ -2108,7 +2083,7 @@ describe('compiler compliance', () => {
factory: function ForOfDirective_Factory(t) {
return new (t || ForOfDirective)($r3$.ɵdirectiveInject(ViewContainerRef), $r3$.ɵdirectiveInject(TemplateRef));
},
features: [$r3$PublicFeature, $r3$NgOnChangesFeature],
features: [$r3$.ɵNgOnChangesFeature],
inputs: {forOf: "forOf"}
});
`;
@ -2131,7 +2106,6 @@ describe('compiler compliance', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 2,
vars: 1,
template: function MyComponent_Template(rf, ctx) {
@ -2231,7 +2205,6 @@ describe('compiler compliance', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 2,
vars: 1,
template: function MyComponent_Template(rf, ctx) {

View File

@ -42,7 +42,6 @@ describe('compiler compliance: directives', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 0,
template: function MyComponent_Template(rf, ctx) {
@ -88,7 +87,6 @@ describe('compiler compliance: directives', () => {
type: MyComponent,
selectors: [["my-component"]],
factory: function MyComponent_Factory(t) { return new (t || MyComponent)(); },
features: [$r3$.ɵPublicFeature],
consts: 1,
vars: 0,
template: function MyComponent_Template(rf, ctx) {

Some files were not shown because too many files have changed in this diff Show More