1- import { chain , FileEntry , Rule , SchematicContext , Tree } from '@angular-devkit/schematics' ;
1+ import { FileEntry , Rule , SchematicContext , Tree } from '@angular-devkit/schematics' ;
22import {
33 NodePackageInstallTask ,
44 RunSchematicTask ,
55 TslintFixTask
66} from '@angular-devkit/schematics/tasks' ;
77import * as path from 'path' ;
8+ import { existsSync , readFileSync } from 'fs' ;
9+ import { getProjectFromWorkspace , getWorkspace } from '../utils/devkit-utils/config' ;
810
911const schematicsSrcPath = 'node_modules/@angular/material/schematics' ;
1012const schematicsTmpPath = 'node_modules/_tmp_angular_material_schematics' ;
1113
1214/** Entry point for `ng update` from Angular CLI. */
1315export default function ( ) : Rule {
1416 return ( tree : Tree , context : SchematicContext ) => {
17+ // If this script failed in an earlier run, clear out the temporary files from that failed
18+ // run before doing anything else.
19+ tree . getDir ( schematicsTmpPath ) . visit ( ( _ , entry ) => tree . delete ( entry . path ) ) ;
20+
1521 // Copy the update schematics to a temporary directory.
1622 const updateSrcs : FileEntry [ ] = [ ] ;
1723 tree . getDir ( schematicsSrcPath ) . visit ( ( _ , entry ) => updateSrcs . push ( entry ) ) ;
@@ -25,48 +31,52 @@ export default function(): Rule {
2531 packageName : '@angular/cdk@">=5 <6" @angular/material@">=5 <6"'
2632 } ) ) ;
2733
28- // Run the update tslint rules.
29- const updateTask = context . addTask ( new TslintFixTask ( {
30- rulesDirectory : path . join ( schematicsTmpPath , 'update/rules' ) ,
31- rules : {
32- // Automatic fixes.
33- "switch-identifiers" : true ,
34- "switch-property-names" : true ,
35- "switch-string-literal-attribute-selectors" : true ,
36- "switch-string-literal-css-names" : true ,
37- "switch-string-literal-element-selectors" : true ,
38- "switch-stylesheet-attribute-selectors" : true ,
39- "switch-stylesheet-css-names" : true ,
40- "switch-stylesheet-element-selectors" : true ,
41- "switch-stylesheet-input-names" : true ,
42- "switch-stylesheet-output-names" : true ,
43- "switch-template-attribute-selectors" : true ,
44- "switch-template-css-names" : true ,
45- "switch-template-element-selectors" : true ,
46- "switch-template-export-as-names" : true ,
47- "switch-template-input-names" : true ,
48- "switch-template-output-names" : true ,
34+ const allTsConfigPaths = getTsConfigPaths ( tree ) ;
35+ const allUpdateTasks = [ ] ;
36+ for ( const tsconfig of allTsConfigPaths ) {
37+ // Run the update tslint rules.
38+ allUpdateTasks . push ( context . addTask ( new TslintFixTask ( {
39+ rulesDirectory : path . join ( schematicsTmpPath , 'update/rules' ) ,
40+ rules : {
41+ // Automatic fixes.
42+ "switch-identifiers" : true ,
43+ "switch-property-names" : true ,
44+ "switch-string-literal-attribute-selectors" : true ,
45+ "switch-string-literal-css-names" : true ,
46+ "switch-string-literal-element-selectors" : true ,
47+ "switch-stylesheet-attribute-selectors" : true ,
48+ "switch-stylesheet-css-names" : true ,
49+ "switch-stylesheet-element-selectors" : true ,
50+ "switch-stylesheet-input-names" : true ,
51+ "switch-stylesheet-output-names" : true ,
52+ "switch-template-attribute-selectors" : true ,
53+ "switch-template-css-names" : true ,
54+ "switch-template-element-selectors" : true ,
55+ "switch-template-export-as-names" : true ,
56+ "switch-template-input-names" : true ,
57+ "switch-template-output-names" : true ,
4958
50- // Additional issues we can detect but not automatically fix.
51- "check-class-declaration-misc" : true ,
52- "check-identifier-misc" : true ,
53- "check-import-misc" : true ,
54- "check-inheritance" : true ,
55- "check-method-calls" : true ,
56- "check-property-access-misc" : true ,
57- "check-template-misc" : true
58- }
59- } , {
60- silent : false ,
61- ignoreErrors : true ,
62- tsConfigPath : './src/tsconfig.json' ,
63- } ) , [ downgradeTask ] ) ;
59+ // Additional issues we can detect but not automatically fix.
60+ "check-class-declaration-misc" : true ,
61+ "check-identifier-misc" : true ,
62+ "check-import-misc" : true ,
63+ "check-inheritance" : true ,
64+ "check-method-calls" : true ,
65+ "check-property-access-misc" : true ,
66+ "check-template-misc" : true
67+ }
68+ } , {
69+ silent : false ,
70+ ignoreErrors : true ,
71+ tsConfigPath : tsconfig ,
72+ } ) , [ downgradeTask ] ) ) ;
73+ }
6474
6575 // Upgrade @angular /material back to 6.x.
6676 const upgradeTask = context . addTask ( new NodePackageInstallTask ( {
6777 // TODO(mmalerba): Change "next" to ">=6 <7".
6878 packageName : '@angular/cdk@next @angular/material@next'
69- } ) , [ updateTask ] ) ;
79+ } ) , allUpdateTasks ) ;
7080
7181 // Delete the temporary schematics directory.
7282 context . addTask (
@@ -94,3 +104,36 @@ export function postPostUpdate(): Rule {
94104 '\nComplete! Please check the output above for any issues that were detected but could not' +
95105 ' be automatically fixed.' ) ;
96106}
107+
108+ /** Gets the first tsconfig path from possibile locations based on the history of the CLI. */
109+ function getTsConfigPaths ( tree : Tree ) : string [ ] {
110+ // Start with some tsconfig paths that are generally used.
111+ const tsconfigPaths = [
112+ './tsconfig.json' ,
113+ './src/tsconfig.json' ,
114+ './src/tsconfig.app.json' ,
115+ ] ;
116+
117+ // Add any tsconfig directly referenced in a build or test task of the angular.json workspace.
118+ const workspace = getWorkspace ( tree ) ;
119+ for ( const project of Object . values ( workspace . projects ) ) {
120+ if ( project && project . architect ) {
121+ for ( const taskName of [ 'build' , 'test' ] ) {
122+ const task = project . architect [ taskName ] ;
123+ if ( task && task . options && task . options . tsConfig ) {
124+ const tsConfigOption = project . architect . tsConfig ;
125+ if ( typeof tsConfigOption === 'string' ) {
126+ tsconfigPaths . push ( tsConfigOption ) ;
127+ } else if ( Array . isArray ( tsConfigOption ) ) {
128+ tsconfigPaths . push ( ...tsConfigOption ) ;
129+ }
130+ }
131+ }
132+ }
133+ }
134+
135+ // Filter out tsconfig files that don't exist and remove any duplicates.
136+ return tsconfigPaths
137+ . filter ( p => existsSync ( p ) )
138+ . filter ( ( value , index , self ) => self . indexOf ( value ) === index ) ;
139+ }
0 commit comments