| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  | /** | 
					
						
							|  |  |  |  * @license | 
					
						
							|  |  |  |  * Copyright Google Inc. All Rights Reserved. | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  * Use of this source code is governed by an MIT-style license that can be | 
					
						
							|  |  |  |  * found in the LICENSE file at https://angular.io/license
 | 
					
						
							|  |  |  |  */ | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | import * as ts from 'typescript'; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | import {createLanguageService} from './language_service'; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  | import {Completion, Diagnostic, LanguageService, LanguageServiceHost} from './types'; | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  | import {TypeScriptServiceHost} from './typescript_host'; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  | const projectHostMap = new WeakMap<any, TypeScriptServiceHost>(); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | export function getExternalFiles(project: any): string[]|undefined { | 
					
						
							|  |  |  |   const host = projectHostMap.get(project); | 
					
						
							|  |  |  |   if (host) { | 
					
						
							|  |  |  |     return host.getTemplateReferences(); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | const angularOnlyResults = process.argv.indexOf('--angularOnlyResults') >= 0; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | function angularOnlyFilter(ls: ts.LanguageService): ts.LanguageService { | 
					
						
							|  |  |  |   return { | 
					
						
							|  |  |  |     cleanupSemanticCache: () => ls.cleanupSemanticCache(), | 
					
						
							|  |  |  |     getSyntacticDiagnostics: fileName => <ts.Diagnostic[]>[], | 
					
						
							|  |  |  |     getSemanticDiagnostics: fileName => <ts.Diagnostic[]>[], | 
					
						
							|  |  |  |     getCompilerOptionsDiagnostics: () => <ts.Diagnostic[]>[], | 
					
						
							|  |  |  |     getSyntacticClassifications: (fileName, span) => [], | 
					
						
							|  |  |  |     getSemanticClassifications: (fileName, span) => [], | 
					
						
							|  |  |  |     getEncodedSyntacticClassifications: (fileName, span) => <ts.Classifications><any>{undefined}, | 
					
						
							|  |  |  |     getEncodedSemanticClassifications: (fileName, span) => <ts.Classifications><any>undefined, | 
					
						
							|  |  |  |     getCompletionsAtPosition: (fileName, position) => <ts.CompletionInfo><any>undefined, | 
					
						
							|  |  |  |     getCompletionEntryDetails: (fileName, position, entryName) => | 
					
						
							|  |  |  |                                    <ts.CompletionEntryDetails><any>undefined, | 
					
						
							|  |  |  |     getCompletionEntrySymbol: (fileName, position, entryName) => <ts.Symbol><any>undefined, | 
					
						
							|  |  |  |     getQuickInfoAtPosition: (fileName, position) => <ts.QuickInfo><any>undefined, | 
					
						
							|  |  |  |     getNameOrDottedNameSpan: (fileName, startPos, endPos) => <ts.TextSpan><any>undefined, | 
					
						
							|  |  |  |     getBreakpointStatementAtPosition: (fileName, position) => <ts.TextSpan><any>undefined, | 
					
						
							|  |  |  |     getSignatureHelpItems: (fileName, position) => <ts.SignatureHelpItems><any>undefined, | 
					
						
							|  |  |  |     getRenameInfo: (fileName, position) => <ts.RenameInfo><any>undefined, | 
					
						
							|  |  |  |     findRenameLocations: (fileName, position, findInStrings, findInComments) => | 
					
						
							|  |  |  |                              <ts.RenameLocation[]>[], | 
					
						
							|  |  |  |     getDefinitionAtPosition: (fileName, position) => <ts.DefinitionInfo[]>[], | 
					
						
							|  |  |  |     getTypeDefinitionAtPosition: (fileName, position) => <ts.DefinitionInfo[]>[], | 
					
						
							|  |  |  |     getImplementationAtPosition: (fileName, position) => <ts.ImplementationLocation[]>[], | 
					
						
							|  |  |  |     getReferencesAtPosition: (fileName: string, position: number) => <ts.ReferenceEntry[]>[], | 
					
						
							|  |  |  |     findReferences: (fileName: string, position: number) => <ts.ReferencedSymbol[]>[], | 
					
						
							|  |  |  |     getDocumentHighlights: (fileName, position, filesToSearch) => <ts.DocumentHighlights[]>[], | 
					
						
							|  |  |  |     /** @deprecated */ | 
					
						
							|  |  |  |     getOccurrencesAtPosition: (fileName, position) => <ts.ReferenceEntry[]>[], | 
					
						
							|  |  |  |     getNavigateToItems: searchValue => <ts.NavigateToItem[]>[], | 
					
						
							|  |  |  |     getNavigationBarItems: fileName => <ts.NavigationBarItem[]>[], | 
					
						
							|  |  |  |     getNavigationTree: fileName => <ts.NavigationTree><any>undefined, | 
					
						
							|  |  |  |     getOutliningSpans: fileName => <ts.OutliningSpan[]>[], | 
					
						
							|  |  |  |     getTodoComments: (fileName, descriptors) => <ts.TodoComment[]>[], | 
					
						
							|  |  |  |     getBraceMatchingAtPosition: (fileName, position) => <ts.TextSpan[]>[], | 
					
						
							|  |  |  |     getIndentationAtPosition: (fileName, position, options) => <number><any>undefined, | 
					
						
							|  |  |  |     getFormattingEditsForRange: (fileName, start, end, options) => <ts.TextChange[]>[], | 
					
						
							|  |  |  |     getFormattingEditsForDocument: (fileName, options) => <ts.TextChange[]>[], | 
					
						
							|  |  |  |     getFormattingEditsAfterKeystroke: (fileName, position, key, options) => <ts.TextChange[]>[], | 
					
						
							|  |  |  |     getDocCommentTemplateAtPosition: (fileName, position) => <ts.TextInsertion><any>undefined, | 
					
						
							|  |  |  |     isValidBraceCompletionAtPosition: (fileName, position, openingBrace) => <boolean><any>undefined, | 
					
						
							|  |  |  |     getCodeFixesAtPosition: (fileName, start, end, errorCodes) => <ts.CodeAction[]>[], | 
					
						
							|  |  |  |     getEmitOutput: fileName => <ts.EmitOutput><any>undefined, | 
					
						
							|  |  |  |     getProgram: () => ls.getProgram(), | 
					
						
							| 
									
										
										
										
											2017-09-08 18:40:32 -07:00
										 |  |  |     dispose: () => ls.dispose(), | 
					
						
							|  |  |  |     getApplicableRefactors: (fileName, positionOrRaneg) => <ts.ApplicableRefactorInfo[]>[], | 
					
						
							|  |  |  |     getEditsForRefactor: (fileName, formatOptions, positionOrRange, refactorName, actionName) => | 
					
						
							|  |  |  |                              undefined, | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |   }; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  | export function create(info: any /* ts.server.PluginCreateInfo */): ts.LanguageService { | 
					
						
							|  |  |  |   // Create the proxy
 | 
					
						
							|  |  |  |   const proxy: ts.LanguageService = Object.create(null); | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |   let oldLS: ts.LanguageService = info.languageService; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   if (angularOnlyResults) { | 
					
						
							|  |  |  |     oldLS = angularOnlyFilter(oldLS); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   function tryCall<T>(fileName: string | undefined, callback: () => T): T { | 
					
						
							|  |  |  |     if (fileName && !oldLS.getProgram().getSourceFile(fileName)) { | 
					
						
							|  |  |  |       return undefined as any as T; | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     try { | 
					
						
							|  |  |  |       return callback(); | 
					
						
							|  |  |  |     } catch (e) { | 
					
						
							|  |  |  |       return undefined as any as T; | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   function tryFilenameCall<T>(m: (fileName: string) => T): (fileName: string) => T { | 
					
						
							|  |  |  |     return fileName => tryCall(fileName, () => <T>(m.call(ls, fileName))); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   function tryFilenameOneCall<T, P>(m: (fileName: string, p: P) => T): (filename: string, p: P) => | 
					
						
							|  |  |  |       T { | 
					
						
							|  |  |  |     return (fileName, p) => tryCall(fileName, () => <T>(m.call(ls, fileName, p))); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   function tryFilenameTwoCall<T, P1, P2>(m: (fileName: string, p1: P1, p2: P2) => T): ( | 
					
						
							|  |  |  |       filename: string, p1: P1, p2: P2) => T { | 
					
						
							|  |  |  |     return (fileName, p1, p2) => tryCall(fileName, () => <T>(m.call(ls, fileName, p1, p2))); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   function tryFilenameThreeCall<T, P1, P2, P3>(m: (fileName: string, p1: P1, p2: P2, p3: P3) => T): | 
					
						
							|  |  |  |       (filename: string, p1: P1, p2: P2, p3: P3) => T { | 
					
						
							|  |  |  |     return (fileName, p1, p2, p3) => tryCall(fileName, () => <T>(m.call(ls, fileName, p1, p2, p3))); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-05-16 13:29:38 -07:00
										 |  |  |   function tryFilenameFourCall<T, P1, P2, P3, P4>( | 
					
						
							|  |  |  |       m: (fileName: string, p1: P1, p2: P2, p3: P3, p4: P4) => | 
					
						
							|  |  |  |           T): (fileName: string, p1: P1, p2: P2, p3: P3, p4: P4) => T { | 
					
						
							|  |  |  |     return (fileName, p1, p2, p3, p4) => | 
					
						
							|  |  |  |                tryCall(fileName, () => <T>(m.call(ls, fileName, p1, p2, p3, p4))); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |   function typescriptOnly(ls: ts.LanguageService): ts.LanguageService { | 
					
						
							|  |  |  |     return { | 
					
						
							|  |  |  |       cleanupSemanticCache: () => ls.cleanupSemanticCache(), | 
					
						
							|  |  |  |       getSyntacticDiagnostics: tryFilenameCall(ls.getSyntacticDiagnostics), | 
					
						
							|  |  |  |       getSemanticDiagnostics: tryFilenameCall(ls.getSemanticDiagnostics), | 
					
						
							|  |  |  |       getCompilerOptionsDiagnostics: () => ls.getCompilerOptionsDiagnostics(), | 
					
						
							|  |  |  |       getSyntacticClassifications: tryFilenameOneCall(ls.getSemanticClassifications), | 
					
						
							|  |  |  |       getSemanticClassifications: tryFilenameOneCall(ls.getSemanticClassifications), | 
					
						
							|  |  |  |       getEncodedSyntacticClassifications: tryFilenameOneCall(ls.getEncodedSyntacticClassifications), | 
					
						
							|  |  |  |       getEncodedSemanticClassifications: tryFilenameOneCall(ls.getEncodedSemanticClassifications), | 
					
						
							|  |  |  |       getCompletionsAtPosition: tryFilenameOneCall(ls.getCompletionsAtPosition), | 
					
						
							|  |  |  |       getCompletionEntryDetails: tryFilenameTwoCall(ls.getCompletionEntryDetails), | 
					
						
							|  |  |  |       getCompletionEntrySymbol: tryFilenameTwoCall(ls.getCompletionEntrySymbol), | 
					
						
							|  |  |  |       getQuickInfoAtPosition: tryFilenameOneCall(ls.getQuickInfoAtPosition), | 
					
						
							|  |  |  |       getNameOrDottedNameSpan: tryFilenameTwoCall(ls.getNameOrDottedNameSpan), | 
					
						
							|  |  |  |       getBreakpointStatementAtPosition: tryFilenameOneCall(ls.getBreakpointStatementAtPosition), | 
					
						
							|  |  |  |       getSignatureHelpItems: tryFilenameOneCall(ls.getSignatureHelpItems), | 
					
						
							|  |  |  |       getRenameInfo: tryFilenameOneCall(ls.getRenameInfo), | 
					
						
							|  |  |  |       findRenameLocations: tryFilenameThreeCall(ls.findRenameLocations), | 
					
						
							|  |  |  |       getDefinitionAtPosition: tryFilenameOneCall(ls.getDefinitionAtPosition), | 
					
						
							|  |  |  |       getTypeDefinitionAtPosition: tryFilenameOneCall(ls.getTypeDefinitionAtPosition), | 
					
						
							|  |  |  |       getImplementationAtPosition: tryFilenameOneCall(ls.getImplementationAtPosition), | 
					
						
							|  |  |  |       getReferencesAtPosition: tryFilenameOneCall(ls.getReferencesAtPosition), | 
					
						
							|  |  |  |       findReferences: tryFilenameOneCall(ls.findReferences), | 
					
						
							|  |  |  |       getDocumentHighlights: tryFilenameTwoCall(ls.getDocumentHighlights), | 
					
						
							|  |  |  |       /** @deprecated */ | 
					
						
							|  |  |  |       getOccurrencesAtPosition: tryFilenameOneCall(ls.getOccurrencesAtPosition), | 
					
						
							|  |  |  |       getNavigateToItems: | 
					
						
							|  |  |  |           (searchValue, maxResultCount, fileName, excludeDtsFiles) => tryCall( | 
					
						
							|  |  |  |               fileName, | 
					
						
							|  |  |  |               () => ls.getNavigateToItems(searchValue, maxResultCount, fileName, excludeDtsFiles)), | 
					
						
							|  |  |  |       getNavigationBarItems: tryFilenameCall(ls.getNavigationBarItems), | 
					
						
							|  |  |  |       getNavigationTree: tryFilenameCall(ls.getNavigationTree), | 
					
						
							|  |  |  |       getOutliningSpans: tryFilenameCall(ls.getOutliningSpans), | 
					
						
							|  |  |  |       getTodoComments: tryFilenameOneCall(ls.getTodoComments), | 
					
						
							|  |  |  |       getBraceMatchingAtPosition: tryFilenameOneCall(ls.getBraceMatchingAtPosition), | 
					
						
							|  |  |  |       getIndentationAtPosition: tryFilenameTwoCall(ls.getIndentationAtPosition), | 
					
						
							|  |  |  |       getFormattingEditsForRange: tryFilenameThreeCall(ls.getFormattingEditsForRange), | 
					
						
							|  |  |  |       getFormattingEditsForDocument: tryFilenameOneCall(ls.getFormattingEditsForDocument), | 
					
						
							|  |  |  |       getFormattingEditsAfterKeystroke: tryFilenameThreeCall(ls.getFormattingEditsAfterKeystroke), | 
					
						
							|  |  |  |       getDocCommentTemplateAtPosition: tryFilenameOneCall(ls.getDocCommentTemplateAtPosition), | 
					
						
							|  |  |  |       isValidBraceCompletionAtPosition: tryFilenameTwoCall(ls.isValidBraceCompletionAtPosition), | 
					
						
							| 
									
										
										
										
											2017-05-16 13:29:38 -07:00
										 |  |  |       getCodeFixesAtPosition: tryFilenameFourCall(ls.getCodeFixesAtPosition), | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |       getEmitOutput: tryFilenameCall(ls.getEmitOutput), | 
					
						
							|  |  |  |       getProgram: () => ls.getProgram(), | 
					
						
							| 
									
										
										
										
											2017-09-08 18:40:32 -07:00
										 |  |  |       dispose: () => ls.dispose(), | 
					
						
							|  |  |  |       getApplicableRefactors: (fileName, positionOrRaneg) => <ts.ApplicableRefactorInfo[]>[], | 
					
						
							|  |  |  |       getEditsForRefactor: (fileName, formatOptions, positionOrRange, refactorName, actionName) => | 
					
						
							|  |  |  |                                undefined, | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |     }; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   oldLS = typescriptOnly(oldLS); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   for (const k in oldLS) { | 
					
						
							|  |  |  |     (<any>proxy)[k] = function() { return (oldLS as any)[k].apply(oldLS, arguments); }; | 
					
						
							|  |  |  |   } | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   function completionToEntry(c: Completion): ts.CompletionEntry { | 
					
						
							| 
									
										
										
										
											2017-10-26 17:23:30 -07:00
										 |  |  |     return { | 
					
						
							|  |  |  |       // TODO: remove any and fix type error.
 | 
					
						
							|  |  |  |       kind: c.kind as any, | 
					
						
							|  |  |  |       name: c.name, | 
					
						
							|  |  |  |       sortText: c.sort, | 
					
						
							|  |  |  |       kindModifiers: '' | 
					
						
							|  |  |  |     }; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   } | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   function diagnosticToDiagnostic(d: Diagnostic, file: ts.SourceFile): ts.Diagnostic { | 
					
						
							| 
									
										
										
										
											2017-04-28 15:10:30 -07:00
										 |  |  |     const result = { | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |       file, | 
					
						
							|  |  |  |       start: d.span.start, | 
					
						
							|  |  |  |       length: d.span.end - d.span.start, | 
					
						
							|  |  |  |       messageText: d.message, | 
					
						
							|  |  |  |       category: ts.DiagnosticCategory.Error, | 
					
						
							| 
									
										
										
										
											2017-04-28 15:10:30 -07:00
										 |  |  |       code: 0, | 
					
						
							|  |  |  |       source: 'ng' | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     }; | 
					
						
							| 
									
										
										
										
											2017-04-28 15:10:30 -07:00
										 |  |  |     return result; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   } | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |   function tryOperation<T>(attempting: string, callback: () => T): T|null { | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     try { | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |       return callback(); | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     } catch (e) { | 
					
						
							|  |  |  |       info.project.projectService.logger.info(`Failed to ${attempting}: ${e.toString()}`); | 
					
						
							|  |  |  |       info.project.projectService.logger.info(`Stack trace: ${e.stack}`); | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |       return null; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     } | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   const serviceHost = new TypeScriptServiceHost(info.languageServiceHost, info.languageService); | 
					
						
							| 
									
										
										
										
											2017-03-24 09:57:32 -07:00
										 |  |  |   const ls = createLanguageService(serviceHost as any); | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   serviceHost.setSite(ls); | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |   projectHostMap.set(info.project, serviceHost); | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   proxy.getCompletionsAtPosition = function(fileName: string, position: number) { | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |     let base = oldLS.getCompletionsAtPosition(fileName, position) || { | 
					
						
							|  |  |  |       isGlobalCompletion: false, | 
					
						
							|  |  |  |       isMemberCompletion: false, | 
					
						
							|  |  |  |       isNewIdentifierLocation: false, | 
					
						
							|  |  |  |       entries: [] | 
					
						
							|  |  |  |     }; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     tryOperation('get completions', () => { | 
					
						
							|  |  |  |       const results = ls.getCompletionsAt(fileName, position); | 
					
						
							|  |  |  |       if (results && results.length) { | 
					
						
							|  |  |  |         if (base === undefined) { | 
					
						
							| 
									
										
										
										
											2017-01-24 09:05:34 -08:00
										 |  |  |           base = { | 
					
						
							|  |  |  |             isGlobalCompletion: false, | 
					
						
							|  |  |  |             isMemberCompletion: false, | 
					
						
							|  |  |  |             isNewIdentifierLocation: false, | 
					
						
							|  |  |  |             entries: [] | 
					
						
							|  |  |  |           }; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |         } | 
					
						
							|  |  |  |         for (const entry of results) { | 
					
						
							|  |  |  |           base.entries.push(completionToEntry(entry)); | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  |     return base; | 
					
						
							|  |  |  |   }; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   proxy.getQuickInfoAtPosition = function(fileName: string, position: number): ts.QuickInfo { | 
					
						
							|  |  |  |     let base = oldLS.getQuickInfoAtPosition(fileName, position); | 
					
						
							| 
									
										
										
										
											2017-04-14 16:04:59 -07:00
										 |  |  |     // TODO(vicb): the tags property has been removed in TS 2.2
 | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     tryOperation('get quick info', () => { | 
					
						
							|  |  |  |       const ours = ls.getHoverAt(fileName, position); | 
					
						
							|  |  |  |       if (ours) { | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |         const displayParts: ts.SymbolDisplayPart[] = []; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |         for (const part of ours.text) { | 
					
						
							| 
									
										
										
										
											2017-04-28 15:10:30 -07:00
										 |  |  |           displayParts.push({kind: part.language || 'angular', text: part.text}); | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |         } | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |         const tags = base && (<any>base).tags; | 
					
						
							| 
									
										
										
										
											2017-04-14 16:04:59 -07:00
										 |  |  |         base = <any>{ | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |           displayParts, | 
					
						
							|  |  |  |           documentation: [], | 
					
						
							|  |  |  |           kind: 'angular', | 
					
						
							|  |  |  |           kindModifiers: 'what does this do?', | 
					
						
							| 
									
										
										
										
											2017-01-24 09:05:34 -08:00
										 |  |  |           textSpan: {start: ours.span.start, length: ours.span.end - ours.span.start}, | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |         }; | 
					
						
							| 
									
										
										
										
											2017-04-14 16:04:59 -07:00
										 |  |  |         if (tags) { | 
					
						
							|  |  |  |           (<any>base).tags = tags; | 
					
						
							|  |  |  |         } | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  |       } | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     }); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     return base; | 
					
						
							|  |  |  |   }; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   proxy.getSemanticDiagnostics = function(fileName: string) { | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |     let result = oldLS.getSemanticDiagnostics(fileName); | 
					
						
							|  |  |  |     const base = result || []; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |     tryOperation('get diagnostics', () => { | 
					
						
							|  |  |  |       info.project.projectService.logger.info(`Computing Angular semantic diagnostics...`); | 
					
						
							|  |  |  |       const ours = ls.getDiagnostics(fileName); | 
					
						
							|  |  |  |       if (ours && ours.length) { | 
					
						
							|  |  |  |         const file = oldLS.getProgram().getSourceFile(fileName); | 
					
						
							|  |  |  |         base.push.apply(base, ours.map(d => diagnosticToDiagnostic(d, file))); | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     return base; | 
					
						
							|  |  |  |   }; | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   proxy.getDefinitionAtPosition = function( | 
					
						
							|  |  |  |                                       fileName: string, position: number): ts.DefinitionInfo[] { | 
					
						
							|  |  |  |     let base = oldLS.getDefinitionAtPosition(fileName, position); | 
					
						
							|  |  |  |     if (base && base.length) { | 
					
						
							|  |  |  |       return base; | 
					
						
							| 
									
										
										
										
											2016-11-22 09:10:23 -08:00
										 |  |  |     } | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |     return tryOperation('get definition', () => { | 
					
						
							|  |  |  |              const ours = ls.getDefinitionAt(fileName, position); | 
					
						
							|  |  |  |              if (ours && ours.length) { | 
					
						
							|  |  |  |                base = base || []; | 
					
						
							|  |  |  |                for (const loc of ours) { | 
					
						
							|  |  |  |                  base.push({ | 
					
						
							|  |  |  |                    fileName: loc.fileName, | 
					
						
							|  |  |  |                    textSpan: {start: loc.span.start, length: loc.span.end - loc.span.start}, | 
					
						
							|  |  |  |                    name: '', | 
					
						
							| 
									
										
										
										
											2017-10-26 17:23:30 -07:00
										 |  |  |                    // TODO: remove any and fix type error.
 | 
					
						
							|  |  |  |                    kind: 'definition' as any, | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |                    containerName: loc.fileName, | 
					
						
							| 
									
										
										
										
											2017-10-26 17:23:30 -07:00
										 |  |  |                    containerKind: 'file' as any, | 
					
						
							| 
									
										
										
										
											2017-04-25 12:13:06 -07:00
										 |  |  |                  }); | 
					
						
							|  |  |  |                } | 
					
						
							|  |  |  |              } | 
					
						
							|  |  |  |              return base; | 
					
						
							|  |  |  |            }) || []; | 
					
						
							| 
									
										
										
										
											2017-01-06 20:43:17 -08:00
										 |  |  |   }; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   return proxy; | 
					
						
							|  |  |  | } |