From 5afa287e47388ce7a3c8309d6b5058cdd602e6d3 Mon Sep 17 00:00:00 2001 From: Karl Burtram Date: Wed, 17 Jan 2018 14:24:05 -0800 Subject: [PATCH] Fix broken XEvent Profiler (#504) * Fix broken profilergrid and choose columns dialog * Additional profiler changes * Additonal profiler bugs fixes --- .../parts/profiler/contrib/profilerActions.ts | 21 +++++ .../parts/profiler/editor/profilerEditor.ts | 6 +- .../parts/profiler/editor/profilerInput.ts | 80 ++++++++++++++----- .../viewlet/serverTreeActionProvider.ts | 2 +- .../api/node/mainThreadDataProtocol.ts | 5 -- 5 files changed, 82 insertions(+), 32 deletions(-) diff --git a/src/sql/parts/profiler/contrib/profilerActions.ts b/src/sql/parts/profiler/contrib/profilerActions.ts index ed6c3f1475..7f3a66fcb5 100644 --- a/src/sql/parts/profiler/contrib/profilerActions.ts +++ b/src/sql/parts/profiler/contrib/profilerActions.ts @@ -17,6 +17,9 @@ import * as nls from 'vs/nls'; import { IEditorAction } from 'vs/editor/common/editorCommon'; import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/editorService'; import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation'; +import { ObjectExplorerActionsContext } from 'sql/parts/registeredServer/viewlet/objectExplorerActions'; +import { ConnectionProfile } from 'sql/parts/connection/common/connectionProfile'; +import { IConnectionManagementService, IConnectionCompletionOptions, ConnectionType } from 'sql/parts/connection/common/connectionManagement'; export class ProfilerConnect extends Action { public static ID = 'profiler.connect'; @@ -228,17 +231,35 @@ export class NewProfilerAction extends TaskAction { public static LABEL = nls.localize('newProfiler', 'New Profiler'); public static ICON = 'profile'; + private _connectionProfile: ConnectionProfile; + constructor( id: string, label: string, icon: string, @IWorkbenchEditorService private _editorService: IWorkbenchEditorService, + @IConnectionManagementService private _connectionService: IConnectionManagementService, @IInstantiationService private _instantiationService: IInstantiationService ) { super(id, label, icon); } run(actionContext: BaseActionContext): TPromise { + if (actionContext instanceof ObjectExplorerActionsContext) { + this._connectionProfile = actionContext.connectionProfile; + } + let profilerInput = this._instantiationService.createInstance(ProfilerInput, actionContext.profile); return this._editorService.openEditor(profilerInput, { pinned: true }, false).then(() => { + let options: IConnectionCompletionOptions = { + params: undefined, + saveTheConnection: false, + showConnectionDialogOnError: true, + showDashboard: false, + showFirewallRuleOnError: true + }; + this._connectionService.connect(this._connectionProfile, profilerInput.id, options).then(() => { + TPromise.as(true); + }); + return TPromise.as(true); }); } diff --git a/src/sql/parts/profiler/editor/profilerEditor.ts b/src/sql/parts/profiler/editor/profilerEditor.ts index 0196f3cf09..bdcffa2da5 100644 --- a/src/sql/parts/profiler/editor/profilerEditor.ts +++ b/src/sql/parts/profiler/editor/profilerEditor.ts @@ -44,8 +44,6 @@ import { CommonFindController, FindStartFocusAction } from 'vs/editor/contrib/fi import * as types from 'vs/base/common/types'; import { attachSelectBoxStyler } from 'vs/platform/theme/common/styler'; -import { ProfilerTestBackend } from 'sql/parts/profiler/service/profilerTestBackend'; - class BasicView extends View { private _previousSize: number; private _collapsed: boolean; @@ -157,7 +155,7 @@ export class ProfilerEditor extends BaseEditor { let tableContainer = this._createProfilerTable(); let paneContainer = this._createProfilerPane(); this._splitView.addView(new BasicView( - undefined, + 300, tableContainer, () => this._profilerTableEditor.focus(), size => this._profilerTableEditor.layout(new Dimension(parseFloat(DOM.getComputedStyle(this._body).width), size)), @@ -165,7 +163,7 @@ export class ProfilerEditor extends BaseEditor { )); this._panelView = new BasicView( - undefined, + 300, paneContainer, () => this._tabbedPanel.focus(), size => this._tabbedPanel.layout(new Dimension(DOM.getTotalWidth(this._body), size)), diff --git a/src/sql/parts/profiler/editor/profilerInput.ts b/src/sql/parts/profiler/editor/profilerInput.ts index c4f66260fa..8cb43d331b 100644 --- a/src/sql/parts/profiler/editor/profilerInput.ts +++ b/src/sql/parts/profiler/editor/profilerInput.ts @@ -62,19 +62,17 @@ export class ProfilerInput extends EditorInput implements IProfilerSession { } public set sessionTemplate(template: IProfilerSessionTemplate) { - if (!this.state.isConnected || this.state.isStopped) { - this._sessionTemplate = template; - let newColumns = this.sessionTemplate.view.events.reduce>((p, e) => { - e.columns.forEach(c => { - if (!p.includes(c)) { - p.push(c); - } - }); - return p; - }, []); - newColumns.unshift('EventClass'); - this.setColumns(newColumns); - } + this._sessionTemplate = template; + let newColumns = this.sessionTemplate.view.events.reduce>((p, e) => { + e.columns.forEach(c => { + if (!p.includes(c)) { + p.push(c); + } + }); + return p; + }, []); + newColumns.unshift('EventClass'); + this.setColumns(newColumns); } public get sessionTemplate(): IProfilerSessionTemplate { @@ -125,16 +123,54 @@ export class ProfilerInput extends EditorInput implements IProfilerSession { return this._state; } - public onMoreRows(events: data.ProfilerSessionEvents) { + public onMoreRows(eventMessage: data.ProfilerSessionEvents) { + for (let i: number = 0; i < eventMessage.events.length && i < 500; ++i) { + let e: data.ProfilerEvent = eventMessage.events[i]; + let data = {}; + data['EventClass'] = e.name; + data['StartTime'] = e.timestamp; + data['EndTime'] = e.timestamp; + const columns = [ + 'TextData', + 'ApplicationName', + 'NTUserName', + 'LoginName', + 'CPU', + 'Reads', + 'Writes', + 'Duration', + 'ClientProcessID', + 'SPID', + 'StartTime', + 'EndTime', + 'BinaryData' + ]; - events = undefined; + let columnNameMap: Map = new Map(); + columnNameMap['client_app_name'] = 'ApplicationName'; + columnNameMap['nt_username'] = 'NTUserName'; + columnNameMap['options_text'] = 'TextData'; + columnNameMap['server_principal_name'] = 'LoginName'; + columnNameMap['session_id'] = 'SPID'; + columnNameMap['batch_text'] = 'TextData'; + columnNameMap['cpu_time'] = 'CPU'; + columnNameMap['duration'] = 'Duration'; + columnNameMap['logical_reads'] = 'Reads'; + + for (let idx = 0; idx < columns.length; ++idx) { + let columnName = columns[idx]; + data[columnName] = ''; + } + + for (let key in e.values) { + let columnName = columnNameMap[key]; + if (columnName) { + let value = e.values[key]; + data[columnName] = value; + } + } + this._data.push(data); + } - // let validColumns = this.sessionTemplate.view.events.find(i => i.name === data.EventClass).columns; - // Object.keys(rowCount).forEach(k => { - // if (!validColumns.includes(k)) { - // delete rowCount[k]; - // } - // }); - // this._data.push(data); } } diff --git a/src/sql/parts/registeredServer/viewlet/serverTreeActionProvider.ts b/src/sql/parts/registeredServer/viewlet/serverTreeActionProvider.ts index f263f381c6..0061a6af12 100644 --- a/src/sql/parts/registeredServer/viewlet/serverTreeActionProvider.ts +++ b/src/sql/parts/registeredServer/viewlet/serverTreeActionProvider.ts @@ -25,7 +25,7 @@ import { ConnectionProfileGroup } from 'sql/parts/connection/common/connectionPr import { ConnectionProfile } from 'sql/parts/connection/common/connectionProfile'; import { NewProfilerAction } from 'sql/parts/profiler/contrib/profilerActions'; import { TreeUpdateUtils } from 'sql/parts/registeredServer/viewlet/treeUpdateUtils'; -import { IConnectionManagementService, IErrorMessageService } from 'sql/parts/connection/common/connectionManagement'; +import { IConnectionManagementService } from 'sql/parts/connection/common/connectionManagement'; /** * Provides actions for the server tree elements diff --git a/src/sql/workbench/api/node/mainThreadDataProtocol.ts b/src/sql/workbench/api/node/mainThreadDataProtocol.ts index eb83323d7f..b4d978402c 100644 --- a/src/sql/workbench/api/node/mainThreadDataProtocol.ts +++ b/src/sql/workbench/api/node/mainThreadDataProtocol.ts @@ -349,10 +349,7 @@ export class MainThreadDataProtocol extends MainThreadDataProtocolShape { // Profiler handlers public $onSessionEventsAvailable(handle: number, response: data.ProfilerSessionEvents): void { - this._profilerService.onMoreRows(response); - //this._profilerService.onMoreRows - //this._taskService.onNewTaskCreated(handle, taskInfo); } public $unregisterProvider(handle: number): TPromise { @@ -364,6 +361,4 @@ export class MainThreadDataProtocol extends MainThreadDataProtocolShape { return undefined; } - - }