Skip to content

Commit 1fb969f

Browse files
author
Zhengbo Li
authored
Split tests and fix issues with missing referenced files (microsoft#10599)
* Split tsserver project system tests to seperate files * fix issues with missing references * Incorporate changes in tsserverVS-WIP branch * drop ts prefix
1 parent 38ce627 commit 1fb969f

8 files changed

Lines changed: 923 additions & 854 deletions

File tree

Jakefile.js

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -209,6 +209,9 @@ var harnessSources = harnessCoreSources.concat([
209209
"convertCompilerOptionsFromJson.ts",
210210
"convertTypingOptionsFromJson.ts",
211211
"tsserverProjectSystem.ts",
212+
"compileOnSave.ts",
213+
"typingsInstaller.ts",
214+
"projectErrors.ts",
212215
"matchFiles.ts",
213216
"initializeTSConfig.ts",
214217
].map(function (f) {

src/harness/tsconfig.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -90,6 +90,9 @@
9090
"./unittests/convertTypingOptionsFromJson.ts",
9191
"./unittests/tsserverProjectSystem.ts",
9292
"./unittests/matchFiles.ts",
93-
"./unittests/initializeTSConfig.ts"
93+
"./unittests/initializeTSConfig.ts",
94+
"./unittests/compileOnSave.ts",
95+
"./unittests/typingsInstaller.ts",
96+
"./unittests/projectErrors.ts"
9497
]
9598
}

src/harness/unittests/compileOnSave.ts

Lines changed: 495 additions & 0 deletions
Large diffs are not rendered by default.
Lines changed: 186 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,186 @@
1+
/// <reference path="../harness.ts" />
2+
/// <reference path="./tsserverProjectSystem.ts" />
3+
/// <reference path="../../server/typingsInstaller/typingsInstaller.ts" />
4+
5+
namespace ts.projectSystem {
6+
describe("Project errors", () => {
7+
function checkProjectErrors(projectFiles: server.ProjectFilesWithTSDiagnostics, expectedErrors: string[]) {
8+
assert.isTrue(projectFiles !== undefined, "missing project files");
9+
const errors = projectFiles.projectErrors;
10+
assert.equal(errors ? errors.length : 0, expectedErrors.length, `expected ${expectedErrors.length} error in the list`);
11+
if (expectedErrors.length) {
12+
for (let i = 0; i < errors.length; i++) {
13+
const actualMessage = flattenDiagnosticMessageText(errors[i].messageText, "\n");
14+
const expectedMessage = expectedErrors[i];
15+
assert.isTrue(actualMessage.indexOf(expectedMessage) === 0, `error message does not match, expected ${actualMessage} to start with ${expectedMessage}`);
16+
}
17+
}
18+
}
19+
20+
it("external project - diagnostics for missing files", () => {
21+
const file1 = {
22+
path: "/a/b/app.ts",
23+
content: ""
24+
};
25+
const file2 = {
26+
path: "/a/b/lib.ts",
27+
content: ""
28+
};
29+
// only file1 exists - expect error
30+
const host = createServerHost([file1]);
31+
const projectService = createProjectService(host);
32+
const projectFileName = "/a/b/test.csproj";
33+
34+
{
35+
projectService.openExternalProject({
36+
projectFileName,
37+
options: {},
38+
rootFiles: toExternalFiles([file1.path, file2.path])
39+
});
40+
41+
projectService.checkNumberOfProjects({ externalProjects: 1 });
42+
const knownProjects = projectService.synchronizeProjectList([]);
43+
checkProjectErrors(knownProjects[0], ["File '/a/b/lib.ts' not found."]);
44+
}
45+
// only file2 exists - expect error
46+
host.reloadFS([file2]);
47+
{
48+
projectService.openExternalProject({
49+
projectFileName,
50+
options: {},
51+
rootFiles: toExternalFiles([file1.path, file2.path])
52+
});
53+
projectService.checkNumberOfProjects({ externalProjects: 1 });
54+
const knownProjects = projectService.synchronizeProjectList([]);
55+
checkProjectErrors(knownProjects[0], ["File '/a/b/app.ts' not found."]);
56+
}
57+
58+
// both files exist - expect no errors
59+
host.reloadFS([file1, file2]);
60+
{
61+
projectService.openExternalProject({
62+
projectFileName,
63+
options: {},
64+
rootFiles: toExternalFiles([file1.path, file2.path])
65+
});
66+
67+
projectService.checkNumberOfProjects({ externalProjects: 1 });
68+
const knownProjects = projectService.synchronizeProjectList([]);
69+
checkProjectErrors(knownProjects[0], []);
70+
}
71+
});
72+
73+
it("configured projects - diagnostics for missing files", () => {
74+
const file1 = {
75+
path: "/a/b/app.ts",
76+
content: ""
77+
};
78+
const file2 = {
79+
path: "/a/b/lib.ts",
80+
content: ""
81+
};
82+
const config = {
83+
path: "/a/b/tsconfig.json",
84+
content: JSON.stringify({ files: [file1, file2].map(f => getBaseFileName(f.path)) })
85+
};
86+
const host = createServerHost([file1, config]);
87+
const projectService = createProjectService(host);
88+
89+
projectService.openClientFile(file1.path);
90+
projectService.checkNumberOfProjects({ configuredProjects: 1 });
91+
checkProjectErrors(projectService.synchronizeProjectList([])[0], ["File '/a/b/lib.ts' not found."]);
92+
93+
host.reloadFS([file1, file2, config]);
94+
95+
projectService.openClientFile(file1.path);
96+
projectService.checkNumberOfProjects({ configuredProjects: 1 });
97+
checkProjectErrors(projectService.synchronizeProjectList([])[0], []);
98+
});
99+
100+
it("configured projects - diagnostics for corrupted config 1", () => {
101+
const file1 = {
102+
path: "/a/b/app.ts",
103+
content: ""
104+
};
105+
const file2 = {
106+
path: "/a/b/lib.ts",
107+
content: ""
108+
};
109+
const correctConfig = {
110+
path: "/a/b/tsconfig.json",
111+
content: JSON.stringify({ files: [file1, file2].map(f => getBaseFileName(f.path)) })
112+
};
113+
const corruptedConfig = {
114+
path: correctConfig.path,
115+
content: correctConfig.content.substr(1)
116+
};
117+
const host = createServerHost([file1, file2, corruptedConfig]);
118+
const projectService = createProjectService(host);
119+
120+
projectService.openClientFile(file1.path);
121+
{
122+
projectService.checkNumberOfProjects({ configuredProjects: 1 });
123+
const configuredProject = forEach(projectService.synchronizeProjectList([]), f => f.info.projectName === corruptedConfig.path && f);
124+
assert.isTrue(configuredProject !== undefined, "should find configured project");
125+
checkProjectErrors(configuredProject, [
126+
"')' expected.",
127+
"Declaration or statement expected.",
128+
"Declaration or statement expected.",
129+
"Failed to parse file '/a/b/tsconfig.json'"
130+
]);
131+
}
132+
// fix config and trigger watcher
133+
host.reloadFS([file1, file2, correctConfig]);
134+
host.triggerFileWatcherCallback(correctConfig.path, /*false*/);
135+
{
136+
projectService.checkNumberOfProjects({ configuredProjects: 1 });
137+
const configuredProject = forEach(projectService.synchronizeProjectList([]), f => f.info.projectName === corruptedConfig.path && f);
138+
assert.isTrue(configuredProject !== undefined, "should find configured project");
139+
checkProjectErrors(configuredProject, []);
140+
}
141+
});
142+
143+
it("configured projects - diagnostics for corrupted config 2", () => {
144+
const file1 = {
145+
path: "/a/b/app.ts",
146+
content: ""
147+
};
148+
const file2 = {
149+
path: "/a/b/lib.ts",
150+
content: ""
151+
};
152+
const correctConfig = {
153+
path: "/a/b/tsconfig.json",
154+
content: JSON.stringify({ files: [file1, file2].map(f => getBaseFileName(f.path)) })
155+
};
156+
const corruptedConfig = {
157+
path: correctConfig.path,
158+
content: correctConfig.content.substr(1)
159+
};
160+
const host = createServerHost([file1, file2, correctConfig]);
161+
const projectService = createProjectService(host);
162+
163+
projectService.openClientFile(file1.path);
164+
{
165+
projectService.checkNumberOfProjects({ configuredProjects: 1 });
166+
const configuredProject = forEach(projectService.synchronizeProjectList([]), f => f.info.projectName === corruptedConfig.path && f);
167+
assert.isTrue(configuredProject !== undefined, "should find configured project");
168+
checkProjectErrors(configuredProject, []);
169+
}
170+
// break config and trigger watcher
171+
host.reloadFS([file1, file2, corruptedConfig]);
172+
host.triggerFileWatcherCallback(corruptedConfig.path, /*false*/);
173+
{
174+
projectService.checkNumberOfProjects({ configuredProjects: 1 });
175+
const configuredProject = forEach(projectService.synchronizeProjectList([]), f => f.info.projectName === corruptedConfig.path && f);
176+
assert.isTrue(configuredProject !== undefined, "should find configured project");
177+
checkProjectErrors(configuredProject, [
178+
"')' expected.",
179+
"Declaration or statement expected.",
180+
"Declaration or statement expected.",
181+
"Failed to parse file '/a/b/tsconfig.json'"
182+
]);
183+
}
184+
});
185+
});
186+
}

0 commit comments

Comments
 (0)