mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-05-15 04:43:37 -05:00
Merge pull request #20515 from Microsoft/fileAddedAfterProjectOpen
Update the project graph before checking if opened file is present in the existing project
This commit is contained in:
@@ -3510,6 +3510,38 @@ namespace ts.projectSystem {
|
||||
it("works when project root is used with case-insensitive system", () => {
|
||||
verifyOpenFileWorks(/*useCaseSensitiveFileNames*/ false);
|
||||
});
|
||||
|
||||
it("uses existing project even if project refresh is pending", () => {
|
||||
const projectFolder = "/user/someuser/projects/myproject";
|
||||
const aFile: FileOrFolder = {
|
||||
path: `${projectFolder}/src/a.ts`,
|
||||
content: "export const x = 0;"
|
||||
};
|
||||
const configFile: FileOrFolder = {
|
||||
path: `${projectFolder}/tsconfig.json`,
|
||||
content: "{}"
|
||||
};
|
||||
const files = [aFile, configFile, libFile];
|
||||
const host = createServerHost(files);
|
||||
const service = createProjectService(host);
|
||||
service.openClientFile(aFile.path, /*fileContent*/ undefined, ScriptKind.TS, projectFolder);
|
||||
verifyProject();
|
||||
|
||||
const bFile: FileOrFolder = {
|
||||
path: `${projectFolder}/src/b.ts`,
|
||||
content: `export {}; declare module "./a" { export const y: number; }`
|
||||
};
|
||||
files.push(bFile);
|
||||
host.reloadFS(files);
|
||||
service.openClientFile(bFile.path, /*fileContent*/ undefined, ScriptKind.TS, projectFolder);
|
||||
verifyProject();
|
||||
|
||||
function verifyProject() {
|
||||
assert.isDefined(service.configuredProjects.get(configFile.path));
|
||||
const project = service.configuredProjects.get(configFile.path);
|
||||
checkProjectActualFiles(project, files.map(f => f.path));
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
describe("tsserverProjectSystem Language service", () => {
|
||||
|
||||
@@ -727,15 +727,6 @@ namespace ts.server {
|
||||
}
|
||||
}
|
||||
|
||||
private findContainingExternalProject(fileName: NormalizedPath): ExternalProject {
|
||||
for (const proj of this.externalProjects) {
|
||||
if (proj.containsFile(fileName)) {
|
||||
return proj;
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
getFormatCodeOptions(file?: NormalizedPath) {
|
||||
let formatCodeSettings: FormatCodeSettings;
|
||||
if (file) {
|
||||
@@ -1994,13 +1985,24 @@ namespace ts.server {
|
||||
return this.openClientFileWithNormalizedPath(toNormalizedPath(fileName), fileContent, scriptKind, /*hasMixedContent*/ false, projectRootPath ? toNormalizedPath(projectRootPath) : undefined);
|
||||
}
|
||||
|
||||
private findExternalProjetContainingOpenScriptInfo(info: ScriptInfo): ExternalProject {
|
||||
for (const proj of this.externalProjects) {
|
||||
// Ensure project structure is uptodate to check if info is present in external project
|
||||
proj.updateGraph();
|
||||
if (proj.containsScriptInfo(info)) {
|
||||
return proj;
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
openClientFileWithNormalizedPath(fileName: NormalizedPath, fileContent?: string, scriptKind?: ScriptKind, hasMixedContent?: boolean, projectRootPath?: NormalizedPath): OpenConfiguredProjectResult {
|
||||
let configFileName: NormalizedPath;
|
||||
let sendConfigFileDiagEvent = false;
|
||||
let configFileErrors: ReadonlyArray<Diagnostic>;
|
||||
|
||||
const info = this.getOrCreateScriptInfoOpenedByClientForNormalizedPath(fileName, projectRootPath ? this.getNormalizedAbsolutePath(projectRootPath) : this.currentDirectory, fileContent, scriptKind, hasMixedContent);
|
||||
let project: ConfiguredProject | ExternalProject = this.findContainingExternalProject(fileName);
|
||||
let project: ConfiguredProject | ExternalProject = this.findExternalProjetContainingOpenScriptInfo(info);
|
||||
if (!project) {
|
||||
configFileName = this.getConfigFileNameForFile(info, projectRootPath);
|
||||
if (configFileName) {
|
||||
@@ -2010,6 +2012,10 @@ namespace ts.server {
|
||||
// Send the event only if the project got created as part of this open request
|
||||
sendConfigFileDiagEvent = true;
|
||||
}
|
||||
else {
|
||||
// Ensure project is ready to check if it contains opened script info
|
||||
project.updateGraph();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (project && !project.languageServiceEnabled) {
|
||||
|
||||
@@ -7789,7 +7789,6 @@ declare namespace ts.server {
|
||||
* @param forceInferredProjectsRefresh when true updates the inferred projects even if there is no pending work to update the files/project structures
|
||||
*/
|
||||
private ensureProjectStructuresUptoDate(forceInferredProjectsRefresh?);
|
||||
private findContainingExternalProject(fileName);
|
||||
getFormatCodeOptions(file?: NormalizedPath): FormatCodeSettings;
|
||||
private updateProjectGraphs(projects);
|
||||
private onSourceFileChanged(fileName, eventKind);
|
||||
@@ -7907,6 +7906,7 @@ declare namespace ts.server {
|
||||
* @param fileContent is a known version of the file content that is more up to date than the one on disk
|
||||
*/
|
||||
openClientFile(fileName: string, fileContent?: string, scriptKind?: ScriptKind, projectRootPath?: string): OpenConfiguredProjectResult;
|
||||
private findExternalProjetContainingOpenScriptInfo(info);
|
||||
openClientFileWithNormalizedPath(fileName: NormalizedPath, fileContent?: string, scriptKind?: ScriptKind, hasMixedContent?: boolean, projectRootPath?: NormalizedPath): OpenConfiguredProjectResult;
|
||||
/**
|
||||
* Close file whose contents is managed by the client
|
||||
|
||||
Reference in New Issue
Block a user