@dugararchit/cdk 0.0.0-dugararchit

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (206) hide show
  1. package/_index.scss +8 -0
  2. package/a11y/_index.import.scss +2 -0
  3. package/a11y/_index.scss +102 -0
  4. package/a11y/a11y-prebuilt.scss +3 -0
  5. package/fesm2022/stagefright5-cdk-a11y.mjs +2381 -0
  6. package/fesm2022/stagefright5-cdk-a11y.mjs.map +1 -0
  7. package/fesm2022/stagefright5-cdk-accordion.mjs +267 -0
  8. package/fesm2022/stagefright5-cdk-accordion.mjs.map +1 -0
  9. package/fesm2022/stagefright5-cdk-bidi.mjs +185 -0
  10. package/fesm2022/stagefright5-cdk-bidi.mjs.map +1 -0
  11. package/fesm2022/stagefright5-cdk-clipboard.mjs +250 -0
  12. package/fesm2022/stagefright5-cdk-clipboard.mjs.map +1 -0
  13. package/fesm2022/stagefright5-cdk-coercion.mjs +128 -0
  14. package/fesm2022/stagefright5-cdk-coercion.mjs.map +1 -0
  15. package/fesm2022/stagefright5-cdk-collections.mjs +472 -0
  16. package/fesm2022/stagefright5-cdk-collections.mjs.map +1 -0
  17. package/fesm2022/stagefright5-cdk-drag-drop.mjs +3690 -0
  18. package/fesm2022/stagefright5-cdk-drag-drop.mjs.map +1 -0
  19. package/fesm2022/stagefright5-cdk-keycodes.mjs +159 -0
  20. package/fesm2022/stagefright5-cdk-keycodes.mjs.map +1 -0
  21. package/fesm2022/stagefright5-cdk-layout.mjs +246 -0
  22. package/fesm2022/stagefright5-cdk-layout.mjs.map +1 -0
  23. package/fesm2022/stagefright5-cdk-observers.mjs +203 -0
  24. package/fesm2022/stagefright5-cdk-observers.mjs.map +1 -0
  25. package/fesm2022/stagefright5-cdk-overlay.mjs +3033 -0
  26. package/fesm2022/stagefright5-cdk-overlay.mjs.map +1 -0
  27. package/fesm2022/stagefright5-cdk-platform.mjs +375 -0
  28. package/fesm2022/stagefright5-cdk-platform.mjs.map +1 -0
  29. package/fesm2022/stagefright5-cdk-portal.mjs +672 -0
  30. package/fesm2022/stagefright5-cdk-portal.mjs.map +1 -0
  31. package/fesm2022/stagefright5-cdk-scrolling.mjs +1399 -0
  32. package/fesm2022/stagefright5-cdk-scrolling.mjs.map +1 -0
  33. package/fesm2022/stagefright5-cdk-stepper.mjs +624 -0
  34. package/fesm2022/stagefright5-cdk-stepper.mjs.map +1 -0
  35. package/fesm2022/stagefright5-cdk-table.mjs +2346 -0
  36. package/fesm2022/stagefright5-cdk-table.mjs.map +1 -0
  37. package/fesm2022/stagefright5-cdk-testing-protractor.mjs +324 -0
  38. package/fesm2022/stagefright5-cdk-testing-protractor.mjs.map +1 -0
  39. package/fesm2022/stagefright5-cdk-testing-selenium-webdriver.mjs +364 -0
  40. package/fesm2022/stagefright5-cdk-testing-selenium-webdriver.mjs.map +1 -0
  41. package/fesm2022/stagefright5-cdk-testing-testbed.mjs +806 -0
  42. package/fesm2022/stagefright5-cdk-testing-testbed.mjs.map +1 -0
  43. package/fesm2022/stagefright5-cdk-testing.mjs +740 -0
  44. package/fesm2022/stagefright5-cdk-testing.mjs.map +1 -0
  45. package/fesm2022/stagefright5-cdk-text-field.mjs +453 -0
  46. package/fesm2022/stagefright5-cdk-text-field.mjs.map +1 -0
  47. package/fesm2022/stagefright5-cdk-tree.mjs +945 -0
  48. package/fesm2022/stagefright5-cdk-tree.mjs.map +1 -0
  49. package/fesm2022/stagefright5-cdk.mjs +26 -0
  50. package/fesm2022/stagefright5-cdk.mjs.map +1 -0
  51. package/overlay/_index-deprecated.scss +13 -0
  52. package/overlay/_index.import.scss +13 -0
  53. package/overlay/_index.scss +148 -0
  54. package/overlay/overlay-prebuilt.scss +3 -0
  55. package/package.json +159 -0
  56. package/schematics/ng-update/test-cases/misc/global-stylesheets-test.scss +3 -0
  57. package/schematics/schematics/BUILD.bazel +104 -0
  58. package/schematics/schematics/README.md +4 -0
  59. package/schematics/schematics/collection.json +18 -0
  60. package/schematics/schematics/index.ts +22 -0
  61. package/schematics/schematics/migration.json +50 -0
  62. package/schematics/schematics/ng-add/index.spec.ts +50 -0
  63. package/schematics/schematics/ng-add/index.ts +39 -0
  64. package/schematics/schematics/ng-add/package-config.ts +62 -0
  65. package/schematics/schematics/ng-add/schema.json +16 -0
  66. package/schematics/schematics/ng-add/schema.ts +12 -0
  67. package/schematics/schematics/ng-generate/drag-drop/files/__path__/__name@dasherize@if-flat__/__name@dasherize__.component.__style__.template +53 -0
  68. package/schematics/schematics/ng-generate/drag-drop/files/__path__/__name@dasherize@if-flat__/__name@dasherize__.component.html.template +17 -0
  69. package/schematics/schematics/ng-generate/drag-drop/files/__path__/__name@dasherize@if-flat__/__name@dasherize__.component.spec.ts.template +29 -0
  70. package/schematics/schematics/ng-generate/drag-drop/files/__path__/__name@dasherize@if-flat__/__name@dasherize__.component.ts.template +43 -0
  71. package/schematics/schematics/ng-generate/drag-drop/index.spec.ts +205 -0
  72. package/schematics/schematics/ng-generate/drag-drop/index.ts +35 -0
  73. package/schematics/schematics/ng-generate/drag-drop/schema.json +93 -0
  74. package/schematics/schematics/ng-generate/drag-drop/schema.ts +11 -0
  75. package/schematics/schematics/ng-update/data/attribute-selectors.ts +29 -0
  76. package/schematics/schematics/ng-update/data/class-names.ts +50 -0
  77. package/schematics/schematics/ng-update/data/constructor-checks.ts +75 -0
  78. package/schematics/schematics/ng-update/data/css-selectors.ts +33 -0
  79. package/schematics/schematics/ng-update/data/element-selectors.ts +21 -0
  80. package/schematics/schematics/ng-update/data/index.ts +18 -0
  81. package/schematics/schematics/ng-update/data/input-names.ts +118 -0
  82. package/schematics/schematics/ng-update/data/method-call-checks.ts +63 -0
  83. package/schematics/schematics/ng-update/data/output-names.ts +42 -0
  84. package/schematics/schematics/ng-update/data/property-names.ts +151 -0
  85. package/schematics/schematics/ng-update/data/symbol-removal.ts +22 -0
  86. package/schematics/schematics/ng-update/devkit-file-system.ts +87 -0
  87. package/schematics/schematics/ng-update/devkit-migration-rule.ts +185 -0
  88. package/schematics/schematics/ng-update/devkit-migration.ts +47 -0
  89. package/schematics/schematics/ng-update/find-stylesheets.ts +43 -0
  90. package/schematics/schematics/ng-update/html-parsing/angular.ts +49 -0
  91. package/schematics/schematics/ng-update/html-parsing/elements.ts +66 -0
  92. package/schematics/schematics/ng-update/index.ts +113 -0
  93. package/schematics/schematics/ng-update/migrations/attribute-selectors.ts +83 -0
  94. package/schematics/schematics/ng-update/migrations/class-inheritance.ts +63 -0
  95. package/schematics/schematics/ng-update/migrations/class-names.ts +107 -0
  96. package/schematics/schematics/ng-update/migrations/constructor-signature.ts +170 -0
  97. package/schematics/schematics/ng-update/migrations/css-selectors.ts +83 -0
  98. package/schematics/schematics/ng-update/migrations/element-selectors.ts +75 -0
  99. package/schematics/schematics/ng-update/migrations/input-names.ts +83 -0
  100. package/schematics/schematics/ng-update/migrations/method-call-arguments.ts +70 -0
  101. package/schematics/schematics/ng-update/migrations/misc-template.ts +36 -0
  102. package/schematics/schematics/ng-update/migrations/output-names.ts +61 -0
  103. package/schematics/schematics/ng-update/migrations/property-names.ts +61 -0
  104. package/schematics/schematics/ng-update/migrations/symbol-removal.ts +51 -0
  105. package/schematics/schematics/ng-update/migrations/tilde-import-v13/tilde-import-migration.ts +40 -0
  106. package/schematics/schematics/ng-update/public-api.ts +18 -0
  107. package/schematics/schematics/ng-update/test-cases/index.spec.ts +18 -0
  108. package/schematics/schematics/ng-update/test-cases/misc/external-resource-resolution.spec.ts +32 -0
  109. package/schematics/schematics/ng-update/test-cases/misc/external-resource-resolution_input.ts +22 -0
  110. package/schematics/schematics/ng-update/test-cases/misc/global-stylesheets-test.scss +3 -0
  111. package/schematics/schematics/ng-update/test-cases/misc/global-stylesheets.spec.ts +50 -0
  112. package/schematics/schematics/ng-update/test-cases/misc/global-stylesheets_input.ts +8 -0
  113. package/schematics/schematics/ng-update/test-cases/misc/method-call-checks.spec.ts +20 -0
  114. package/schematics/schematics/ng-update/test-cases/misc/method-call-checks_input.ts +18 -0
  115. package/schematics/schematics/ng-update/test-cases/misc/module-resolution.spec.ts +27 -0
  116. package/schematics/schematics/ng-update/test-cases/v13/misc/tilde-import-v13.spec.ts +149 -0
  117. package/schematics/schematics/ng-update/test-cases/v6/attribute-selectors_expected_output.ts +36 -0
  118. package/schematics/schematics/ng-update/test-cases/v6/attribute-selectors_input.ts +36 -0
  119. package/schematics/schematics/ng-update/test-cases/v6/class-names_expected_output.ts +8 -0
  120. package/schematics/schematics/ng-update/test-cases/v6/class-names_input.ts +8 -0
  121. package/schematics/schematics/ng-update/test-cases/v6/input-names_expected_output.ts +22 -0
  122. package/schematics/schematics/ng-update/test-cases/v6/input-names_input.ts +22 -0
  123. package/schematics/schematics/ng-update/test-cases/v6/property-names_expected_output.ts +64 -0
  124. package/schematics/schematics/ng-update/test-cases/v6/property-names_input.ts +64 -0
  125. package/schematics/schematics/ng-update/test-cases/v7/property-names_expected_output.ts +28 -0
  126. package/schematics/schematics/ng-update/test-cases/v7/property-names_input.ts +28 -0
  127. package/schematics/schematics/ng-update/typescript/base-types.ts +22 -0
  128. package/schematics/schematics/ng-update/typescript/imports.ts +54 -0
  129. package/schematics/schematics/ng-update/typescript/literal.ts +32 -0
  130. package/schematics/schematics/ng-update/typescript/module-specifiers.ts +39 -0
  131. package/schematics/schematics/ng-update/update-schematic.md +209 -0
  132. package/schematics/schematics/ng-update/upgrade-data.ts +79 -0
  133. package/schematics/schematics/paths.ts +15 -0
  134. package/schematics/schematics/testing/BUILD.bazel +27 -0
  135. package/schematics/schematics/testing/file-content.ts +20 -0
  136. package/schematics/schematics/testing/index.ts +14 -0
  137. package/schematics/schematics/testing/post-scheduled-tasks.ts +45 -0
  138. package/schematics/schematics/testing/resolve-bazel-path.ts +46 -0
  139. package/schematics/schematics/testing/test-app.ts +21 -0
  140. package/schematics/schematics/testing/test-case-setup.ts +236 -0
  141. package/schematics/schematics/testing/test-library.ts +21 -0
  142. package/schematics/schematics/testing/test-project.ts +40 -0
  143. package/schematics/schematics/testing/tsconfig.json +7 -0
  144. package/schematics/schematics/tsconfig.json +28 -0
  145. package/schematics/schematics/update-tool/BUILD.bazel +19 -0
  146. package/schematics/schematics/update-tool/component-resource-collector.ts +195 -0
  147. package/schematics/schematics/update-tool/file-system.ts +78 -0
  148. package/schematics/schematics/update-tool/index.ts +191 -0
  149. package/schematics/schematics/update-tool/logger.ts +23 -0
  150. package/schematics/schematics/update-tool/migration.ts +88 -0
  151. package/schematics/schematics/update-tool/public-api.ts +16 -0
  152. package/schematics/schematics/update-tool/target-version.ts +31 -0
  153. package/schematics/schematics/update-tool/tsconfig.json +7 -0
  154. package/schematics/schematics/update-tool/update-recorder.ts +14 -0
  155. package/schematics/schematics/update-tool/utils/decorators.ts +54 -0
  156. package/schematics/schematics/update-tool/utils/functions.ts +18 -0
  157. package/schematics/schematics/update-tool/utils/imports.ts +128 -0
  158. package/schematics/schematics/update-tool/utils/line-mappings.ts +84 -0
  159. package/schematics/schematics/update-tool/utils/parse-tsconfig.ts +25 -0
  160. package/schematics/schematics/update-tool/utils/property-name.ts +28 -0
  161. package/schematics/schematics/update-tool/utils/virtual-host.ts +116 -0
  162. package/schematics/schematics/update-tool/version-changes.ts +49 -0
  163. package/schematics/schematics/utils/ast/ng-module-imports.spec.ts +43 -0
  164. package/schematics/schematics/utils/ast/ng-module-imports.ts +102 -0
  165. package/schematics/schematics/utils/ast.ts +88 -0
  166. package/schematics/schematics/utils/build-component.ts +252 -0
  167. package/schematics/schematics/utils/get-project.ts +27 -0
  168. package/schematics/schematics/utils/html-manipulation.ts +105 -0
  169. package/schematics/schematics/utils/index.ts +19 -0
  170. package/schematics/schematics/utils/parse5-element.ts +34 -0
  171. package/schematics/schematics/utils/project-index-file.ts +21 -0
  172. package/schematics/schematics/utils/project-main-file.ts +26 -0
  173. package/schematics/schematics/utils/project-style-file.ts +53 -0
  174. package/schematics/schematics/utils/project-targets.ts +43 -0
  175. package/schematics/schematics/utils/project-tsconfig-paths.spec.ts +91 -0
  176. package/schematics/schematics/utils/project-tsconfig-paths.ts +49 -0
  177. package/schematics/schematics/utils/schematic-options.ts +65 -0
  178. package/schematics/schematics/utils/vendored-ast-utils/index.ts +599 -0
  179. package/scrolling/virtual-scroll-viewport.scss +87 -0
  180. package/table/table.scss +3 -0
  181. package/text-field/_index.import.scss +2 -0
  182. package/text-field/_index.scss +89 -0
  183. package/text-field/text-field-prebuilt.scss +4 -0
  184. package/types/stagefright5-cdk-a11y.d.ts +1160 -0
  185. package/types/stagefright5-cdk-accordion.d.ts +95 -0
  186. package/types/stagefright5-cdk-bidi.d.ts +95 -0
  187. package/types/stagefright5-cdk-clipboard.d.ts +116 -0
  188. package/types/stagefright5-cdk-coercion.d.ts +101 -0
  189. package/types/stagefright5-cdk-collections.d.ts +405 -0
  190. package/types/stagefright5-cdk-drag-drop.d.ts +1471 -0
  191. package/types/stagefright5-cdk-keycodes.d.ts +142 -0
  192. package/types/stagefright5-cdk-layout.d.ts +96 -0
  193. package/types/stagefright5-cdk-observers.d.ts +91 -0
  194. package/types/stagefright5-cdk-overlay.d.ts +1258 -0
  195. package/types/stagefright5-cdk-platform.d.ts +130 -0
  196. package/types/stagefright5-cdk-portal.d.ts +327 -0
  197. package/types/stagefright5-cdk-scrolling.d.ts +631 -0
  198. package/types/stagefright5-cdk-stepper.d.ts +302 -0
  199. package/types/stagefright5-cdk-table.d.ts +1128 -0
  200. package/types/stagefright5-cdk-testing-protractor.d.ts +146 -0
  201. package/types/stagefright5-cdk-testing-selenium-webdriver.d.ts +161 -0
  202. package/types/stagefright5-cdk-testing-testbed.d.ts +168 -0
  203. package/types/stagefright5-cdk-testing.d.ts +735 -0
  204. package/types/stagefright5-cdk-text-field.d.ts +171 -0
  205. package/types/stagefright5-cdk-tree.d.ts +522 -0
  206. package/types/stagefright5-cdk.d.ts +14 -0
