From ab928dd42427ee802077426f5c6ceb0baadeef42 Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders <293473+sandersn@users.noreply.github.com> Date: Mon, 16 May 2022 11:26:34 -0700 Subject: [PATCH] Restore setModifiedTime It got deleted in the code move; executeCommandLine checks that it's required and asserts if it's not there. --- .../unittests/tsserver/updateFileSystem.ts | 210 +++++++++--------- src/vfs/virtualFileSystemWithWatch.ts | 9 + .../reference/api/tsserverlibrary.d.ts | 14 +- .../updateFileSystem/open-and-close-files.txt | 19 +- 4 files changed, 131 insertions(+), 121 deletions(-) diff --git a/src/testRunner/unittests/tsserver/updateFileSystem.ts b/src/testRunner/unittests/tsserver/updateFileSystem.ts index 4d5cba2ad2e..c60bf2f7475 100644 --- a/src/testRunner/unittests/tsserver/updateFileSystem.ts +++ b/src/testRunner/unittests/tsserver/updateFileSystem.ts @@ -1,105 +1,105 @@ -namespace ts.projectSystem { - describe("unittests:: tsserver:: updateFileSystem", () => { - const config: protocol.FileSystemRequestArgs = { - file: "/a/b/tsconfig.json", - fileContent: "{}" - }; - const file3: protocol.FileSystemRequestArgs = { - file: "/a/b/file3.ts", - fileContent: "export let xyz = 1;" - }; - const app: protocol.FileSystemRequestArgs = { - file: "/a/b/app.ts", - fileContent: "import { xyz } from './file3'; let x = xyz" - }; - const file1: protocol.FileSystemRequestArgs = { - file: "/a/b/commonFile1.ts", - fileContent: "let x = 1" - }; - const file2: protocol.FileSystemRequestArgs = { - file: "/a/b/commonFile2.ts", - fileContent: "let y = 1" - }; - const lib: protocol.FileSystemRequestArgs = { - file: "/a/lib/lib.d.ts", - fileContent: `/// -interface Boolean {} -interface Function {} -interface CallableFunction {} -interface NewableFunction {} -interface IArguments {} -interface Number { toExponential: any; } -interface Object {} -interface RegExp {} -interface String { charAt: any; } -interface Array { length: number; [n: number]: T; }` - }; - - function fileContentWithComment(file: protocol.FileSystemRequestArgs) { - return `// some copy right notice -${file.fileContent}`; - } - function baselineFileSystem(scenario: string, subScenario: string, requests: [string, Partial][], host: VirtualFS.VirtualServerHost, session: TestSession) { - const history: string[] = [] - let prev = host.snap() - for (const [name, request] of requests) { - session.executeCommandSeq(request) - history.push("") - history.push("#### " + name) - host.diff(history, prev) - prev = host.snap() - } - Harness.Baseline.runBaseline(`tsserver/${scenario}/${subScenario.split(" ").join("-")}.txt`, history.join("\r\n")); - baselineTsserverLogs(scenario, subScenario, session) - } - - it("with updateFileSystem request", () => { - const host = VirtualFS.createVirtualServerHost({ executingFilePath: "/a/tsc.js" }); - const session = createSession(host, { fshost: host, logger: createLoggerWithInMemoryLogs(), canUseEvents: true }); - const requests: [string, Partial][] = [ - ["Initial updateFileSystem", { - command: protocol.CommandTypes.UpdateFileSystem, - arguments:{ - fileSystem: "memfs", - files: [app, file1, file2, file3, config, lib], - deleted: [], - } - }], - ["Opening app.ts", { - command: protocol.CommandTypes.Open, - arguments: { file: app.file } - }], - ["Opening file3.ts", { - command: protocol.CommandTypes.Open, - arguments: { - file: file3.file, - fileContent: fileContentWithComment(file3) - } - }], - ["non-delete", { - command: protocol.CommandTypes.UpdateFileSystem, - arguments:{ - fileSystem: "memfs", - files: [], - deleted: [], - } - }], - ["delete", { - command: protocol.CommandTypes.UpdateFileSystem, - arguments:{ - fileSystem: "memfs", - files: [], - deleted: [file1.file], - } - }], - ["close", { - command: protocol.CommandTypes.Close, - arguments: { file: app.file } - }], - ] - const scenario = "updateFileSystem" - const subScenario = "open and close files" - baselineFileSystem(scenario, subScenario, requests, host, session); - }); - }); -} +namespace ts.projectSystem { + describe("unittests:: tsserver:: updateFileSystem", () => { + const config: protocol.FileSystemRequestArgs = { + file: "/a/b/tsconfig.json", + fileContent: "{}" + }; + const file3: protocol.FileSystemRequestArgs = { + file: "/a/b/file3.ts", + fileContent: "export let xyz = 1;" + }; + const app: protocol.FileSystemRequestArgs = { + file: "/a/b/app.ts", + fileContent: "import { xyz } from './file3'; let x = xyz" + }; + const file1: protocol.FileSystemRequestArgs = { + file: "/a/b/commonFile1.ts", + fileContent: "let x = 1" + }; + const file2: protocol.FileSystemRequestArgs = { + file: "/a/b/commonFile2.ts", + fileContent: "let y = 1" + }; + const lib: protocol.FileSystemRequestArgs = { + file: "/a/lib/lib.d.ts", + fileContent: `/// +interface Boolean {} +interface Function {} +interface CallableFunction {} +interface NewableFunction {} +interface IArguments {} +interface Number { toExponential: any; } +interface Object {} +interface RegExp {} +interface String { charAt: any; } +interface Array { length: number; [n: number]: T; }` + }; + + function fileContentWithComment(file: protocol.FileSystemRequestArgs) { + return `// some copy right notice +${file.fileContent}`; + } + function baselineFileSystem(scenario: string, subScenario: string, requests: [string, Partial][], host: VirtualFS.VirtualServerHost, session: TestSession) { + const history: string[] = [] + let prev = host.snap() + for (const [name, request] of requests) { + session.executeCommandSeq(request) + history.push("") + history.push("#### " + name) + host.diff(history, prev) + prev = host.snap() + } + Harness.Baseline.runBaseline(`tsserver/${scenario}/${subScenario.split(" ").join("-")}.txt`, history.join("\r\n")); + baselineTsserverLogs(scenario, subScenario, session) + } + + it("with updateFileSystem request", () => { + const host = VirtualFS.createVirtualServerHost({ executingFilePath: "/a/tsc.js" }); + const session = createSession(host, { fshost: host, logger: createLoggerWithInMemoryLogs(), canUseEvents: true }); + const requests: [string, Partial][] = [ + ["Initial updateFileSystem", { + command: protocol.CommandTypes.UpdateFileSystem, + arguments:{ + fileSystem: "memfs", + files: [app, file1, file2, file3, config, lib], + deleted: [], + } + }], + ["Opening app.ts", { + command: protocol.CommandTypes.Open, + arguments: { file: app.file } + }], + ["Opening file3.ts", { + command: protocol.CommandTypes.Open, + arguments: { + file: file3.file, + fileContent: fileContentWithComment(file3) + } + }], + ["non-delete", { + command: protocol.CommandTypes.UpdateFileSystem, + arguments:{ + fileSystem: "memfs", + files: [], + deleted: [], + } + }], + ["delete", { + command: protocol.CommandTypes.UpdateFileSystem, + arguments:{ + fileSystem: "memfs", + files: [], + deleted: [file1.file], + } + }], + ["close", { + command: protocol.CommandTypes.Close, + arguments: { file: app.file } + }], + ] + const scenario = "updateFileSystem" + const subScenario = "open and close files" + baselineFileSystem(scenario, subScenario, requests, host, session); + }); + }); +} diff --git a/src/vfs/virtualFileSystemWithWatch.ts b/src/vfs/virtualFileSystemWithWatch.ts index be32cbeef03..1a76338596c 100644 --- a/src/vfs/virtualFileSystemWithWatch.ts +++ b/src/vfs/virtualFileSystemWithWatch.ts @@ -456,6 +456,15 @@ namespace ts.VirtualFS { return (fsEntry && fsEntry.modifiedTime)!; // TODO: GH#18217 } + setModifiedTime(s: string, date: Date) { + const path = this.toFullPath(s); + const fsEntry = this.fs.get(path); + if (fsEntry) { + fsEntry.modifiedTime = date; + this.invokeFileAndFsWatches(fsEntry.fullPath, FileWatcherEventKind.Changed); + } + } + readFile(s: string): string | undefined { const fsEntry = this.getRealFile(this.toFullPath(s)); return fsEntry ? fsEntry.content : undefined; diff --git a/tests/baselines/reference/api/tsserverlibrary.d.ts b/tests/baselines/reference/api/tsserverlibrary.d.ts index 9bb0421d471..9165a8d2827 100644 --- a/tests/baselines/reference/api/tsserverlibrary.d.ts +++ b/tests/baselines/reference/api/tsserverlibrary.d.ts @@ -6958,6 +6958,7 @@ declare namespace ts.server { trace?(s: string): void; require?(initialPath: string, moduleName: string): RequireResult; } + type FileServerHost = Pick; } declare namespace ts.server { enum LogLevel { @@ -9899,7 +9900,7 @@ declare namespace ts.server { private formatSettings; private preferences; private textStorage; - constructor(host: ServerHost, fileName: NormalizedPath, scriptKind: ScriptKind, hasMixedContent: boolean, path: Path, initialVersion?: ScriptInfoVersion); + constructor(host: FileServerHost, fileName: NormalizedPath, scriptKind: ScriptKind, hasMixedContent: boolean, path: Path, initialVersion?: ScriptInfoVersion); isScriptOpen(): boolean; open(newText: string): void; close(fileExists?: boolean): void; @@ -9963,6 +9964,7 @@ declare namespace ts.server { languageService: LanguageService; languageServiceHost: LanguageServiceHost; serverHost: ServerHost; + fsHost: FileServerHost; session?: Session; config: any; } @@ -10027,7 +10029,7 @@ declare namespace ts.server { private readonly cancellationToken; isNonTsProject(): boolean; isJsOnlyProject(): boolean; - static resolveModule(moduleName: string, initialDir: string, host: ServerHost, fshost: ServerHost, log: (message: string) => void, logErrors?: (message: string) => void): {} | undefined; + static resolveModule(moduleName: string, initialDir: string, host: ServerHost, fshost: FileServerHost, log: (message: string) => void, logErrors?: (message: string) => void): {} | undefined; isKnownTypesPackageName(name: string): boolean; installPackage(options: InstallPackageOptions): Promise; private get typingsCache(); @@ -10341,7 +10343,7 @@ declare namespace ts.server { } export interface ProjectServiceOptions { host: ServerHost; - fshost: ServerHost | undefined; + fshost: FileServerHost | undefined; logger: Logger; cancellationToken: HostCancellationToken; useSingleInferredProject: boolean; @@ -10413,7 +10415,7 @@ declare namespace ts.server { readonly currentDirectory: NormalizedPath; readonly toCanonicalFileName: (f: string) => string; readonly host: ServerHost; - readonly fshost: ServerHost | undefined; + readonly fshost: FileServerHost; readonly logger: Logger; readonly cancellationToken: HostCancellationToken; readonly useSingleInferredProject: boolean; @@ -10616,7 +10618,7 @@ declare namespace ts.server { } interface SessionOptions { host: ServerHost; - fshost: ServerHost | undefined; + fshost?: FileServerHost; cancellationToken: ServerCancellationToken; useSingleInferredProject: boolean; useInferredProjectPerProjectRoot: boolean; @@ -10658,7 +10660,7 @@ declare namespace ts.server { private suppressDiagnosticEvents?; private eventHandler; private readonly noGetErrOnBackgroundUpdate?; - private fshost; + private fshost?; constructor(opts: SessionOptions); private sendRequestCompletedEvent; private addPerformanceData; diff --git a/tests/baselines/reference/tsserver/updateFileSystem/open-and-close-files.txt b/tests/baselines/reference/tsserver/updateFileSystem/open-and-close-files.txt index 5b11517890e..b4722c13d5d 100644 --- a/tests/baselines/reference/tsserver/updateFileSystem/open-and-close-files.txt +++ b/tests/baselines/reference/tsserver/updateFileSystem/open-and-close-files.txt @@ -1,21 +1,21 @@ #### Initial updateFileSystem -//// [/a/b/app.ts] added +//// [/a/b/app.ts] import { xyz } from './file3'; let x = xyz -//// [/a/b/commonFile1.ts] added +//// [/a/b/commonFile1.ts] let x = 1 -//// [/a/b/commonFile2.ts] added +//// [/a/b/commonFile2.ts] let y = 1 -//// [/a/b/file3.ts] added +//// [/a/b/file3.ts] export let xyz = 1; -//// [/a/b/tsconfig.json] added +//// [/a/b/tsconfig.json] {} -//// [/a/lib/lib.d.ts] added +//// [/a/lib/lib.d.ts] /// interface Boolean {} interface Function {} @@ -31,17 +31,16 @@ interface Array { length: number; [n: number]: T; } #### Opening app.ts -No changes. + #### Opening file3.ts -No changes. + #### non-delete -No changes. + #### delete //// [/a/b/commonFile1.ts] deleted #### close -No changes. \ No newline at end of file