added tests

This commit is contained in:
Vladimir Matveev
2016-07-21 14:17:22 -07:00
parent 7da455c390
commit 2c254773bb
3 changed files with 62 additions and 17 deletions

View File

@@ -1291,5 +1291,39 @@ namespace ts {
projectService.ensureInferredProjectsUpToDate_TestOnly();
checkNumberOfProjects(projectService, { inferredProjects: 2 });
});
it("files with mixed content are handled correctly", () => {
const file1 = {
path: "/a/b/f1.html",
content: `<html><script language="javascript">var x = 1;</></html>`
};
const host = createServerHost([file1]);
const projectService = new server.ProjectService(host, nullLogger, nullCancellationToken, /*useSingleInferredProject*/ false);
const projectFileName = "projectFileName";
projectService.openExternalProject({ projectFileName, options: {}, rootFiles: [{ fileName: file1.path, scriptKind: ScriptKind.JS, hasMixedContent: true }] });
checkNumberOfProjects(projectService, { externalProjects: 1 });
checkWatchedFiles(host, []);
const project = projectService.externalProjects[0];
const scriptInfo = project.getScriptInfo(file1.path);
const snap = scriptInfo.snap();
const actualText = snap.getText(0, snap.getLength());
assert.equal(actualText, "", `expected content to be empty string, got "${actualText}"`);
projectService.openClientFile(file1.path, `var x = 1;`);
project.updateGraph();
const quickInfo = project.languageService.getQuickInfoAtPosition(file1.path, 4);
assert.equal(quickInfo.kind, ScriptElementKind.variableElement);
projectService.closeClientFile(file1.path);
const scriptInfo2 = project.getScriptInfo(file1.path);
const snap2 = scriptInfo2.snap();
const actualText2 = snap2.getText(0, snap.getLength());
assert.equal(actualText2, "", `expected content to be empty string, got "${actualText2}"`);
});
});
}

View File

