From e8c5a591a48f6c42fbb040bfc0d0fd1dd8126239 Mon Sep 17 00:00:00 2001 From: Vladimir Matveev Date: Wed, 15 Jun 2016 13:05:55 -0700 Subject: [PATCH] getSemanticDiagnostics --- src/server/editorServices.ts | 9 +++++++++ src/server/protocol.d.ts | 15 +++++++++++++++ src/server/session.ts | 27 +++++++++++++++++++++++++++ src/services/services.ts | 16 ++++++++++++++++ src/services/shims.ts | 15 --------------- 5 files changed, 67 insertions(+), 15 deletions(-) diff --git a/src/server/editorServices.ts b/src/server/editorServices.ts index 22da5536eff..0e01c4c5baa 100644 --- a/src/server/editorServices.ts +++ b/src/server/editorServices.ts @@ -676,6 +676,15 @@ namespace ts.server { } } + getProject(projectFileName: string): Project { + // TODO: fixme + if (!projectFileName) { + // TODO: fixme + return this.inferredProjects.length ? this.inferredProjects[0] : undefined; + } + return this.findExternalProjectByProjectFileName(projectFileName) || this.findConfiguredProjectByConfigFile(projectFileName); + } + getFormatCodeOptions(file?: string) { if (file) { const info = this.filenameToScriptInfo[file]; diff --git a/src/server/protocol.d.ts b/src/server/protocol.d.ts index 6f2adc6d7d4..ef66b0119d4 100644 --- a/src/server/protocol.d.ts +++ b/src/server/protocol.d.ts @@ -91,6 +91,11 @@ declare namespace ts.server.protocol { * The file for the request (absolute pathname required). */ file: string; + + /* + * Optional name of project that contains file + */ + projectFileName?: string; } /** @@ -125,6 +130,16 @@ declare namespace ts.server.protocol { fileNames?: string[]; } + export interface DiagnosticWithLinePosition { + message: string; + start: number; + length: number; + startLocation: Location; + endLocation: Location; + category: string; + code: number; + } + /** * Response message for "projectInfo" request */ diff --git a/src/server/session.ts b/src/server/session.ts index fa883fbe9de..d7c0fe96e20 100644 --- a/src/server/session.ts +++ b/src/server/session.ts @@ -114,6 +114,7 @@ namespace ts.server { export const Formatonkey = "formatonkey"; export const Geterr = "geterr"; export const GeterrForProject = "geterrForProject"; + export const SemanticDiagnosticsFull = "semanticDiagnostics-full"; export const NavBar = "navbar"; export const Navto = "navto"; export const Occurrences = "occurrences"; @@ -245,6 +246,29 @@ namespace ts.server { this.response(body, commandName, requestSequence, errorMessage); } + private getLocation(position: number, scriptInfo: ScriptInfo): protocol.Location { + const { line, offset } = scriptInfo.positionToLineOffset(position); + return { line, offset: offset + 1 }; + } + + private getSemanticDiagnostics(args: protocol.FileRequestArgs): protocol.DiagnosticWithLinePosition[] { + var project = this.projectService.getProject(args.projectFileName) || this.projectService.getProjectForFile(args.file); + if (!project) { + return []; + } + const scriptInfo = project.getScriptInfo(args.file); + const diagnostics = project.languageService.getSemanticDiagnostics(args.file); + return diagnostics.map(d => { + message: flattenDiagnosticMessageText(d.messageText, this.host.newLine), + start: d.start, + length: d.length, + category: DiagnosticCategory[d.category].toLowerCase(), + code: d.code, + startLocation: this.getLocation(d.start, scriptInfo), + endLocation: this.getLocation(d.start + d.length, scriptInfo) + }); + } + private semanticCheck(file: string, project: Project) { try { const diags = project.languageService.getSemanticDiagnostics(file); @@ -1170,6 +1194,9 @@ namespace ts.server { [CommandNames.SignatureHelpFull]: (request: protocol.SignatureHelpRequest) => { return this.requiredResponse(this.getSignatureHelpItems(request.arguments, /*simplifiedResult*/ false)); }, + [CommandNames.SemanticDiagnosticsFull]: (request: protocol.FileRequest) => { + return this.requiredResponse(this.getSemanticDiagnostics(request.arguments)); + }, [CommandNames.Geterr]: (request: protocol.Request) => { const geterrArgs = request.arguments; return { response: this.getDiagnostics(geterrArgs.delay, geterrArgs.files), responseRequired: false }; diff --git a/src/services/services.ts b/src/services/services.ts index 8931fa72542..9209fc157c2 100644 --- a/src/services/services.ts +++ b/src/services/services.ts @@ -124,6 +124,7 @@ namespace ts { return new StringScriptSnapshot(text); } } + export interface PreProcessedFileInfo { referencedFiles: FileReference[]; typeReferenceDirectives: FileReference[]; @@ -132,6 +133,21 @@ namespace ts { isLibFile: boolean; } + export function realizeDiagnostics(diagnostics: Diagnostic[], newLine: string): { message: string; start: number; length: number; category: string; code: number; }[] { + return diagnostics.map(d => realizeDiagnostic(d, newLine)); + } + + export function realizeDiagnostic(diagnostic: Diagnostic, newLine: string): { message: string; start: number; length: number; category: string; code: number; } { + return { + message: flattenDiagnosticMessageText(diagnostic.messageText, newLine), + start: diagnostic.start, + length: diagnostic.length, + /// TODO: no need for the tolowerCase call + category: DiagnosticCategory[diagnostic.category].toLowerCase(), + code: diagnostic.code + }; + } + const scanner: Scanner = createScanner(ScriptTarget.Latest, /*skipTrivia*/ true); const emptyArray: any[] = []; diff --git a/src/services/shims.ts b/src/services/shims.ts index 96392ca42be..4cc1944c94b 100644 --- a/src/services/shims.ts +++ b/src/services/shims.ts @@ -517,21 +517,6 @@ namespace ts { } } - export function realizeDiagnostics(diagnostics: Diagnostic[], newLine: string): { message: string; start: number; length: number; category: string; code: number; }[] { - return diagnostics.map(d => realizeDiagnostic(d, newLine)); - } - - function realizeDiagnostic(diagnostic: Diagnostic, newLine: string): { message: string; start: number; length: number; category: string; code: number; } { - return { - message: flattenDiagnosticMessageText(diagnostic.messageText, newLine), - start: diagnostic.start, - length: diagnostic.length, - /// TODO: no need for the tolowerCase call - category: DiagnosticCategory[diagnostic.category].toLowerCase(), - code: diagnostic.code - }; - } - class LanguageServiceShimObject extends ShimBase implements LanguageServiceShim { private logger: Logger; private logPerformance = false;