@@ -0,0 +1,252 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {strings, template as interpolateTemplate} from '@angular-devkit/core';
10
+ import {
11
+ apply,
12
+ applyTemplates,
13
+ branchAndMerge,
14
+ chain,
15
+ filter,
16
+ mergeWith,
17
+ move,
18
+ noop,
19
+ Rule,
20
+ SchematicsException,
21
+ Tree,
22
+ url,
23
+ } from '@angular-devkit/schematics';
24
+ import {FileSystemSchematicContext} from '@angular-devkit/schematics/tools';
25
+ import {Schema as ComponentOptions, Style} from '@schematics/angular/component/schema';
26
+ import {InsertChange} from '@schematics/angular/utility/change';
27
+ import {getWorkspace} from '@schematics/angular/utility/workspace';
28
+ import {buildRelativePath, findModuleFromOptions} from '@schematics/angular/utility/find-module';
29
+ import {parseName} from '@schematics/angular/utility/parse-name';
30
+ import {validateHtmlSelector} from '@schematics/angular/utility/validation';
31
+ import {ProjectType} from '@schematics/angular/utility/workspace-models';
32
+ import {readFileSync, statSync} from 'fs';
33
+ import {dirname, join, resolve} from 'path';
34
+ import * as ts from 'typescript';
35
+ import {addDeclarationToModule, addExportToModule} from '../utils/vendored-ast-utils';
36
+ import {getProjectFromWorkspace} from './get-project';
37
+ import {getDefaultComponentOptions} from './schematic-options';
38
+ import {ProjectDefinition} from '@angular-devkit/core/src/workspace';
39
+
40
+ /**
41
+ * Build a default project path for generating.
42
+ * @param project The project to build the path for.
43
+ */
44
+ function buildDefaultPath(project: ProjectDefinition): string {
45
+ const root = project.sourceRoot ? `/${project.sourceRoot}/` : `/${project.root}/src/`;
46
+
47
+ const projectDirName = project.extensions.projectType === ProjectType.Application ? 'app' : 'lib';
48
+
49
+ return `${root}${projectDirName}`;
50
+ }
51
+
52
+ /**
53
+ * List of style extensions which are CSS compatible. All supported CLI style extensions can be
54
+ * found here: angular/angular-cli/main/packages/schematics/angular/ng-new/schema.json#L118-L122
55
+ */
56
+ const supportedCssExtensions = ['css', 'scss', 'less'];
57
+
58
+ function readIntoSourceFile(host: Tree, modulePath: string) {
59
+ const text = host.read(modulePath);
60
+ if (text === null) {
61
+ throw new SchematicsException(`File ${modulePath} does not exist.`);
62
+ }
63
+
64
+ return ts.createSourceFile(modulePath, text.toString('utf-8'), ts.ScriptTarget.Latest, true);
65
+ }
66
+
67
+ function addDeclarationToNgModule(options: ComponentOptions): Rule {
68
+ return (host: Tree) => {
69
+ if (options.skipImport || !options.module) {
70
+ return host;
71
+ }
72
+
73
+ const modulePath = options.module;
74
+ let source = readIntoSourceFile(host, modulePath);
75
+
76
+ const componentPath =
77
+ `/${options.path}/` +
78
+ (options.flat ? '' : strings.dasherize(options.name) + '/') +
79
+ strings.dasherize(options.name) +
80
+ '.component';
81
+ const relativePath = buildRelativePath(modulePath, componentPath);
82
+ const classifiedName = strings.classify(`${options.name}Component`);
83
+
84
+ const declarationChanges = addDeclarationToModule(
85
+ source,
86
+ modulePath,
87
+ classifiedName,
88
+ relativePath,
89
+ );
90
+
91
+ const declarationRecorder = host.beginUpdate(modulePath);
92
+ for (const change of declarationChanges) {
93
+ if (change instanceof InsertChange) {
94
+ declarationRecorder.insertLeft(change.pos, change.toAdd);
95
+ }
96
+ }
97
+ host.commitUpdate(declarationRecorder);
98
+
99
+ if (options.export) {
100
+ // Need to refresh the AST because we overwrote the file in the host.
101
+ source = readIntoSourceFile(host, modulePath);
102
+
103
+ const exportRecorder = host.beginUpdate(modulePath);
104
+ const exportChanges = addExportToModule(
105
+ source,
106
+ modulePath,
107
+ strings.classify(`${options.name}Component`),
108
+ relativePath,
109
+ );
110
+
111
+ for (const change of exportChanges) {
112
+ if (change instanceof InsertChange) {
113
+ exportRecorder.insertLeft(change.pos, change.toAdd);
114
+ }
115
+ }
116
+ host.commitUpdate(exportRecorder);
117
+ }
118
+
119
+ return host;
120
+ };
121
+ }
122
+
123
+ function buildSelector(options: ComponentOptions, projectPrefix?: string) {
124
+ let selector = strings.dasherize(options.name);
125
+ if (options.prefix) {
126
+ selector = `${options.prefix}-${selector}`;
127
+ } else if (options.prefix === undefined && projectPrefix) {
128
+ selector = `${projectPrefix}-${selector}`;
129
+ }
130
+
131
+ return selector;
132
+ }
133
+
134
+ /**
135
+ * Indents the text content with the amount of specified spaces. The spaces will be added after
136
+ * every line-break. This utility function can be used inside of EJS templates to properly
137
+ * include the additional files.
138
+ */
139
+ function indentTextContent(text: string, numSpaces: number): string {
140
+ // In the Material project there should be only LF line-endings, but the schematic files
141
+ // are not being linted and therefore there can be also CRLF or just CR line-endings.
142
+ return text.replace(/(\r\n|\r|\n)/g, `$1${' '.repeat(numSpaces)}`);
143
+ }
144
+
145
+ /**
146
+ * Rule that copies and interpolates the files that belong to this schematic context. Additionally
147
+ * a list of file paths can be passed to this rule in order to expose them inside the EJS
148
+ * template context.
149
+ *
150
+ * This allows inlining the external template or stylesheet files in EJS without having
151
+ * to manually duplicate the file content.
152
+ */
153
+ export function buildComponent(
154
+ options: ComponentOptions,
155
+ additionalFiles: {[key: string]: string} = {},
156
+ ): Rule {
157
+ return async (host, ctx) => {
158
+ const context = ctx as FileSystemSchematicContext;
159
+ const workspace = await getWorkspace(host);
160
+ const project = getProjectFromWorkspace(workspace, options.project);
161
+ const defaultComponentOptions = getDefaultComponentOptions(project);
162
+
163
+ // TODO(devversion): Remove if we drop support for older CLI versions.
164
+ // This handles an unreported breaking change from the @angular-devkit/schematics. Previously
165
+ // the description path resolved to the factory file, but starting from 6.2.0, it resolves
166
+ // to the factory directory.
167
+ const schematicPath = statSync(context.schematic.description.path).isDirectory()
168
+ ? context.schematic.description.path
169
+ : dirname(context.schematic.description.path);
170
+
171
+ const schematicFilesUrl = './files';
172
+ const schematicFilesPath = resolve(schematicPath, schematicFilesUrl);
173
+
174
+ // Add the default component option values to the options if an option is not explicitly
175
+ // specified but a default component option is available.
176
+ Object.keys(options)
177
+ .filter(
178
+ key =>
179
+ options[key as keyof ComponentOptions] == null &&
180
+ defaultComponentOptions[key as keyof ComponentOptions],
181
+ )
182
+ .forEach(
183
+ key =>
184
+ ((options as any)[key] = (defaultComponentOptions as ComponentOptions)[
185
+ key as keyof ComponentOptions
186
+ ]),
187
+ );
188
+
189
+ if (options.path === undefined) {
190
+ // TODO(jelbourn): figure out if the need for this `as any` is a bug due to two different
191
+ // incompatible `ProjectDefinition` classes in @angular-devkit
192
+ options.path = buildDefaultPath(project as any);
193
+ }
194
+
195
+ options.module = findModuleFromOptions(host, options);
196
+
197
+ const parsedPath = parseName(options.path!, options.name);
198
+
199
+ options.name = parsedPath.name;
200
+ options.path = parsedPath.path;
201
+ options.selector = options.selector || buildSelector(options, project.prefix);
202
+
203
+ validateHtmlSelector(options.selector!);
204
+
205
+ // In case the specified style extension is not part of the supported CSS supersets,
206
+ // we generate the stylesheets with the "css" extension. This ensures that we don't
207
+ // accidentally generate invalid stylesheets (e.g. drag-drop-comp.styl) which will
208
+ // break the Angular CLI project. See: https://github.com/angular/components/issues/15164
209
+ if (!supportedCssExtensions.includes(options.style!)) {
210
+ // TODO: Cast is necessary as we can't use the Style enum which has been introduced
211
+ // within CLI v7.3.0-rc.0. This would break the schematic for older CLI versions.
212
+ options.style = 'css' as Style;
213
+ }
214
+
215
+ // Object that will be used as context for the EJS templates.
216
+ const baseTemplateContext = {
217
+ ...strings,
218
+ 'if-flat': (s: string) => (options.flat ? '' : s),
219
+ ...options,
220
+ };
221
+
222
+ // Key-value object that includes the specified additional files with their loaded content.
223
+ // The resolved contents can be used inside EJS templates.
224
+ const resolvedFiles: Record<string, string> = {};
225
+
226
+ for (let key in additionalFiles) {
227
+ if (additionalFiles[key]) {
228
+ const fileContent = readFileSync(join(schematicFilesPath, additionalFiles[key]), 'utf-8');
229
+
230
+ // Interpolate the additional files with the base EJS template context.
231
+ resolvedFiles[key] = interpolateTemplate(fileContent)(baseTemplateContext);
232
+ }
233
+ }
234
+
235
+ const templateSource = apply(url(schematicFilesUrl), [
236
+ options.skipTests ? filter(path => !path.endsWith('.spec.ts.template')) : noop(),
237
+ options.inlineStyle ? filter(path => !path.endsWith('.__style__.template')) : noop(),
238
+ options.inlineTemplate ? filter(path => !path.endsWith('.html.template')) : noop(),
239
+ // Treat the template options as any, because the type definition for the template options
240
+ // is made unnecessarily explicit. Every type of object can be used in the EJS template.
241
+ applyTemplates({indentTextContent, resolvedFiles, ...baseTemplateContext} as any),
242
+ // TODO(devversion): figure out why we cannot just remove the first parameter
243
+ // See for example: angular-cli#schematics/angular/component/index.ts#L160
244
+ move(null as any, parsedPath.path),
245
+ ]);
246
+
247
+ return () =>
248
+ chain([
249
+ branchAndMerge(chain([addDeclarationToNgModule(options), mergeWith(templateSource)])),
250
+ ])(host, context);
251
+ };
252
+ }
@@ -0,0 +1,27 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {ProjectDefinition, WorkspaceDefinition} from '@angular-devkit/core/src/workspace';
10
+ import {SchematicsException} from '@angular-devkit/schematics';
11
+
12
+ /**
13
+ * Finds the specified project configuration in the workspace. Throws an error if the project
14
+ * couldn't be found.
15
+ */
16
+ export function getProjectFromWorkspace(
17
+ workspace: WorkspaceDefinition,
18
+ projectName = workspace.extensions.defaultProject as string,
19
+ ): ProjectDefinition {
20
+ const project = workspace.projects.get(projectName);
21
+
22
+ if (!project) {
23
+ throw new SchematicsException(`Could not find project in workspace: ${projectName}`);
24
+ }
25
+
26
+ return project;
27
+ }
@@ -0,0 +1,105 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {SchematicsException, Tree} from '@angular-devkit/schematics';
10
+ import {getChildElementIndentation} from './parse5-element';
11
+ import {Element, parse as parseHtml} from 'parse5';
12
+
13
+ /** Appends the given element HTML fragment to the `<head>` element of the specified HTML file. */
14
+ export function appendHtmlElementToHead(host: Tree, htmlFilePath: string, elementHtml: string) {
15
+ const htmlFileBuffer = host.read(htmlFilePath);
16
+
17
+ if (!htmlFileBuffer) {
18
+ throw new SchematicsException(`Could not read file for path: ${htmlFilePath}`);
19
+ }
20
+
21
+ const htmlContent = htmlFileBuffer.toString();
22
+
23
+ if (htmlContent.includes(elementHtml)) {
24
+ return;
25
+ }
26
+
27
+ const headTag = getHtmlHeadTagElement(htmlContent);
28
+
29
+ if (!headTag) {
30
+ throw Error(`Could not find '<head>' element in HTML file: ${htmlFileBuffer}`);
31
+ }
32
+
33
+ // We always have access to the source code location here because the `getHeadTagElement`
34
+ // function explicitly has the `sourceCodeLocationInfo` option enabled.
35
+ const endTagOffset = headTag.sourceCodeLocation!.endTag.startOffset;
36
+ const indentationOffset = getChildElementIndentation(headTag);
37
+ const insertion = `${' '.repeat(indentationOffset)}${elementHtml}`;
38
+
39
+ const recordedChange = host.beginUpdate(htmlFilePath).insertRight(endTagOffset, `${insertion}\n`);
40
+
41
+ host.commitUpdate(recordedChange);
42
+ }
43
+
44
+ /** Parses the given HTML file and returns the head element if available. */
45
+ export function getHtmlHeadTagElement(htmlContent: string): Element | null {
46
+ return getElementByTagName('head', htmlContent);
47
+ }
48
+
49
+ /** Adds a class to the body of the document. */
50
+ export function addBodyClass(host: Tree, htmlFilePath: string, className: string): void {
51
+ const htmlFileBuffer = host.read(htmlFilePath);
52
+
53
+ if (!htmlFileBuffer) {
54
+ throw new SchematicsException(`Could not read file for path: ${htmlFilePath}`);
55
+ }
56
+
57
+ const htmlContent = htmlFileBuffer.toString();
58
+ const body = getElementByTagName('body', htmlContent);
59
+
60
+ if (!body) {
61
+ throw Error(`Could not find <body> element in HTML file: ${htmlFileBuffer}`);
62
+ }
63
+
64
+ const classAttribute = body.attrs.find(attribute => attribute.name === 'class');
65
+
66
+ if (classAttribute) {
67
+ const hasClass = classAttribute.value
68
+ .split(' ')
69
+ .map(part => part.trim())
70
+ .includes(className);
71
+
72
+ if (!hasClass) {
73
+ // We have source code location info enabled, and we pre-checked that the element
74
+ // has attributes, specifically the `class` attribute.
75
+ const classAttributeLocation = body.sourceCodeLocation!.attrs!.class;
76
+ const recordedChange = host
77
+ .beginUpdate(htmlFilePath)
78
+ .insertRight(classAttributeLocation.endOffset - 1, ` ${className}`);
79
+ host.commitUpdate(recordedChange);
80
+ }
81
+ } else {
82
+ const recordedChange = host
83
+ .beginUpdate(htmlFilePath)
84
+ .insertRight(body.sourceCodeLocation!.startTag.endOffset - 1, ` class="${className}"`);
85
+ host.commitUpdate(recordedChange);
86
+ }
87
+ }
88
+
89
+ /** Finds an element by its tag name. */
90
+ function getElementByTagName(tagName: string, htmlContent: string): Element | null {
91
+ const document = parseHtml(htmlContent, {sourceCodeLocationInfo: true});
92
+ const nodeQueue = [...document.childNodes];
93
+
94
+ while (nodeQueue.length) {
95
+ const node = nodeQueue.shift() as Element;
96
+
97
+ if (node.nodeName.toLowerCase() === tagName) {
98
+ return node;
99
+ } else if (node.childNodes) {
100
+ nodeQueue.push(...node.childNodes);
101
+ }
102
+ }
103
+
104
+ return null;
105
+ }
@@ -0,0 +1,19 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ export * from './ast';
10
+ export * from './ast/ng-module-imports';
11
+ export * from './build-component';
12
+ export * from './get-project';
13
+ export * from './html-manipulation';
14
+ export * from './parse5-element';
15
+ export * from './project-index-file';
16
+ export * from './project-main-file';
17
+ export * from './project-style-file';
18
+ export * from './project-targets';
19
+ export * from './schematic-options';
@@ -0,0 +1,34 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {SchematicsException} from '@angular-devkit/schematics';
10
+ import {Element} from 'parse5';
11
+
12
+ /** Determines the indentation of child elements for the given Parse5 element. */
13
+ export function getChildElementIndentation(element: Element) {
14
+ const childElement = element.childNodes.find(node => (node as Element).tagName) as Element | null;
15
+
16
+ if ((childElement && !childElement.sourceCodeLocation) || !element.sourceCodeLocation) {
17
+ throw new SchematicsException(
18
+ 'Cannot determine child element indentation because the ' +
19
+ 'specified Parse5 element does not have any source code location metadata.',
20
+ );
21
+ }
22
+
23
+ const startColumns = childElement
24
+ ? // In case there are child elements inside of the element, we assume that their
25
+ // indentation is also applicable for other child elements.
26
+ childElement.sourceCodeLocation!.startCol
27
+ : // In case there is no child element, we just assume that child elements should be indented
28
+ // by two spaces.
29
+ element.sourceCodeLocation!.startCol + 2;
30
+
31
+ // Since Parse5 does not set the `startCol` properties as zero-based, we need to subtract
32
+ // one column in order to have a proper zero-based offset for the indentation.
33
+ return startColumns - 1;
34
+ }
@@ -0,0 +1,21 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {Path} from '@angular-devkit/core';
10
+ import {ProjectDefinition} from '@angular-devkit/core/src/workspace';
11
+ import {defaultTargetBuilders, getTargetsByBuilderName} from './project-targets';
12
+
13
+ /** Gets the path of the index file in the given project. */
14
+ export function getProjectIndexFiles(project: ProjectDefinition): Path[] {
15
+ const paths = getTargetsByBuilderName(project, defaultTargetBuilders.build)
16
+ .filter(t => t.options?.index)
17
+ .map(t => t.options!.index as Path);
18
+
19
+ // Use a set to remove duplicate index files referenced in multiple build targets of a project.
20
+ return Array.from(new Set(paths));
21
+ }
@@ -0,0 +1,26 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {Path} from '@angular-devkit/core';
10
+ import {ProjectDefinition} from '@angular-devkit/core/src/workspace';
11
+ import {SchematicsException} from '@angular-devkit/schematics';
12
+ import {getProjectTargetOptions} from './project-targets';
13
+
14
+ /** Looks for the main TypeScript file in the given project and returns its path. */
15
+ export function getProjectMainFile(project: ProjectDefinition): Path {
16
+ const buildOptions = getProjectTargetOptions(project, 'build');
17
+
18
+ if (!buildOptions.main) {
19
+ throw new SchematicsException(
20
+ `Could not find the project main file inside of the ` +
21
+ `workspace config (${project.sourceRoot})`,
22
+ );
23
+ }
24
+
25
+ return buildOptions.main as Path;
26
+ }
@@ -0,0 +1,53 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {isJsonArray, normalize} from '@angular-devkit/core';
10
+ import {ProjectDefinition} from '@angular-devkit/core/src/workspace';
11
+ import {getProjectTargetOptions} from './project-targets';
12
+
13
+ /** Regular expression that matches all possible Angular CLI default style files. */
14
+ const defaultStyleFileRegex = /styles\.(c|le|sc)ss/;
15
+
16
+ /** Regular expression that matches all files that have a proper stylesheet extension. */
17
+ const validStyleFileRegex = /\.(c|le|sc)ss/;
18
+
19
+ /**
20
+ * Gets a style file with the given extension in a project and returns its path. If no
21
+ * extension is specified, any style file with a valid extension will be returned.
22
+ */
23
+ export function getProjectStyleFile(project: ProjectDefinition, extension?: string): string | null {
24
+ const buildOptions = getProjectTargetOptions(project, 'build');
25
+ if (buildOptions.styles && isJsonArray(buildOptions.styles) && buildOptions.styles.length) {
26
+ const styles = buildOptions.styles.map(s =>
27
+ typeof s === 'string' ? s : (s as {input: string}).input,
28
+ );
29
+
30
+ // Look for the default style file that is generated for new projects by the Angular CLI. This
31
+ // default style file is usually called `styles.ext` unless it has been changed explicitly.
32
+ const defaultMainStylePath = styles.find(file =>
33
+ extension ? file === `styles.${extension}` : defaultStyleFileRegex.test(file),
34
+ );
35
+
36
+ if (defaultMainStylePath) {
37
+ return normalize(defaultMainStylePath);
38
+ }
39
+
40
+ // If no default style file could be found, use the first style file that matches the given
41
+ // extension. If no extension specified explicitly, we look for any file with a valid style
42
+ // file extension.
43
+ const fallbackStylePath = styles.find(file =>
44
+ extension ? file.endsWith(`.${extension}`) : validStyleFileRegex.test(file),
45
+ );
46
+
47
+ if (fallbackStylePath) {
48
+ return normalize(fallbackStylePath);
49
+ }
50
+ }
51
+
52
+ return null;
53
+ }
@@ -0,0 +1,43 @@
1
+ /**
2
+ * @license
3
+ * Copyright Google LLC All Rights Reserved.
4
+ *
5
+ * Use of this source code is governed by an MIT-style license that can be
6
+ * found in the LICENSE file at https://angular.io/license
7
+ */
8
+
9
+ import {ProjectDefinition, TargetDefinition} from '@angular-devkit/core/src/workspace';
10
+ import {JsonValue} from '@angular-devkit/core';
11
+ import {SchematicsException} from '@angular-devkit/schematics';
12
+
13
+ /** Object that maps a CLI target to its default builder name. */
14
+ export const defaultTargetBuilders = {
15
+ build: '@angular-devkit/build-angular:browser',
16
+ test: '@angular-devkit/build-angular:karma',
17
+ };
18
+
19
+ /** Resolves the architect options for the build target of the given project. */
20
+ export function getProjectTargetOptions(
21
+ project: ProjectDefinition,
22
+ buildTarget: string,
23
+ ): Record<string, JsonValue | undefined> {
24
+ const options = project.targets?.get(buildTarget)?.options;
25
+
26
+ if (!options) {
27
+ throw new SchematicsException(
28
+ `Cannot determine project target configuration for: ${buildTarget}.`,
29
+ );
30
+ }
31
+
32
+ return options;
33
+ }
34
+
35
+ /** Gets all targets from the given project that match the specified builder name. */
36
+ export function getTargetsByBuilderName(
37
+ project: ProjectDefinition,
38
+ builderName: string,
39
+ ): TargetDefinition[] {
40
+ return Array.from(project.targets.keys())
41
+ .filter(name => project.targets.get(name)?.builder === builderName)
42
+ .map(name => project.targets.get(name)!);
43
+ }
@@ -0,0 +1,91 @@
1
+ import {HostTree} from '@angular-devkit/schematics';
2
+ import {UnitTestTree} from '@angular-devkit/schematics/testing';
3
+ import {WorkspacePath} from '../update-tool/file-system';
4
+ import {getTargetTsconfigPath, getWorkspaceConfigGracefully} from './project-tsconfig-paths';
5
+
6
+ describe('project tsconfig paths', () => {
7
+ let testTree: UnitTestTree;
8
+
9
+ beforeEach(() => {
10
+ testTree = new UnitTestTree(new HostTree());
11
+ });
12
+
13
+ it('should detect build tsconfig path inside of angular.json file', async () => {
14
+ testTree.create('/my-custom-config.json', '');
15
+ testTree.create(
16
+ '/angular.json',
17
+ JSON.stringify({
18
+ version: 1,
19
+ projects: {my_name: {architect: {build: {options: {tsConfig: './my-custom-config.json'}}}}},
20
+ }),
21
+ );
22
+
23
+ const config = await getWorkspaceConfigGracefully(testTree);
24
+ expect(config).not.toBeNull();
25
+ expect(getTargetTsconfigPath(config!.projects!.get('my_name')!, 'build')).toEqual(
26
+ 'my-custom-config.json' as WorkspacePath,
27
+ );
28
+ });
29
+
30
+ it('should be able to read workspace configuration which is using JSON5 features', async () => {
31
+ testTree.create('/my-build-config.json', '');
32
+ testTree.create(
33
+ '/angular.json',
34
+ `{
35
+ // Comments, unquoted properties or trailing commas are only supported in JSON5.
36
+ version: 1,
37
+ projects: {
38
+ with_tests: {
39
+ targets: {
40
+ build: {
41
+ options: {
42
+ tsConfig: './my-build-config.json',
43
+ }
44
+ }
45
+ }
46
+ }
47
+ },
48
+ }`,
49
+ );
50
+
51
+ const config = await getWorkspaceConfigGracefully(testTree);
52
+ expect(config).not.toBeNull();
53
+ expect(getTargetTsconfigPath(config!.projects.get('with_tests')!, 'build')).toEqual(
54
+ 'my-build-config.json' as WorkspacePath,
55
+ );
56
+ });
57
+
58
+ it('should detect test tsconfig path inside of angular.json file', async () => {
59
+ testTree.create('/my-test-config.json', '');
60
+ testTree.create(
61
+ '/angular.json',
62
+ JSON.stringify({
63
+ version: 1,
64
+ projects: {my_name: {architect: {test: {options: {tsConfig: './my-test-config.json'}}}}},
65
+ }),
66
+ );
67
+
68
+ const config = await getWorkspaceConfigGracefully(testTree);
69
+ expect(config).not.toBeNull();
70
+ expect(getTargetTsconfigPath(config!.projects.get('my_name')!, 'test')).toEqual(
71
+ 'my-test-config.json' as WorkspacePath,
72
+ );
73
+ });
74
+
75
+ it('should detect test tsconfig path inside of .angular.json file', async () => {
76
+ testTree.create('/my-test-config.json', '');
77
+ testTree.create(
78
+ '/.angular.json',
79
+ JSON.stringify({
80
+ version: 1,
81
+ projects: {with_tests: {architect: {test: {options: {tsConfig: './my-test-config.json'}}}}},
82
+ }),
83
+ );
84
+
85
+ const config = await getWorkspaceConfigGracefully(testTree);
86
+ expect(config).not.toBeNull();
87
+ expect(getTargetTsconfigPath(config!.projects.get('with_tests')!, 'test')).toEqual(
88
+ 'my-test-config.json' as WorkspacePath,
89
+ );
90
+ });
91
+ });