diff --git a/src/AzureRMTools.ts b/src/AzureRMTools.ts index cf335b2e2..b67859776 100644 --- a/src/AzureRMTools.ts +++ b/src/AzureRMTools.ts @@ -22,7 +22,7 @@ import { startArmLanguageServer, stopArmLanguageServer } from "./languageclient/ import { PositionContext } from "./PositionContext"; import * as Reference from "./Reference"; import { Stopwatch } from "./Stopwatch"; -import { armDeploymentDocumentSelector, mightBeDeploymentTemplate, shouldWatchDocument } from "./supported"; +import { armDeploymentDocumentSelector, mightBeDeploymentTemplate } from "./supported"; import * as TLE from "./TLE"; import { JsonOutlineProvider } from "./Treeview"; import { UnrecognizedFunctionIssue } from "./UnrecognizedFunctionIssue"; @@ -122,72 +122,56 @@ export class AzureRMTools { actionContext.telemetry.properties.isActivationEvent = 'true'; actionContext.telemetry.properties.fileExt = path.extname(document.fileName); - let foundDeploymentTemplate = false; - - if (shouldWatchDocument(document)) { - if (mightBeDeploymentTemplate(document)) { - // If the documentUri is not in our dictionary of deployment templates, then we - // know that this document was just opened (as opposed to changed/updated). - let stopwatch: Stopwatch; - const documentUri: string = document.uri.toString(); - if (!this._deploymentTemplates[documentUri]) { - stopwatch = new Stopwatch(); - stopwatch.start(); - } + const stopwatch = new Stopwatch(); + stopwatch.start(); + + let treatAsDeploymentTemplate = false; + let isNewlyOpened = false; // As opposed to already opened and being activated + + if (document.languageId === armDeploymentLanguageId) { + // Lang ID is set to ARM, whether auto or manual, respect the setting + treatAsDeploymentTemplate = true; + } + + let shouldParseFile = treatAsDeploymentTemplate || mightBeDeploymentTemplate(document); + if (shouldParseFile) { + // If the documentUri is not in our dictionary of deployment templates, then we + // know that this document was just opened (as opposed to changed/updated). + const documentUri: string = document.uri.toString(); + if (!this._deploymentTemplates[documentUri]) { + isNewlyOpened = true; + } + + // Do a full parse + let deploymentTemplate: DeploymentTemplate = new DeploymentTemplate(document.getText(), documentUri); + if (deploymentTemplate.hasArmSchemaUri()) { + treatAsDeploymentTemplate = true; + } + actionContext.telemetry.measurements.parseDurationInMilliseconds = stopwatch.duration.totalMilliseconds; + + if (treatAsDeploymentTemplate) { + this.ensureDeploymentTemplateEventsHookedUp(); + this._deploymentTemplates[documentUri] = deploymentTemplate; - // Might be a deployment template, need to do a full parse to make sure - let deploymentTemplate: DeploymentTemplate = new DeploymentTemplate(document.getText(), documentUri); - if (deploymentTemplate.hasArmSchemaUri()) { - foundDeploymentTemplate = true; - - this.ensureDeploymentTemplateEventsHookedUp(); - - this._deploymentTemplates[documentUri] = deploymentTemplate; - - // We only initialized the stopwatch if the deployment template was being - // opened. The stopwatch variable will not be initialized if the deployment - // template is being edited. - if (stopwatch) { - // A deployment template has been opened (as opposed to having been tabbed to) - - stopwatch.stop(); - - // Set the language ID to ARM deployment template - if (document.languageId !== armDeploymentLanguageId) { - vscode.languages.setTextDocumentLanguage(document, armDeploymentLanguageId); - - // The document will be reloaded, firing this event again with the new langid - actionContext.telemetry.properties.switchedToArm = 'true'; - actionContext.telemetry.properties.docLangId = document.languageId; - actionContext.telemetry.properties.docExtension = path.extname(document.fileName); - actionContext.telemetry.suppressIfSuccessful = false; - return; - } - - ext.reporter.sendTelemetryEvent( - "Deployment Template Opened", - { - docLangId: document.languageId, - docExtension: path.extname(document.fileName), - }, - { - documentSizeInCharacters: document.getText().length, - parseDurationInMilliseconds: stopwatch.duration.totalMilliseconds, - lineCount: deploymentTemplate.lineCount, - paramsCount: deploymentTemplate.parameterDefinitions.length, - varsCount: deploymentTemplate.variableDefinitions.length, - namespacesCount: deploymentTemplate.namespaceDefinitions.length - }); - - this.logFunctionCounts(deploymentTemplate); + if (isNewlyOpened) { + // A deployment template has been opened (as opposed to having been tabbed to) + + // Make sure the language ID is set to ARM deployment template + if (document.languageId !== armDeploymentLanguageId) { + // The document will be reloaded, firing this event again with the new langid + AzureRMTools.setLanguageToArm(document, actionContext); + return; } - this.reportDeploymentTemplateErrors(document, deploymentTemplate); + // Template for template opened + this.reportTemplateOpenedTelemetry(document, deploymentTemplate, stopwatch); } + + this.reportDeploymentTemplateErrors(document, deploymentTemplate); } } - if (!foundDeploymentTemplate) { + if (!treatAsDeploymentTemplate) { // If the document is not a deployment template, then we need // to remove it from our deployment template cache. It doesn't // matter if the document is a JSON file and was never a @@ -201,6 +185,38 @@ export class AzureRMTools { }); } + private static setLanguageToArm(document: vscode.TextDocument, actionContext: IActionContext): void { + vscode.languages.setTextDocumentLanguage(document, armDeploymentLanguageId); + + actionContext.telemetry.properties.switchedToArm = 'true'; + actionContext.telemetry.properties.docLangId = document.languageId; + actionContext.telemetry.properties.docExtension = path.extname(document.fileName); + actionContext.telemetry.suppressIfSuccessful = false; + } + + private reportTemplateOpenedTelemetry( + document: vscode.TextDocument, + deploymentTemplate: DeploymentTemplate, + stopwatch: Stopwatch + ): void { + ext.reporter.sendTelemetryEvent( + "Deployment Template Opened", + { + docLangId: document.languageId, + docExtension: path.extname(document.fileName), + }, + { + documentSizeInCharacters: document.getText().length, + parseDurationInMilliseconds: stopwatch.duration.totalMilliseconds, + lineCount: deploymentTemplate.lineCount, + paramsCount: deploymentTemplate.parameterDefinitions.length, + varsCount: deploymentTemplate.variableDefinitions.length, + namespacesCount: deploymentTemplate.namespaceDefinitions.length + }); + + this.logFunctionCounts(deploymentTemplate); + } + private reportDeploymentTemplateErrors(document: vscode.TextDocument, deploymentTemplate: DeploymentTemplate): void { // Don't wait // tslint:disable-next-line: no-floating-promises diff --git a/src/Treeview.ts b/src/Treeview.ts index e01f6e079..66d049427 100644 --- a/src/Treeview.ts +++ b/src/Treeview.ts @@ -68,7 +68,7 @@ export class JsonOutlineProvider implements vscode.TreeDataProvider { public getChildren(element?: string): string[] { // check if there is a visible text editor if (vscode.window.visibleTextEditors.length > 0) { - if (vscode.window.activeTextEditor && this.isArmTemplateDocument(vscode.window.activeTextEditor.document)) { + if (vscode.window.activeTextEditor && this.shouldShowTreeForDocument(vscode.window.activeTextEditor.document)) { if (!this.tree) { this.refresh(); @@ -148,7 +148,7 @@ export class JsonOutlineProvider implements vscode.TreeDataProvider { } private parseTree(document?: vscode.TextDocument): void { - if (this.isArmTemplateDocument(document)) { + if (this.shouldShowTreeForDocument(document)) { this.text = document.getText(); this.tree = Json.parse(this.text); } @@ -342,7 +342,7 @@ export class JsonOutlineProvider implements vscode.TreeDataProvider { const activeEditor: vscode.TextEditor = vscode.window.activeTextEditor; const document: vscode.TextDocument = !!activeEditor ? activeEditor.document : null; this.parseTree(document); - const showTreeView = this.isArmTemplateDocument(document); + const showTreeView = this.shouldShowTreeForDocument(document); if (showTreeView) { this.refresh(); @@ -351,7 +351,7 @@ export class JsonOutlineProvider implements vscode.TreeDataProvider { this.setTreeViewContext(showTreeView); } - private isArmTemplateDocument(document?: vscode.TextDocument): boolean { + private shouldShowTreeForDocument(document?: vscode.TextDocument): boolean { // Only show view if the language is set to ARM Deployment Template return !!document && document.languageId === armDeploymentLanguageId; } diff --git a/src/supported.ts b/src/supported.ts index 5bf59e73a..e9f466a5c 100644 --- a/src/supported.ts +++ b/src/supported.ts @@ -21,7 +21,7 @@ function isJsonOrJsoncLangId(textDocument: TextDocument): boolean { // We keep track of arm-deployment files, of course, // but also JSON/JSONC (unless auto-detect is disabled) so we can check them for the ARM schema -export function shouldWatchDocument(textDocument: TextDocument): boolean { +function shouldWatchDocument(textDocument: TextDocument): boolean { if (textDocument.uri.scheme !== 'file') { return false; }