Skip to content

Commit 2f4a855

Browse files
committed
Use rooted paths in the fourslash virtual file system
1 parent cc35bd5 commit 2f4a855

34 files changed

+81
-80
lines changed

src/compiler/checker.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19892,7 +19892,7 @@ namespace ts {
1989219892
function getAmbientModules(): Symbol[] {
1989319893
const result: Symbol[] = [];
1989419894
for (const sym in globals) {
19895-
if (globals.hasOwnProperty(sym) && ambientModuleSymbolRegex.test(sym)) {
19895+
if (hasProperty(globals, sym) && ambientModuleSymbolRegex.test(sym)) {
1989619896
result.push(globals[sym]);
1989719897
}
1989819898
}

src/harness/fourslash.ts

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2352,12 +2352,16 @@ namespace FourSlash {
23522352
}
23532353

23542354
export function runFourSlashTestContent(basePath: string, testType: FourSlashTestType, content: string, fileName: string): void {
2355+
// Give file paths an absolute path for the virtual file system
2356+
const absoluteBasePath = ts.combinePaths(Harness.virtualFileSystemRoot, basePath);
2357+
const absoluteFileName = ts.combinePaths(Harness.virtualFileSystemRoot, fileName);
2358+
23552359
// Parse out the files and their metadata
2356-
const testData = parseTestData(basePath, content, fileName);
2357-
const state = new TestState(basePath, testType, testData);
2360+
const testData = parseTestData(absoluteBasePath, content, absoluteFileName);
2361+
const state = new TestState(absoluteBasePath, testType, testData);
23582362
const output = ts.transpileModule(content, { reportDiagnostics: true });
23592363
if (output.diagnostics.length > 0) {
2360-
throw new Error(`Syntax error in ${basePath}: ${output.diagnostics[0].messageText}`);
2364+
throw new Error(`Syntax error in ${absoluteBasePath}: ${output.diagnostics[0].messageText}`);
23612365
}
23622366
runCode(output.outputText, state);
23632367
}

src/harness/harness.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -458,6 +458,9 @@ namespace Harness {
458458
// harness always uses one kind of new line
459459
const harnessNewLine = "\r\n";
460460

461+
// Roote for file paths that are stored in a virtual file system
462+
export const virtualFileSystemRoot = "/";
463+
461464
namespace IOImpl {
462465
declare class Enumerator {
463466
public atEnd(): boolean;

src/harness/harnessLanguageService.ts

Lines changed: 4 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ namespace Harness.LanguageService {
123123
}
124124

125125
export class LanguageServiceAdapterHost {
126-
protected virtualFileSystem: Utils.VirtualFileSystem<ScriptInfo> = new Utils.VirtualFileSystem<ScriptInfo>(/*root*/"c:", /*useCaseSensitiveFilenames*/false);
126+
protected virtualFileSystem: Utils.VirtualFileSystem<ScriptInfo> = new Utils.VirtualFileSystem<ScriptInfo>(virtualFileSystemRoot, /*useCaseSensitiveFilenames*/false);
127127

128128
constructor(protected cancellationToken = DefaultHostCancellationToken.Instance,
129129
protected settings = ts.getDefaultCompilerOptions()) {
@@ -191,7 +191,7 @@ namespace Harness.LanguageService {
191191
}
192192
return [];
193193
}
194-
getCurrentDirectory(): string { return ""; }
194+
getCurrentDirectory(): string { return virtualFileSystemRoot }
195195
getDefaultLibFileName(): string { return Harness.Compiler.defaultLibFileName; }
196196
getScriptFileNames(): string[] { return this.getFilenames(); }
197197
getScriptSnapshot(fileName: string): ts.IScriptSnapshot {
@@ -211,7 +211,7 @@ namespace Harness.LanguageService {
211211
readDirectory(path: string, extensions?: string[], exclude?: string[], include?: string[]): string[] {
212212
return ts.matchFiles(path, extensions, exclude, include,
213213
/*useCaseSensitiveFileNames*/false,
214-
/*currentDirectory*/"/",
214+
this.getCurrentDirectory(),
215215
(p) => this.virtualFileSystem.getAccessibleFileSystemEntries(p));
216216
}
217217
readFile(path: string, encoding?: string): string {
@@ -220,19 +220,7 @@ namespace Harness.LanguageService {
220220
}
221221
resolvePath(path: string): string {
222222
if (!ts.isRootedDiskPath(path)) {
223-
// An "absolute" path for fourslash is one that is contained within the tests directory
224-
const components = ts.getNormalizedPathComponents(path, this.getCurrentDirectory());
225-
if (components.length) {
226-
// If this is still a relative path after normalization (i.e. currentDirectory is relative), the root will be the empty string
227-
if (!components[0]) {
228-
components.splice(0, 1);
229-
if (components[0] !== "tests") {
230-
// If not contained within test, assume its relative to the directory containing the test files
231-
return ts.normalizePath(ts.combinePaths("tests/cases/fourslash", components.join(ts.directorySeparator)));
232-
}
233-
}
234-
return ts.normalizePath(components.join(ts.directorySeparator));
235-
}
223+
path = ts.combinePaths(this.getCurrentDirectory(), path);
236224
}
237225
return ts.normalizePath(path);
238226
}

src/harness/virtualFileSystem.ts

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,7 @@ namespace Utils {
111111
getFileSystemEntries() { return this.root.getFileSystemEntries(); }
112112

113113
addDirectory(path: string) {
114+
path = this.normalizePathRoot(path);
114115
const components = ts.getNormalizedPathComponents(path, this.currentDirectory);
115116
let directory: VirtualDirectory<T> = this.root;
116117
for (const component of components) {
@@ -124,7 +125,7 @@ namespace Utils {
124125
}
125126

126127
addFile(path: string, content?: T) {
127-
const absolutePath = ts.getNormalizedAbsolutePath(path, this.currentDirectory);
128+
const absolutePath = this.normalizePathRoot(ts.getNormalizedAbsolutePath(path, this.currentDirectory));
128129
const fileName = ts.getBaseFileName(path);
129130
const directoryPath = ts.getDirectoryPath(absolutePath);
130131
const directory = this.addDirectory(directoryPath);
@@ -141,6 +142,7 @@ namespace Utils {
141142
}
142143

143144
traversePath(path: string) {
145+
path = this.normalizePathRoot(path);
144146
let directory: VirtualDirectory<T> = this.root;
145147
for (const component of ts.getNormalizedPathComponents(path, this.currentDirectory)) {
146148
const entry = directory.getFileSystemEntry(component);
@@ -192,7 +194,13 @@ namespace Utils {
192194
}
193195
}
194196

197+
normalizePathRoot(path: string) {
198+
const components = ts.getNormalizedPathComponents(path, this.currentDirectory);
195199

200+
// Toss the root component
201+
components[0] = "";
202+
return components.join(ts.directorySeparator);
203+
}
196204
}
197205

198206
export class MockParseConfigHost extends VirtualFileSystem<string> implements ts.ParseConfigHost {

src/services/services.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3154,9 +3154,7 @@ namespace ts {
31543154
writeFile: (fileName, data, writeByteOrderMark) => { },
31553155
getCurrentDirectory: () => currentDirectory,
31563156
fileExists: (fileName): boolean => {
3157-
// stub missing host functionality
3158-
Debug.assert(!host.resolveModuleNames || !host.resolveTypeReferenceDirectives);
3159-
return hostCache.getOrCreateEntry(fileName) !== undefined;
3157+
return host.fileExists(fileName);
31603158
},
31613159
readFile: (fileName): string => {
31623160
// stub missing host functionality
Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
EmitSkipped: true
22
Diagnostics:
3-
Cannot write file 'tests/cases/fourslash/b.js' because it would overwrite input file.
3+
Cannot write file '/tests/cases/fourslash/b.js' because it would overwrite input file.
44

55
EmitSkipped: false
6-
FileName : tests/cases/fourslash/a.js
6+
FileName : /tests/cases/fourslash/a.js
77
function foo2() { return 30; } // no error - should emit a.js
88

tests/baselines/reference/getEmitOutput-pp.baseline

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,27 @@
11
EmitSkipped: false
2-
FileName : tests/cases/fourslash/shims-pp/inputFile1.js
2+
FileName : /tests/cases/fourslash/shims-pp/inputFile1.js
33
var x = 5;
44
var Bar = (function () {
55
function Bar() {
66
}
77
return Bar;
88
}());
9-
FileName : tests/cases/fourslash/shims-pp/inputFile1.d.ts
9+
FileName : /tests/cases/fourslash/shims-pp/inputFile1.d.ts
1010
declare var x: number;
1111
declare class Bar {
1212
x: string;
1313
y: number;
1414
}
1515

1616
EmitSkipped: false
17-
FileName : tests/cases/fourslash/shims-pp/inputFile2.js
17+
FileName : /tests/cases/fourslash/shims-pp/inputFile2.js
1818
var x1 = "hello world";
1919
var Foo = (function () {
2020
function Foo() {
2121
}
2222
return Foo;
2323
}());
24-
FileName : tests/cases/fourslash/shims-pp/inputFile2.d.ts
24+
FileName : /tests/cases/fourslash/shims-pp/inputFile2.d.ts
2525
declare var x1: string;
2626
declare class Foo {
2727
x: string;

tests/baselines/reference/getEmitOutput.baseline

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,27 @@
11
EmitSkipped: false
2-
FileName : tests/cases/fourslash/shims/inputFile1.js
2+
FileName : /tests/cases/fourslash/shims/inputFile1.js
33
var x = 5;
44
var Bar = (function () {
55
function Bar() {
66
}
77
return Bar;
88
}());
9-
FileName : tests/cases/fourslash/shims/inputFile1.d.ts
9+
FileName : /tests/cases/fourslash/shims/inputFile1.d.ts
1010
declare var x: number;
1111
declare class Bar {
1212
x: string;
1313
y: number;
1414
}
1515

1616
EmitSkipped: false
17-
FileName : tests/cases/fourslash/shims/inputFile2.js
17+
FileName : /tests/cases/fourslash/shims/inputFile2.js
1818
var x1 = "hello world";
1919
var Foo = (function () {
2020
function Foo() {
2121
}
2222
return Foo;
2323
}());
24-
FileName : tests/cases/fourslash/shims/inputFile2.d.ts
24+
FileName : /tests/cases/fourslash/shims/inputFile2.d.ts
2525
declare var x1: string;
2626
declare class Foo {
2727
x: string;

tests/baselines/reference/getEmitOutputDeclarationMultiFiles.baseline

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,27 @@
11
EmitSkipped: false
2-
FileName : tests/cases/fourslash/inputFile1.js
2+
FileName : /tests/cases/fourslash/inputFile1.js
33
var x = 5;
44
var Bar = (function () {
55
function Bar() {
66
}
77
return Bar;
88
}());
9-
FileName : tests/cases/fourslash/inputFile1.d.ts
9+
FileName : /tests/cases/fourslash/inputFile1.d.ts
1010
declare var x: number;
1111
declare class Bar {
1212
x: string;
1313
y: number;
1414
}
1515

1616
EmitSkipped: false
17-
FileName : tests/cases/fourslash/inputFile2.js
17+
FileName : /tests/cases/fourslash/inputFile2.js
1818
var x1 = "hello world";
1919
var Foo = (function () {
2020
function Foo() {
2121
}
2222
return Foo;
2323
}());
24-
FileName : tests/cases/fourslash/inputFile2.d.ts
24+
FileName : /tests/cases/fourslash/inputFile2.d.ts
2525
declare var x1: string;
2626
declare class Foo {
2727
x: string;

0 commit comments

Comments
 (0)