mirror of
https://github.com/ckaczor/azuredatastudio.git
synced 2026-02-16 18:46:40 -05:00
Initial LiveShare extension scaffolding (#7170)
* LiveShare initial shared connection * Various cleanups * Fix type * Fix hygiene
This commit is contained in:
215
extensions/liveshare/src/providers/connectionProvider.ts
Normal file
215
extensions/liveshare/src/providers/connectionProvider.ts
Normal file
@@ -0,0 +1,215 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as azdata from 'azdata';
|
||||
import * as vscode from 'vscode';
|
||||
import * as constants from '../constants';
|
||||
|
||||
import { LiveShare, SharedService, SharedServiceProxy } from '../liveshare';
|
||||
|
||||
export class ConnectionProvider {
|
||||
private _sharedService: SharedService;
|
||||
private _sharedServiceProxy: SharedServiceProxy;
|
||||
|
||||
protected _onConnect: vscode.EventEmitter<any> = new vscode.EventEmitter<any>();
|
||||
public readonly onConnect: vscode.Event<any> = this._onConnect.event;
|
||||
|
||||
protected _onDisconnect: vscode.EventEmitter<any> = new vscode.EventEmitter<any>();
|
||||
public readonly onDisconnect: vscode.Event<any> = this._onDisconnect.event;
|
||||
|
||||
protected _onConnectionChanged: vscode.EventEmitter<any> = new vscode.EventEmitter<any>();
|
||||
public readonly onConnectionChanged: vscode.Event<any> = this._onConnectionChanged.event;
|
||||
|
||||
private _onConnectionCompleteHandler: (connSummary: azdata.ConnectionInfoSummary) => any;
|
||||
|
||||
public constructor(
|
||||
private _isHost: boolean,
|
||||
private _vslsApi: LiveShare,
|
||||
service: SharedService | SharedServiceProxy) {
|
||||
if (this._isHost) {
|
||||
this._sharedService = <SharedService>service;
|
||||
this.registerProviderListener();
|
||||
} else {
|
||||
this._sharedServiceProxy = <SharedServiceProxy>service;
|
||||
this.registerProvider();
|
||||
}
|
||||
}
|
||||
|
||||
public registerProviderListener(): void {
|
||||
let self = this;
|
||||
azdata.connection.registerConnectionEventListener({
|
||||
onConnectionEvent(type: azdata.connection.ConnectionEventType, ownerUri: string, profile: azdata.IConnectionProfile) {
|
||||
try {
|
||||
let localUri: vscode.Uri = self._vslsApi.convertLocalUriToShared(vscode.Uri.parse(ownerUri));
|
||||
ownerUri = localUri.toString();
|
||||
} catch {
|
||||
}
|
||||
|
||||
self._sharedService.notify(<string>type, {
|
||||
ownerUri: ownerUri,
|
||||
profile: profile
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.connectRequest, (args: any) => {
|
||||
return;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.disconnectRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.cancelConnectRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.changeDatabaseRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.listDatabasesRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
this._sharedService.onRequest(constants.getConnectionStringRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.buildConnectionInfoRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.rebuildIntellisenseCacheRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
}
|
||||
|
||||
public registerProvider(): vscode.Disposable {
|
||||
const self = this;
|
||||
this._sharedServiceProxy.onNotify('onConnect', (args: any) => {
|
||||
this._onConnect.fire(args);
|
||||
return args;
|
||||
});
|
||||
|
||||
this._sharedServiceProxy.onNotify('onDisconnect', (args: any) => {
|
||||
this._onDisconnect.fire(args);
|
||||
return args;
|
||||
});
|
||||
|
||||
this._sharedServiceProxy.onNotify('onConnectionChanged', (args: any) => {
|
||||
this._onConnectionChanged.fire(args);
|
||||
return args;
|
||||
});
|
||||
|
||||
let connect = (ownerUri: string, connInfo: azdata.ConnectionInfo): Thenable<boolean> => {
|
||||
if (self._onConnectionCompleteHandler) {
|
||||
// "test" liveshare connection details to be filled out in later iteration
|
||||
let connSummary: azdata.ConnectionInfoSummary = {
|
||||
ownerUri: ownerUri,
|
||||
connectionId: ownerUri,
|
||||
messages: undefined,
|
||||
errorMessage: undefined,
|
||||
errorNumber: undefined,
|
||||
connectionSummary: {
|
||||
serverName: connInfo.options['serverName'],
|
||||
databaseName: connInfo.options['databaseName'],
|
||||
userName: 'liveshare'
|
||||
},
|
||||
serverInfo: {
|
||||
serverMajorVersion: 1,
|
||||
serverMinorVersion: 0,
|
||||
serverReleaseVersion: 1,
|
||||
engineEditionId: 1,
|
||||
serverVersion: '1.0',
|
||||
serverLevel: '1',
|
||||
serverEdition: '1',
|
||||
isCloud: false,
|
||||
azureVersion: 1,
|
||||
osVersion: '1',
|
||||
options: connInfo.options
|
||||
}
|
||||
};
|
||||
self._onConnectionCompleteHandler(connSummary);
|
||||
}
|
||||
|
||||
return self._sharedServiceProxy.request(constants.connectRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
connInfo: connInfo
|
||||
}]);
|
||||
};
|
||||
|
||||
let disconnect = (ownerUri: string): Thenable<boolean> => {
|
||||
return self._sharedServiceProxy.request(constants.disconnectRequest, [{
|
||||
ownerUri: ownerUri
|
||||
}]);
|
||||
};
|
||||
|
||||
let cancelConnect = (ownerUri: string): Thenable<boolean> => {
|
||||
return self._sharedServiceProxy.request(constants.cancelConnectRequest, [{
|
||||
ownerUri: ownerUri
|
||||
}]);
|
||||
};
|
||||
|
||||
let changeDatabase = (ownerUri: string, newDatabase: string): Thenable<boolean> => {
|
||||
return self._sharedServiceProxy.request(constants.changeDatabaseRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
newDatabase: newDatabase
|
||||
}]);
|
||||
};
|
||||
|
||||
let listDatabases = (ownerUri: string): Thenable<azdata.ListDatabasesResult> => {
|
||||
return self._sharedServiceProxy.request(constants.listDatabasesRequest, [{
|
||||
ownerUri: ownerUri
|
||||
}]);
|
||||
};
|
||||
|
||||
let getConnectionString = (ownerUri: string, includePassword: boolean): Thenable<string> => {
|
||||
return self._sharedServiceProxy.request(constants.getConnectionStringRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
includePassword: includePassword
|
||||
}]);
|
||||
};
|
||||
|
||||
let buildConnectionInfo = (connectionString: string): Thenable<azdata.ConnectionInfo> => {
|
||||
return self._sharedServiceProxy.request(constants.buildConnectionInfoRequest, [{
|
||||
connectionString: connectionString
|
||||
}]);
|
||||
};
|
||||
|
||||
let rebuildIntelliSenseCache = (ownerUri: string): Thenable<void> => {
|
||||
return self._sharedServiceProxy.request(constants.rebuildIntellisenseCacheRequest, [{
|
||||
ownerUri: ownerUri
|
||||
}]);
|
||||
};
|
||||
|
||||
let registerOnConnectionComplete = (handler: (connSummary: azdata.ConnectionInfoSummary) => any): void => {
|
||||
self._onConnectionCompleteHandler = handler;
|
||||
return;
|
||||
};
|
||||
|
||||
let registerOnIntelliSenseCacheComplete = (handler: (connectionUri: string) => any): void => {
|
||||
return;
|
||||
};
|
||||
|
||||
let registerOnConnectionChanged = (handler: (changedConnInfo: azdata.ChangedConnectionInfo) => any): void => {
|
||||
return;
|
||||
};
|
||||
|
||||
return azdata.dataprotocol.registerConnectionProvider({
|
||||
providerId: constants.LiveShareProviderId,
|
||||
connect,
|
||||
disconnect,
|
||||
cancelConnect,
|
||||
changeDatabase,
|
||||
listDatabases,
|
||||
getConnectionString,
|
||||
buildConnectionInfo,
|
||||
rebuildIntelliSenseCache,
|
||||
registerOnConnectionChanged,
|
||||
registerOnIntelliSenseCacheComplete,
|
||||
registerOnConnectionComplete
|
||||
});
|
||||
}
|
||||
}
|
||||
233
extensions/liveshare/src/providers/queryProvider.ts
Normal file
233
extensions/liveshare/src/providers/queryProvider.ts
Normal file
@@ -0,0 +1,233 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as azdata from 'azdata';
|
||||
import * as vscode from 'vscode';
|
||||
|
||||
import * as constants from '../constants';
|
||||
import { SharedService, SharedServiceProxy } from '../liveshare';
|
||||
|
||||
export class QueryProvider {
|
||||
private _sharedService: SharedService;
|
||||
private _sharedServiceProxy: SharedServiceProxy;
|
||||
private _onQueryCompleteHandler: (result: azdata.QueryExecuteCompleteNotificationResult) => any;
|
||||
|
||||
public constructor(private _isHost: boolean) { }
|
||||
|
||||
public initialize(isHost: boolean, service: SharedService | SharedServiceProxy) {
|
||||
if (this._isHost) {
|
||||
this._sharedService = <SharedService>service;
|
||||
this.registerProviderListener();
|
||||
} else {
|
||||
this._sharedServiceProxy = <SharedServiceProxy>service;
|
||||
this.registerProvider();
|
||||
}
|
||||
}
|
||||
|
||||
public registerProviderListener() {
|
||||
this._sharedService.onRequest(constants.cancelQueryRequest, (args: any) => {
|
||||
return;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.runQueryRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.runQueryStatementRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.runQueryStringRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.runQueryAndReturnRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.parseSyntaxRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.getQueryRowsRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.disposeQueryRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.saveResultsRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
|
||||
this._sharedService.onRequest(constants.setQueryExecutionOptionsRequest, (args: any) => {
|
||||
return true;
|
||||
});
|
||||
}
|
||||
|
||||
public registerProvider(): vscode.Disposable {
|
||||
const self = this;
|
||||
let runQuery = (ownerUri: string, querySelection: azdata.ISelectionData, executionPlanOptions?: azdata.ExecutionPlanOptions): Thenable<void> => {
|
||||
if (self._onQueryCompleteHandler) {
|
||||
self._onQueryCompleteHandler({
|
||||
ownerUri: ownerUri,
|
||||
batchSummaries: []
|
||||
});
|
||||
}
|
||||
|
||||
return self._sharedServiceProxy.request(constants.runQueryRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
querySelection: querySelection,
|
||||
executionPlanOptions: executionPlanOptions
|
||||
}]);
|
||||
};
|
||||
|
||||
let cancelQuery = (ownerUri: string): Thenable<azdata.QueryCancelResult> => {
|
||||
return self._sharedServiceProxy.request(constants.cancelQueryRequest, [{
|
||||
ownerUri: ownerUri
|
||||
}]);
|
||||
};
|
||||
|
||||
let runQueryStatement = (ownerUri: string, line: number, column: number): Thenable<void> => {
|
||||
return self._sharedServiceProxy.request(constants.runQueryStatementRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
line: line,
|
||||
column: column
|
||||
}]);
|
||||
};
|
||||
|
||||
let runQueryString = (ownerUri: string, query: string): Thenable<void> => {
|
||||
return self._sharedServiceProxy.request(constants.runQueryStringRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
query: query
|
||||
}]);
|
||||
};
|
||||
|
||||
let runQueryAndReturn = (ownerUri: string, queryString: string): Thenable<azdata.SimpleExecuteResult> => {
|
||||
return self._sharedServiceProxy.request(constants.runQueryAndReturnRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
query: queryString
|
||||
}]);
|
||||
};
|
||||
|
||||
let parseSyntax = (ownerUri: string, query: string): Thenable<azdata.SyntaxParseResult> => {
|
||||
return self._sharedServiceProxy.request(constants.parseSyntaxRequest, [{
|
||||
ownerUri: ownerUri,
|
||||
query: query
|
||||
}]);
|
||||
};
|
||||
|
||||
let getQueryRows = (rowData: azdata.QueryExecuteSubsetParams): Thenable<azdata.QueryExecuteSubsetResult> => {
|
||||
return self._sharedServiceProxy.request(constants.getQueryRowsRequest, [{
|
||||
rowData: rowData
|
||||
}]);
|
||||
};
|
||||
|
||||
let disposeQuery = (ownerUri: string): Thenable<void> => {
|
||||
return self._sharedServiceProxy.request(constants.disposeQueryRequest, [{
|
||||
ownerUri: ownerUri
|
||||
}]);
|
||||
};
|
||||
|
||||
let registerOnQueryComplete = (handler: (result: azdata.QueryExecuteCompleteNotificationResult) => any): void => {
|
||||
self._onQueryCompleteHandler = handler;
|
||||
};
|
||||
|
||||
let registerOnBatchStart = (handler: (batchInfo: azdata.QueryExecuteBatchNotificationParams) => any): void => {
|
||||
};
|
||||
|
||||
let registerOnBatchComplete = (handler: (batchInfo: azdata.QueryExecuteBatchNotificationParams) => any): void => {
|
||||
};
|
||||
|
||||
let registerOnResultSetAvailable = (handler: (resultSetInfo: azdata.QueryExecuteResultSetNotificationParams) => any): void => {
|
||||
};
|
||||
|
||||
let registerOnResultSetUpdated = (handler: (resultSetInfo: azdata.QueryExecuteResultSetNotificationParams) => any): void => {
|
||||
};
|
||||
|
||||
let registerOnMessage = (handler: (message: azdata.QueryExecuteMessageParams) => any): void => {
|
||||
};
|
||||
|
||||
let saveResults = (requestParams: azdata.SaveResultsRequestParams): Thenable<azdata.SaveResultRequestResult> => {
|
||||
return Promise.resolve(undefined);
|
||||
};
|
||||
|
||||
let setQueryExecutionOptions = (ownerUri: string, options: azdata.QueryExecutionOptions): Thenable<void> => {
|
||||
return Promise.resolve();
|
||||
};
|
||||
|
||||
// Edit Data Requests
|
||||
let commitEdit = (ownerUri: string): Thenable<void> => {
|
||||
return Promise.resolve();
|
||||
};
|
||||
|
||||
let createRow = (ownerUri: string): Thenable<azdata.EditCreateRowResult> => {
|
||||
return Promise.resolve(undefined);
|
||||
};
|
||||
|
||||
let deleteRow = (ownerUri: string, rowId: number): Thenable<void> => {
|
||||
return Promise.resolve();
|
||||
};
|
||||
|
||||
let disposeEdit = (ownerUri: string): Thenable<void> => {
|
||||
return Promise.resolve();
|
||||
};
|
||||
|
||||
let initializeEdit = (ownerUri: string, schemaName: string, objectName: string, objectType: string, LimitResults: number, queryString: string): Thenable<void> => {
|
||||
return Promise.resolve();
|
||||
};
|
||||
|
||||
let revertCell = (ownerUri: string, rowId: number, columnId: number): Thenable<azdata.EditRevertCellResult> => {
|
||||
return Promise.resolve(undefined);
|
||||
};
|
||||
|
||||
let revertRow = (ownerUri: string, rowId: number): Thenable<void> => {
|
||||
return Promise.resolve();
|
||||
};
|
||||
|
||||
let updateCell = (ownerUri: string, rowId: number, columnId: number, newValue: string): Thenable<azdata.EditUpdateCellResult> => {
|
||||
return Promise.resolve(undefined);
|
||||
};
|
||||
|
||||
let getEditRows = (rowData: azdata.EditSubsetParams): Thenable<azdata.EditSubsetResult> => {
|
||||
return Promise.resolve(undefined);
|
||||
};
|
||||
|
||||
// Edit Data Event Handlers
|
||||
let registerOnEditSessionReady = (handler: (ownerUri: string, success: boolean, message: string) => any): void => {
|
||||
};
|
||||
|
||||
return azdata.dataprotocol.registerQueryProvider({
|
||||
providerId: constants.LiveShareProviderId,
|
||||
cancelQuery,
|
||||
commitEdit,
|
||||
createRow,
|
||||
deleteRow,
|
||||
disposeEdit,
|
||||
disposeQuery,
|
||||
getEditRows,
|
||||
getQueryRows,
|
||||
setQueryExecutionOptions,
|
||||
initializeEdit,
|
||||
registerOnBatchComplete,
|
||||
registerOnBatchStart,
|
||||
registerOnEditSessionReady,
|
||||
registerOnMessage,
|
||||
registerOnQueryComplete,
|
||||
registerOnResultSetAvailable,
|
||||
registerOnResultSetUpdated,
|
||||
revertCell,
|
||||
revertRow,
|
||||
runQuery,
|
||||
runQueryAndReturn,
|
||||
parseSyntax,
|
||||
runQueryStatement,
|
||||
runQueryString,
|
||||
saveResults,
|
||||
updateCell
|
||||
}, true);
|
||||
}
|
||||
}
|
||||
94
extensions/liveshare/src/providers/statusProvider.ts
Normal file
94
extensions/liveshare/src/providers/statusProvider.ts
Normal file
@@ -0,0 +1,94 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as azdata from 'azdata';
|
||||
import * as vscode from 'vscode';
|
||||
import { LiveShare, SharedService, SharedServiceProxy } from '../liveshare';
|
||||
import { ConnectionProvider } from './connectionProvider';
|
||||
import { LiveShareProviderId } from '../constants';
|
||||
|
||||
export class LiveShareDocumentState {
|
||||
public isConnected: boolean;
|
||||
public serverName?: string;
|
||||
public databaseName?: string;
|
||||
}
|
||||
|
||||
export class StatusProvider {
|
||||
private _sharedService: SharedService;
|
||||
private _sharedServiceProxy: SharedServiceProxy;
|
||||
|
||||
public constructor(
|
||||
private _isHost: boolean,
|
||||
private _vslsApi: LiveShare,
|
||||
connectionProvider: ConnectionProvider,
|
||||
service: SharedService | SharedServiceProxy) {
|
||||
|
||||
if (this._isHost) {
|
||||
this._sharedService = <SharedService>service;
|
||||
this.registerStatusProvider();
|
||||
} else {
|
||||
this._sharedServiceProxy = <SharedServiceProxy>service;
|
||||
|
||||
connectionProvider.onConnect(async (args: any) => {
|
||||
if (args && args.ownerUri && args.profile) {
|
||||
let queryDocument = await azdata.queryeditor.getQueryDocument(args.ownerUri);
|
||||
if (queryDocument) {
|
||||
let connectionOptions: Map<string, any> = new Map<string, any>();
|
||||
connectionOptions['providerName'] = LiveShareProviderId;
|
||||
connectionOptions['serverName'] = args.profile.options['server'];
|
||||
connectionOptions['databaseName'] = args.profile.options['database'];
|
||||
connectionOptions['userName'] = 'liveshare';
|
||||
connectionOptions['password'] = 'liveshare';
|
||||
connectionOptions['authenticationType'] = 'liveshare';
|
||||
connectionOptions['savePassword'] = false;
|
||||
connectionOptions['saveProfile'] = false;
|
||||
let profile = azdata.connection.ConnectionProfile.createFrom(connectionOptions);
|
||||
queryDocument.connect(profile);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private registerStatusProvider(): void {
|
||||
let self = this;
|
||||
|
||||
// Retrieves the current document state associated with the URI parameter.
|
||||
// The URI will be in guest Live Share format and needs to be converted back
|
||||
// to the host file path format.
|
||||
this._sharedService.onRequest('getDocumentState', async (args: any[]) => {
|
||||
if (args && args.length > 0) {
|
||||
let ownerUri = vscode.Uri.parse(args[0].ownerUri);
|
||||
let localUri: vscode.Uri = self._vslsApi.convertSharedUriToLocal(ownerUri);
|
||||
let connection = await azdata.connection.getConnection(localUri.toString());
|
||||
|
||||
let serverName: string = 'liveshare';
|
||||
let databaseName: string = 'liveshare';
|
||||
if (connection) {
|
||||
serverName = connection.serverName;
|
||||
databaseName = connection.databaseName;
|
||||
}
|
||||
|
||||
let documentState: LiveShareDocumentState = {
|
||||
isConnected: true,
|
||||
serverName: serverName,
|
||||
databaseName: databaseName
|
||||
};
|
||||
return documentState;
|
||||
}
|
||||
return undefined;
|
||||
});
|
||||
}
|
||||
|
||||
public getDocumentState(doc: vscode.TextDocument): Promise<LiveShareDocumentState> {
|
||||
if (!this._isHost) {
|
||||
return this._sharedServiceProxy.request('getDocumentState', [{
|
||||
ownerUri: doc.uri.toString()
|
||||
}]);
|
||||
} else {
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user