1namespace ts { 2 describe("unittests:: tsbuild:: outFile::", () => { 3 let outFileFs: vfs.FileSystem; 4 let outFileWithBuildFs: vfs.FileSystem; 5 before(() => { 6 outFileFs = loadProjectFromDisk("tests/projects/outfile-concat"); 7 }); 8 after(() => { 9 outFileFs = undefined!; 10 outFileWithBuildFs = undefined!; 11 }); 12 13 interface VerifyOutFileScenarioInput { 14 subScenario: string; 15 modifyFs?: (fs: vfs.FileSystem) => void; 16 modifyAgainFs?: (fs: vfs.FileSystem) => void; 17 ignoreDtsChanged?: true; 18 ignoreDtsUnchanged?: true; 19 baselineOnly?: true; 20 additionalCommandLineArgs?: string[]; 21 } 22 23 function verifyOutFileScenario({ 24 subScenario, 25 modifyFs, 26 modifyAgainFs, 27 ignoreDtsChanged, 28 ignoreDtsUnchanged, 29 baselineOnly, 30 additionalCommandLineArgs, 31 }: VerifyOutFileScenarioInput) { 32 const edits: TestTscEdit[] = []; 33 if (!ignoreDtsChanged) { 34 edits.push({ 35 subScenario: "incremental-declaration-changes", 36 modifyFs: fs => replaceText(fs, "/src/first/first_PART1.ts", "Hello", "Hola"), 37 }); 38 } 39 if (!ignoreDtsUnchanged) { 40 edits.push({ 41 subScenario: "incremental-declaration-doesnt-change", 42 modifyFs: fs => appendText(fs, "/src/first/first_PART1.ts", "console.log(s);"), 43 }); 44 } 45 if (modifyAgainFs) { 46 edits.push({ 47 subScenario: "incremental-headers-change-without-dts-changes", 48 modifyFs: modifyAgainFs 49 }); 50 } 51 const input: VerifyTscWithEditsInput = { 52 subScenario, 53 fs: () => outFileFs, 54 scenario: "outfile-concat", 55 commandLineArgs: ["--b", "/src/third", "--verbose", ...(additionalCommandLineArgs || [])], 56 baselineSourceMap: true, 57 modifyFs, 58 baselineReadFileCalls: !baselineOnly, 59 edits, 60 }; 61 return edits.length ? 62 verifyTscWithEdits(input) : 63 verifyTsc(input); 64 } 65 66 // Verify initial + incremental edits 67 verifyOutFileScenario({ 68 subScenario: "baseline sectioned sourcemaps", 69 }); 70 71 verifyOutFileScenario({ 72 subScenario: "explainFiles", 73 additionalCommandLineArgs: ["--explainFiles"], 74 baselineOnly: true 75 }); 76 77 // Verify baseline with build info + dts unChanged 78 verifyOutFileScenario({ 79 subScenario: "when final project is not composite but uses project references", 80 modifyFs: fs => replaceText(fs, "/src/third/tsconfig.json", `"composite": true,`, ""), 81 ignoreDtsChanged: true, 82 baselineOnly: true 83 }); 84 85 // Verify baseline with build info 86 verifyOutFileScenario({ 87 subScenario: "when final project is not composite but incremental", 88 modifyFs: fs => replaceText(fs, "/src/third/tsconfig.json", `"composite": true,`, `"incremental": true,`), 89 ignoreDtsChanged: true, 90 ignoreDtsUnchanged: true, 91 baselineOnly: true 92 }); 93 94 // Verify baseline with build info 95 verifyOutFileScenario({ 96 subScenario: "when final project specifies tsBuildInfoFile", 97 modifyFs: fs => replaceText(fs, "/src/third/tsconfig.json", `"composite": true,`, `"composite": true, 98 "tsBuildInfoFile": "./thirdjs/output/third.tsbuildinfo",`), 99 ignoreDtsChanged: true, 100 ignoreDtsUnchanged: true, 101 baselineOnly: true 102 }); 103 104 function getOutFileFsAfterBuild() { 105 if (outFileWithBuildFs) return outFileWithBuildFs; 106 const fs = outFileFs.shadow(); 107 const sys = new fakes.System(fs, { executingFilePath: "/lib/tsc" }); 108 const host = createSolutionBuilderHostForBaseline(sys as TscCompileSystem); 109 const builder = createSolutionBuilder(host, ["/src/third"], { dry: false, force: false, verbose: true }); 110 builder.build(); 111 fs.makeReadonly(); 112 return outFileWithBuildFs = fs; 113 } 114 115 verifyTscWithEdits({ 116 scenario: "outFile", 117 subScenario: "clean projects", 118 fs: getOutFileFsAfterBuild, 119 commandLineArgs: ["--b", "/src/third", "--clean"], 120 edits: noChangeOnlyRuns 121 }); 122 123 verifyTsc({ 124 scenario: "outFile", 125 subScenario: "verify buildInfo absence results in new build", 126 fs: getOutFileFsAfterBuild, 127 commandLineArgs: ["--b", "/src/third", "--verbose"], 128 modifyFs: fs => fs.unlinkSync("/src/first/bin/first-output.tsbuildinfo"), 129 }); 130 131 verifyTsc({ 132 scenario: "outFile", 133 subScenario: "tsbuildinfo is not generated when incremental is set to false", 134 fs: () => outFileFs, 135 commandLineArgs: ["--b", "/src/third", "--verbose"], 136 modifyFs: fs => replaceText(fs, "/src/third/tsconfig.json", `"composite": true,`, ""), 137 }); 138 139 verifyTscCompileLike(testTscCompileLike, { 140 scenario: "outFile", 141 subScenario: "rebuilds completely when version in tsbuildinfo doesnt match ts version", 142 fs: getOutFileFsAfterBuild, 143 commandLineArgs: ["--b", "/src/third", "--verbose"], 144 compile: sys => { 145 // Buildinfo will have version which does not match with current ts version 146 const buildHost = createSolutionBuilderHostForBaseline(sys, "FakeTSCurrentVersion"); 147 const builder = createSolutionBuilder(buildHost, ["/src/third"], { verbose: true }); 148 sys.exit(builder.build()); 149 } 150 }); 151 152 verifyTscWithEdits({ 153 scenario: "outFile", 154 subScenario: "rebuilds completely when command line incremental flag changes between non dts changes", 155 fs: () => outFileFs, 156 // Make non composite third project 157 modifyFs: fs => replaceText(fs, "/src/third/tsconfig.json", `"composite": true,`, ""), 158 // Build with command line incremental 159 commandLineArgs: ["--b", "/src/third", "--i", "--verbose"], 160 edits: [ 161 { 162 subScenario: "Make non incremental build with change in file that doesnt affect dts", 163 modifyFs: fs => appendText(fs, "/src/first/first_PART1.ts", "console.log(s);"), 164 commandLineArgs: ["--b", "/src/third", "--verbose"], 165 }, 166 { 167 subScenario: "Make incremental build with change in file that doesnt affect dts", 168 modifyFs: fs => appendText(fs, "/src/first/first_PART1.ts", "console.log(s);"), 169 commandLineArgs: ["--b", "/src/third", "--verbose", "--incremental"], 170 } 171 ] 172 }); 173 174 verifyTscWithEdits({ 175 scenario: "outFile", 176 subScenario: "when input file text does not change but its modified time changes", 177 fs: () => outFileFs, 178 commandLineArgs: ["--b", "/src/third", "--verbose"], 179 edits: [ 180 { 181 subScenario: "upstream project changes without changing file text", 182 modifyFs: fs => { 183 const time = new Date(fs.time()); 184 fs.utimesSync("/src/first/first_PART1.ts", time, time); 185 }, 186 }, 187 ] 188 }); 189 190 verifyTscCompileLike(testTscCompileLike, { 191 scenario: "outFile", 192 subScenario: "builds till project specified", 193 fs: () => outFileFs, 194 commandLineArgs: ["--build", "/src/second/tsconfig.json"], 195 compile: sys => { 196 const buildHost = createSolutionBuilderHostForBaseline(sys); 197 const builder = createSolutionBuilder(buildHost, ["/src/third/tsconfig.json"], {}); 198 sys.exit(builder.build("/src/second/tsconfig.json")); 199 } 200 }); 201 202 verifyTscCompileLike(testTscCompileLike, { 203 scenario: "outFile", 204 subScenario: "cleans till project specified", 205 fs: getOutFileFsAfterBuild, 206 commandLineArgs: ["--build", "--clean", "/src/second/tsconfig.json"], 207 compile: sys => { 208 const buildHost = createSolutionBuilderHostForBaseline(sys); 209 const builder = createSolutionBuilder(buildHost, ["/src/third/tsconfig.json"], { verbose: true }); 210 sys.exit(builder.clean("/src/second/tsconfig.json")); 211 } 212 }); 213 214 describe("Prepend output with .tsbuildinfo", () => { 215 // Prologues 216 describe("Prologues", () => { 217 // Verify initial + incremental edits 218 verifyOutFileScenario({ 219 subScenario: "strict in all projects", 220 modifyFs: fs => { 221 enableStrict(fs, "/src/first/tsconfig.json"); 222 enableStrict(fs, "/src/second/tsconfig.json"); 223 enableStrict(fs, "/src/third/tsconfig.json"); 224 }, 225 modifyAgainFs: fs => addTestPrologue(fs, "/src/first/first_PART1.ts", `"myPrologue"`) 226 }); 227 228 // Verify ignore dtsChanged 229 verifyOutFileScenario({ 230 subScenario: "strict in one dependency", 231 modifyFs: fs => enableStrict(fs, "/src/second/tsconfig.json"), 232 modifyAgainFs: fs => addTestPrologue(fs, "src/first/first_PART1.ts", `"myPrologue"`), 233 ignoreDtsChanged: true, 234 baselineOnly: true 235 }); 236 237 // Verify initial + incremental edits - sourcemap verification 238 verifyOutFileScenario({ 239 subScenario: "multiple prologues in all projects", 240 modifyFs: fs => { 241 enableStrict(fs, "/src/first/tsconfig.json"); 242 addTestPrologue(fs, "/src/first/first_PART1.ts", `"myPrologue"`); 243 enableStrict(fs, "/src/second/tsconfig.json"); 244 addTestPrologue(fs, "/src/second/second_part1.ts", `"myPrologue"`); 245 addTestPrologue(fs, "/src/second/second_part2.ts", `"myPrologue2";`); 246 enableStrict(fs, "/src/third/tsconfig.json"); 247 addTestPrologue(fs, "/src/third/third_part1.ts", `"myPrologue";`); 248 addTestPrologue(fs, "/src/third/third_part1.ts", `"myPrologue3";`); 249 }, 250 modifyAgainFs: fs => addTestPrologue(fs, "/src/first/first_PART1.ts", `"myPrologue5"`) 251 }); 252 253 // Verify ignore dtsChanged 254 verifyOutFileScenario({ 255 subScenario: "multiple prologues in different projects", 256 modifyFs: fs => { 257 enableStrict(fs, "/src/first/tsconfig.json"); 258 addTestPrologue(fs, "/src/second/second_part1.ts", `"myPrologue"`); 259 addTestPrologue(fs, "/src/second/second_part2.ts", `"myPrologue2";`); 260 enableStrict(fs, "/src/third/tsconfig.json"); 261 }, 262 modifyAgainFs: fs => addTestPrologue(fs, "/src/first/first_PART1.ts", `"myPrologue5"`), 263 ignoreDtsChanged: true, 264 baselineOnly: true 265 }); 266 }); 267 268 // Shebang 269 describe("Shebang", () => { 270 // changes declaration because its emitted in .d.ts file 271 // Verify initial + incremental edits 272 verifyOutFileScenario({ 273 subScenario: "shebang in all projects", 274 modifyFs: fs => { 275 addShebang(fs, "first", "first_PART1"); 276 addShebang(fs, "first", "first_part2"); 277 addShebang(fs, "second", "second_part1"); 278 addShebang(fs, "third", "third_part1"); 279 }, 280 }); 281 282 // Verify ignore dtsChanged 283 verifyOutFileScenario({ 284 subScenario: "shebang in only one dependency project", 285 modifyFs: fs => addShebang(fs, "second", "second_part1"), 286 ignoreDtsChanged: true, 287 baselineOnly: true 288 }); 289 }); 290 291 // emitHelpers 292 describe("emitHelpers", () => { 293 // Verify initial + incremental edits 294 verifyOutFileScenario({ 295 subScenario: "emitHelpers in all projects", 296 modifyFs: fs => { 297 addRest(fs, "first", "first_PART1"); 298 addRest(fs, "second", "second_part1"); 299 addRest(fs, "third", "third_part1"); 300 }, 301 modifyAgainFs: fs => removeRest(fs, "first", "first_PART1") 302 }); 303 304 // Verify ignore dtsChanged 305 verifyOutFileScenario({ 306 subScenario: "emitHelpers in only one dependency project", 307 modifyFs: fs => { 308 addStubFoo(fs, "first", "first_PART1"); 309 addRest(fs, "second", "second_part1"); 310 }, 311 modifyAgainFs: fs => changeStubToRest(fs, "first", "first_PART1"), 312 ignoreDtsChanged: true, 313 baselineOnly: true 314 }); 315 316 // Verify ignore dtsChanged 317 verifyOutFileScenario({ 318 subScenario: "multiple emitHelpers in all projects", 319 modifyFs: fs => { 320 addRest(fs, "first", "first_PART1"); 321 addSpread(fs, "first", "first_part3"); 322 addRest(fs, "second", "second_part1"); 323 addSpread(fs, "second", "second_part2"); 324 addRest(fs, "third", "third_part1"); 325 addSpread(fs, "third", "third_part1"); 326 }, 327 modifyAgainFs: fs => removeRest(fs, "first", "first_PART1"), 328 ignoreDtsChanged: true, 329 baselineOnly: true 330 }); 331 332 // Verify ignore dtsChanged 333 verifyOutFileScenario({ 334 subScenario: "multiple emitHelpers in different projects", 335 modifyFs: fs => { 336 addRest(fs, "first", "first_PART1"); 337 addSpread(fs, "second", "second_part1"); 338 addRest(fs, "third", "third_part1"); 339 }, 340 modifyAgainFs: fs => removeRest(fs, "first", "first_PART1"), 341 ignoreDtsChanged: true, 342 baselineOnly: true 343 }); 344 }); 345 346 // triple slash refs 347 describe("triple slash refs", () => { 348 // changes declaration because its emitted in .d.ts file 349 // Verify initial + incremental edits 350 verifyOutFileScenario({ 351 subScenario: "triple slash refs in all projects", 352 modifyFs: fs => { 353 addTripleSlashRef(fs, "first", "first_part2"); 354 addTripleSlashRef(fs, "second", "second_part1"); 355 addTripleSlashRef(fs, "third", "third_part1"); 356 } 357 }); 358 359 // Verify ignore dtsChanged 360 verifyOutFileScenario({ 361 subScenario: "triple slash refs in one project", 362 modifyFs: fs => addTripleSlashRef(fs, "second", "second_part1"), 363 ignoreDtsChanged: true, 364 baselineOnly: true 365 }); 366 }); 367 368 describe("stripInternal", () => { 369 function disableRemoveComments(fs: vfs.FileSystem, file: string) { 370 replaceText(fs, file, `"removeComments": true`, `"removeComments": false`); 371 } 372 373 function diableRemoveCommentsInAll(fs: vfs.FileSystem) { 374 disableRemoveComments(fs, "/src/first/tsconfig.json"); 375 disableRemoveComments(fs, "/src/second/tsconfig.json"); 376 disableRemoveComments(fs, "/src/third/tsconfig.json"); 377 } 378 379 function stripInternalOfThird(fs: vfs.FileSystem) { 380 replaceText(fs, "/src/third/tsconfig.json", `"declaration": true,`, `"declaration": true, 381 "stripInternal": true,`); 382 } 383 384 function stripInternalScenario(fs: vfs.FileSystem, removeCommentsDisabled?: boolean, jsDocStyle?: boolean) { 385 const internal: string = jsDocStyle ? `/**@internal*/` : `/*@internal*/`; 386 if (removeCommentsDisabled) { 387 diableRemoveCommentsInAll(fs); 388 } 389 stripInternalOfThird(fs); 390 replaceText(fs, "/src/first/first_PART1.ts", "interface", `${internal} interface`); 391 appendText(fs, "/src/second/second_part1.ts", ` 392class normalC { 393 ${internal} constructor() { } 394 ${internal} prop: string; 395 ${internal} method() { } 396 ${internal} get c() { return 10; } 397 ${internal} set c(val: number) { } 398} 399namespace normalN { 400 ${internal} export class C { } 401 ${internal} export function foo() {} 402 ${internal} export namespace someNamespace { export class C {} } 403 ${internal} export namespace someOther.something { export class someClass {} } 404 ${internal} export import someImport = someNamespace.C; 405 ${internal} export type internalType = internalC; 406 ${internal} export const internalConst = 10; 407 ${internal} export enum internalEnum { a, b, c } 408} 409${internal} class internalC {} 410${internal} function internalfoo() {} 411${internal} namespace internalNamespace { export class someClass {} } 412${internal} namespace internalOther.something { export class someClass {} } 413${internal} import internalImport = internalNamespace.someClass; 414${internal} type internalType = internalC; 415${internal} const internalConst = 10; 416${internal} enum internalEnum { a, b, c }`); 417 } 418 419 // Verify initial + incremental edits 420 verifyOutFileScenario({ 421 subScenario: "stripInternal", 422 modifyFs: stripInternalScenario, 423 modifyAgainFs: fs => replaceText(fs, "/src/first/first_PART1.ts", `/*@internal*/ interface`, "interface"), 424 }); 425 426 // Verify ignore dtsChanged 427 verifyOutFileScenario({ 428 subScenario: "stripInternal with comments emit enabled", 429 modifyFs: fs => stripInternalScenario(fs, /*removeCommentsDisabled*/ true), 430 modifyAgainFs: fs => replaceText(fs, "/src/first/first_PART1.ts", `/*@internal*/ interface`, "interface"), 431 ignoreDtsChanged: true, 432 baselineOnly: true 433 }); 434 435 // Verify ignore dtsChanged 436 verifyOutFileScenario({ 437 subScenario: "stripInternal jsdoc style comment", 438 modifyFs: fs => stripInternalScenario(fs, /*removeCommentsDisabled*/ false, /*jsDocStyle*/ true), 439 modifyAgainFs: fs => replaceText(fs, "/src/first/first_PART1.ts", `/**@internal*/ interface`, "interface"), 440 ignoreDtsChanged: true, 441 baselineOnly: true 442 }); 443 444 // Verify ignore dtsChanged 445 verifyOutFileScenario({ 446 subScenario: "stripInternal jsdoc style with comments emit enabled", 447 modifyFs: fs => stripInternalScenario(fs, /*removeCommentsDisabled*/ true, /*jsDocStyle*/ true), 448 ignoreDtsChanged: true, 449 baselineOnly: true 450 }); 451 452 describe("with three levels of project dependency", () => { 453 function makeOneTwoThreeDependOrder(fs: vfs.FileSystem) { 454 replaceText(fs, "/src/second/tsconfig.json", "[", `[ 455 { "path": "../first", "prepend": true }`); 456 replaceText(fs, "/src/third/tsconfig.json", `{ "path": "../first", "prepend": true },`, ""); 457 } 458 459 function stripInternalWithDependentOrder(fs: vfs.FileSystem, removeCommentsDisabled?: boolean, jsDocStyle?: boolean) { 460 stripInternalScenario(fs, removeCommentsDisabled, jsDocStyle); 461 makeOneTwoThreeDependOrder(fs); 462 } 463 464 // Verify initial + incremental edits 465 verifyOutFileScenario({ 466 subScenario: "stripInternal when one-two-three are prepended in order", 467 modifyFs: stripInternalWithDependentOrder, 468 modifyAgainFs: fs => replaceText(fs, "/src/first/first_PART1.ts", `/*@internal*/ interface`, "interface"), 469 }); 470 471 // Verify ignore dtsChanged 472 verifyOutFileScenario({ 473 subScenario: "stripInternal with comments emit enabled when one-two-three are prepended in order", 474 modifyFs: fs => stripInternalWithDependentOrder(fs, /*removeCommentsDisabled*/ true), 475 modifyAgainFs: fs => replaceText(fs, "/src/first/first_PART1.ts", `/*@internal*/ interface`, "interface"), 476 ignoreDtsChanged: true, 477 baselineOnly: true 478 }); 479 480 // Verify ignore dtsChanged 481 verifyOutFileScenario({ 482 subScenario: "stripInternal jsdoc style comment when one-two-three are prepended in order", 483 modifyFs: fs => stripInternalWithDependentOrder(fs, /*removeCommentsDisabled*/ false, /*jsDocStyle*/ true), 484 modifyAgainFs: fs => replaceText(fs, "/src/first/first_PART1.ts", `/**@internal*/ interface`, "interface"), 485 ignoreDtsChanged: true, 486 baselineOnly: true 487 }); 488 489 // Verify ignore dtsChanged 490 verifyOutFileScenario({ 491 subScenario: "stripInternal jsdoc style with comments emit enabled when one-two-three are prepended in order", 492 modifyFs: fs => stripInternalWithDependentOrder(fs, /*removeCommentsDisabled*/ true, /*jsDocStyle*/ true), 493 ignoreDtsChanged: true, 494 baselineOnly: true 495 }); 496 }); 497 498 // only baseline 499 verifyOutFileScenario({ 500 subScenario: "stripInternal baseline when internal is inside another internal", 501 modifyFs: fs => { 502 stripInternalOfThird(fs); 503 prependText(fs, "/src/first/first_PART1.ts", `namespace ts { 504 /* @internal */ 505 /** 506 * Subset of properties from SourceFile that are used in multiple utility functions 507 */ 508 export interface SourceFileLike { 509 readonly text: string; 510 lineMap?: ReadonlyArray<number>; 511 /* @internal */ 512 getPositionOfLineAndCharacter?(line: number, character: number, allowEdits?: true): number; 513 } 514 515 /* @internal */ 516 export interface RedirectInfo { 517 /** Source file this redirects to. */ 518 readonly redirectTarget: SourceFile; 519 /** 520 * Source file for the duplicate package. This will not be used by the Program, 521 * but we need to keep this around so we can watch for changes in underlying. 522 */ 523 readonly unredirected: SourceFile; 524 } 525 526 // Source files are declarations when they are external modules. 527 export interface SourceFile { 528 someProp: string; 529 } 530}`); 531 }, 532 ignoreDtsChanged: true, 533 ignoreDtsUnchanged: true, 534 baselineOnly: true 535 }); 536 537 // only baseline 538 verifyOutFileScenario({ 539 subScenario: "stripInternal when few members of enum are internal", 540 modifyFs: fs => { 541 stripInternalOfThird(fs); 542 prependText(fs, "/src/first/first_PART1.ts", `enum TokenFlags { 543 None = 0, 544 /* @internal */ 545 PrecedingLineBreak = 1 << 0, 546 /* @internal */ 547 PrecedingJSDocComment = 1 << 1, 548 /* @internal */ 549 Unterminated = 1 << 2, 550 /* @internal */ 551 ExtendedUnicodeEscape = 1 << 3, 552 Scientific = 1 << 4, 553 Octal = 1 << 5, 554 HexSpecifier = 1 << 6, 555 BinarySpecifier = 1 << 7, 556 OctalSpecifier = 1 << 8, 557 /* @internal */ 558 ContainsSeparator = 1 << 9, 559 /* @internal */ 560 BinaryOrOctalSpecifier = BinarySpecifier | OctalSpecifier, 561 /* @internal */ 562 NumericLiteralFlags = Scientific | Octal | HexSpecifier | BinaryOrOctalSpecifier | ContainsSeparator 563} 564`); 565 }, 566 ignoreDtsChanged: true, 567 ignoreDtsUnchanged: true, 568 baselineOnly: true 569 }); 570 571 verifyOutFileScenario({ 572 subScenario: "stripInternal when prepend is completely internal", 573 baselineOnly: true, 574 ignoreDtsChanged: true, 575 ignoreDtsUnchanged: true, 576 modifyFs: fs => { 577 fs.writeFileSync("/src/first/first_PART1.ts", "/* @internal */ const A = 1;"); 578 fs.writeFileSync("/src/third/third_part1.ts", "const B = 2;"); 579 fs.writeFileSync("/src/first/tsconfig.json", JSON.stringify({ 580 compilerOptions: { 581 composite: true, 582 declaration: true, 583 declarationMap: true, 584 skipDefaultLibCheck: true, 585 sourceMap: true, 586 outFile: "./bin/first-output.js" 587 }, 588 files: ["/src/first/first_PART1.ts"] 589 })); 590 fs.writeFileSync("/src/third/tsconfig.json", JSON.stringify({ 591 compilerOptions: { 592 composite: true, 593 declaration: true, 594 declarationMap: false, 595 stripInternal: true, 596 sourceMap: true, 597 outFile: "./thirdjs/output/third-output.js", 598 }, 599 references: [{ path: "../first", prepend: true }], 600 files: ["/src/third/third_part1.ts"] 601 })); 602 } 603 }); 604 }); 605 606 describe("empty source files", () => { 607 function makeThirdEmptySourceFile(fs: vfs.FileSystem) { 608 fs.writeFileSync("/src/third/third_part1.ts", "", "utf8"); 609 } 610 611 // Verify ignore dtsChanged 612 verifyOutFileScenario({ 613 subScenario: "when source files are empty in the own file", 614 modifyFs: makeThirdEmptySourceFile, 615 ignoreDtsChanged: true, 616 baselineOnly: true 617 }); 618 619 // only baseline 620 verifyOutFileScenario({ 621 subScenario: "declarationMap and sourceMap disabled", 622 modifyFs: fs => { 623 makeThirdEmptySourceFile(fs); 624 replaceText(fs, "/src/third/tsconfig.json", `"composite": true,`, ""); 625 replaceText(fs, "/src/third/tsconfig.json", `"sourceMap": true,`, ""); 626 replaceText(fs, "/src/third/tsconfig.json", `"declarationMap": true,`, ""); 627 }, 628 ignoreDtsChanged: true, 629 ignoreDtsUnchanged: true, 630 baselineOnly: true 631 }); 632 }); 633 }); 634 635 verifyTsc({ 636 scenario: "outFile", 637 subScenario: "non module projects without prepend", 638 fs: () => outFileFs, 639 commandLineArgs: ["--b", "/src/third", "--verbose"], 640 modifyFs: fs => { 641 // No prepend 642 replaceText(fs, "/src/third/tsconfig.json", `{ "path": "../first", "prepend": true }`, `{ "path": "../first" }`); 643 replaceText(fs, "/src/third/tsconfig.json", `{ "path": "../second", "prepend": true }`, `{ "path": "../second" }`); 644 645 // Non Modules 646 replaceText(fs, "/src/first/tsconfig.json", `"composite": true,`, `"composite": true, "module": "none",`); 647 replaceText(fs, "/src/second/tsconfig.json", `"composite": true,`, `"composite": true, "module": "none",`); 648 replaceText(fs, "/src/third/tsconfig.json", `"composite": true,`, `"composite": true, "module": "none",`); 649 650 // Own file emit 651 replaceText(fs, "/src/first/tsconfig.json", `"outFile": "./bin/first-output.js",`, ""); 652 replaceText(fs, "/src/second/tsconfig.json", `"outFile": "../2/second-output.js",`, ""); 653 replaceText(fs, "/src/third/tsconfig.json", `"outFile": "./thirdjs/output/third-output.js",`, ""); 654 }, 655 }); 656 }); 657} 658