@@ -647,12 +647,13 @@ namespace ts.server {
return { success: true, projectOptions };
}
private exceededTotalSizeLimitForNonTsFiles(options: CompilerOptions, fileNames: string[]) {
private exceededTotalSizeLimitForNonTsFiles<T>(options: CompilerOptions, fileNames: T[], propertyReader: FilePropertyReader<T>) {
if (options && options.disableSizeLimit || !this.host.getFileSize) {
return false;
}
let totalNonTsFileSize = 0;
for (const fileName of fileNames) {
for (const f of fileNames) {
const fileName = propertyReader.getFileName(f);
if (hasTypeScriptFileExtension(fileName)) {
continue;
}
@@ -664,21 +665,21 @@ namespace ts.server {
return false;
}
private createAndAddExternalProject(projectFileName: string, files: NormalizedPath[], compilerOptions: CompilerOptions) {
private createAndAddExternalProject(projectFileName: string, files: protocol.ExternalFile[], compilerOptions: CompilerOptions) {
const project = new ExternalProject(
projectFileName,
this,
this.documentRegistry,
compilerOptions,
/*languageServiceEnabled*/ !this.exceededTotalSizeLimitForNonTsFiles(compilerOptions, files));
/*languageServiceEnabled*/ !this.exceededTotalSizeLimitForNonTsFiles(compilerOptions, files, externalFilePropertyReader));
const errors = this.addFilesToProjectAndUpdateGraph(project, files, /*clientFileName*/ undefined);
const errors = this.addFilesToProjectAndUpdateGraph(project, files, externalFilePropertyReader, /*clientFileName*/ undefined);
this.externalProjects.push(project);
return { project, errors };
}
private createAndAddConfiguredProject(configFileName: NormalizedPath, projectOptions: ProjectOptions, clientFileName?: string) {
const sizeLimitExceeded = this.exceededTotalSizeLimitForNonTsFiles(projectOptions.compilerOptions, projectOptions.files);
const sizeLimitExceeded = this.exceededTotalSizeLimitForNonTsFiles(projectOptions.compilerOptions, projectOptions.files, fileNamePropertyReader);
const project = new ConfiguredProject(
configFileName,
this,
@@ -688,7 +689,7 @@ namespace ts.server {
projectOptions.wildcardDirectories,
/*languageServiceEnabled*/ !sizeLimitExceeded);
const errors = this.addFilesToProjectAndUpdateGraph(project, projectOptions.files, clientFileName);
const errors = this.addFilesToProjectAndUpdateGraph(project, projectOptions.files, fileNamePropertyReader, clientFileName);
project.watchConfigFile(project => this.onConfigChangedForConfiguredProject(project));
if (!sizeLimitExceeded) {
@@ -706,11 +707,14 @@ namespace ts.server {
}
}
private addFilesToProjectAndUpdateGraph(project: ConfiguredProject | ExternalProject, files: string[], clientFileName: string): Diagnostic[] {
private addFilesToProjectAndUpdateGraph<T>(project: ConfiguredProject | ExternalProject, files: T[], propertyReader: FilePropertyReader<T>, clientFileName: string): Diagnostic[] {
let errors: Diagnostic[];
for (const rootFilename of files) {
for (const f of files) {
const rootFilename = propertyReader.getFileName(f);
const scriptKind = propertyReader.getScriptKind(f);
const hasMixedContent = propertyReader.hasMixedContent(f);
if (this.host.fileExists(rootFilename)) {
const info = this.getOrCreateScriptInfoForNormalizedPath(toNormalizedPath(rootFilename), /*openedByClient*/ clientFileName == rootFilename);
const info = this.getOrCreateScriptInfoForNormalizedPath(toNormalizedPath(rootFilename), /*openedByClient*/ clientFileName == rootFilename, /*fileContent*/ undefined, scriptKind, hasMixedContent);
project.addRoot(info);
}
else {
@@ -805,7 +809,7 @@ namespace ts.server {
return errors;
}
if (this.exceededTotalSizeLimitForNonTsFiles(projectOptions.compilerOptions, projectOptions.files)) {
if (this.exceededTotalSizeLimitForNonTsFiles(projectOptions.compilerOptions, projectOptions.files, fileNamePropertyReader)) {
project.setCompilerOptions(projectOptions.compilerOptions);
if (!project.languageServiceEnabled) {
// language service is already disabled
@@ -872,7 +876,7 @@ namespace ts.server {
}
}
if (content !== undefined) {
info = new ScriptInfo(this.host, fileName, content, scriptKind, openedByClient);
info = new ScriptInfo(this.host, fileName, content, scriptKind, openedByClient, hasMixedContent);
info.setFormatOptions(toEditorSettings(this.getFormatCodeOptions()));
this.filenameToScriptInfo.set(fileName, info);
if (!info.isOpen && !hasMixedContent) {
@@ -1095,14 +1099,14 @@ namespace ts.server {
}
let tsConfigFiles: NormalizedPath[];
const rootFiles: NormalizedPath[] = [];
const rootFiles: protocol.ExternalFile[] = [];
for (const file of proj.rootFiles) {
const normalized = toNormalizedPath(file.fileName);
if (getBaseFileName(normalized) === "tsconfig.json") {
(tsConfigFiles || (tsConfigFiles = [])).push(normalized);
}
else {
rootFiles.push(normalized);
rootFiles.push(file);
}
}
if (tsConfigFiles) {

View File

@@ -13,12 +13,14 @@ namespace ts.server {
private fileWatcher: FileWatcher;
private svc: ScriptVersionCache;
// TODO: allow to update hasMixedContent from the outside
constructor(
private readonly host: ServerHost,
readonly fileName: NormalizedPath,
content: string,
readonly scriptKind: ScriptKind,
public isOpen = false) {
public isOpen = false,
private hasMixedContent = false) {
this.path = toPath(fileName, host.getCurrentDirectory(), createGetCanonicalFileName(host.useCaseSensitiveFileNames));
this.svc = ScriptVersionCache.fromString(host, content);
@@ -116,8 +118,13 @@ namespace ts.server {
}
reloadFromFile() {
this.svc.reloadFromFile(this.fileName);
this.markContainingProjectsAsDirty();
if (this.hasMixedContent) {
this.reload("");
}
else {
this.svc.reloadFromFile(this.fileName);
this.markContainingProjectsAsDirty();
}
}
snap() {