@@ -19,25 +19,6 @@ function writeJson(fileName, object) {
1919 fs . writeFileSync ( fileName , JSON . stringify ( object , null , 2 ) + os . EOL ) ;
2020}
2121
22- const compilerOptions = {
23- // These are suggested values and will be set when not present in the
24- // tsconfig.json
25- target : { suggested : 'es5' } ,
26- allowJs : { suggested : true } ,
27- skipLibCheck : { suggested : true } ,
28- esModuleInterop : { suggested : true } ,
29- allowSyntheticDefaultImports : { suggested : true } ,
30- strict : { suggested : true } ,
31-
32- // These values are required and cannot be changed by the user
33- module : { value : 'esnext' , reason : 'for import() and import/export' } ,
34- moduleResolution : { value : 'node' , reason : 'to match webpack resolution' } ,
35- resolveJsonModule : { value : true , reason : 'to match webpack loader' } ,
36- isolatedModules : { value : true , reason : 'implementation limitation' } ,
37- noEmit : { value : true } ,
38- jsx : { value : 'preserve' , reason : 'JSX is compiled by Babel' } ,
39- } ;
40-
4122function verifyTypeScriptSetup ( ) {
4223 let firstTimeSetup = false ;
4324
@@ -86,8 +67,44 @@ function verifyTypeScriptSetup() {
8667 process . exit ( 1 ) ;
8768 }
8869
70+ const compilerOptions = {
71+ // These are suggested values and will be set when not present in the
72+ // tsconfig.json
73+ // 'parsedValue' matches the output value from ts.parseJsonConfigFileContent()
74+ target : {
75+ parsedValue : ts . ScriptTarget . ES5 ,
76+ suggested : 'es5' ,
77+ } ,
78+ allowJs : { suggested : true } ,
79+ skipLibCheck : { suggested : true } ,
80+ esModuleInterop : { suggested : true } ,
81+ allowSyntheticDefaultImports : { suggested : true } ,
82+ strict : { suggested : true } ,
83+
84+ // These values are required and cannot be changed by the user
85+ module : {
86+ parsedValue : ts . ModuleKind . ESNext ,
87+ value : 'esnext' ,
88+ reason : 'for import() and import/export' ,
89+ } ,
90+ moduleResolution : {
91+ parsedValue : ts . ModuleResolutionKind . NodeJs ,
92+ value : 'node' ,
93+ reason : 'to match webpack resolution' ,
94+ } ,
95+ resolveJsonModule : { value : true , reason : 'to match webpack loader' } ,
96+ isolatedModules : { value : true , reason : 'implementation limitation' } ,
97+ noEmit : { value : true } ,
98+ jsx : {
99+ parsedValue : ts . JsxEmit . Preserve ,
100+ value : 'preserve' ,
101+ reason : 'JSX is compiled by Babel' ,
102+ } ,
103+ } ;
104+
89105 const messages = [ ] ;
90106 let tsconfig ;
107+ let parsedOptions ;
91108 try {
92109 const { config, error } = ts . readConfigFile (
93110 paths . appTsConfig ,
@@ -99,6 +116,21 @@ function verifyTypeScriptSetup() {
99116 }
100117
101118 tsconfig = config ;
119+
120+ // Get TS to parse and resolve any "extends"
121+ // Calling this function also mutates the tsconfig above,
122+ // adding in "include" and "exclude", but the compilerOptions remain untouched
123+ const result = ts . parseJsonConfigFileContent (
124+ config ,
125+ ts . sys ,
126+ path . dirname ( paths . appTsConfig )
127+ ) ;
128+
129+ if ( result . errors && result . errors . length ) {
130+ throw result . errors [ 0 ] ;
131+ }
132+
133+ parsedOptions = result . options ;
102134 } catch ( _ ) {
103135 console . error (
104136 chalk . red . bold (
@@ -116,17 +148,20 @@ function verifyTypeScriptSetup() {
116148 }
117149
118150 for ( const option of Object . keys ( compilerOptions ) ) {
119- const { value, suggested, reason } = compilerOptions [ option ] ;
151+ const { parsedValue, value, suggested, reason } = compilerOptions [ option ] ;
152+
153+ const valueToCheck = parsedValue === undefined ? value : parsedValue ;
154+
120155 if ( suggested != null ) {
121- if ( tsconfig . compilerOptions [ option ] === undefined ) {
156+ if ( parsedOptions [ option ] === undefined ) {
122157 tsconfig . compilerOptions [ option ] = suggested ;
123158 messages . push (
124159 `${ chalk . cyan ( 'compilerOptions.' + option ) } to be ${ chalk . bold (
125160 'suggested'
126161 ) } value: ${ chalk . cyan . bold ( suggested ) } (this can be changed)`
127162 ) ;
128163 }
129- } else if ( tsconfig . compilerOptions [ option ] !== value ) {
164+ } else if ( parsedOptions [ option ] !== valueToCheck ) {
130165 tsconfig . compilerOptions [ option ] = value ;
131166 messages . push (
132167 `${ chalk . cyan ( 'compilerOptions.' + option ) } ${ chalk . bold (
@@ -137,6 +172,7 @@ function verifyTypeScriptSetup() {
137172 }
138173 }
139174
175+ // tsconfig will have the merged "include" and "exclude" by this point
140176 if ( tsconfig . include == null ) {
141177 tsconfig . include = [ 'src' ] ;
142178 messages . push (
0 commit comments