diff --git a/extensions/mssql/src/api/mssqlapis.d.ts b/extensions/mssql/src/api/mssqlapis.d.ts index f5d0f0a354..a32e034bd7 100644 --- a/extensions/mssql/src/api/mssqlapis.d.ts +++ b/extensions/mssql/src/api/mssqlapis.d.ts @@ -22,6 +22,14 @@ export interface MssqlExtensionApi { * @memberof IMssqlExtensionApi */ getMssqlObjectExplorerBrowser(): MssqlObjectExplorerBrowser; + + /** + * Get the Cms Service APIs to communicate with CMS connections supported by this extension + * + * @returns {Promise} + * @memberof IMssqlExtensionApi + */ + getCmsServiceProvider(): Promise; } /** @@ -63,3 +71,95 @@ export interface ITreeNode { export interface IFileNode extends ITreeNode { getFileContentsAsString(maxBytes?: number): Promise; } + +/** + * + * Interface containing all CMS related operations + */ +export interface CmsService { + /** + * Connects to or creates a Central management Server + * + * @param {string} name + * @param {string} description + * @param {azdata.ConnectionInfo} connectiondetails + * @param {string} ownerUri + * @returns {Thenable} + */ + createCmsServer(name: string, description:string, connectiondetails: azdata.ConnectionInfo, ownerUri: string): Thenable; + + /** + * gets all Registered Servers inside a CMS on a particular level + * + * @param {string} ownerUri + * @param {string} relativePath + * @returns {Thenable} + */ + getRegisteredServers(ownerUri: string, relativePath: string): Thenable; + + /** + * Adds a Registered Server inside a CMS on a particular level + * + * @param {string} ownerUri + * @param {string} relativePath + * @param {string} registeredServerName + * @param {string} registeredServerDescription + * @param {azdata.ConnectionInfo} connectiondetails + * @returns {Thenable>} + */ + addRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string, registeredServerDescription:string, connectionDetails:azdata.ConnectionInfo): Thenable; + + /** + * Removes a Registered Server inside a CMS on a particular level + * + * @param {string} ownerUri + * @param {string} relativePath + * @param {string} registeredServerName + * @returns {Thenable} + */ + removeRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string): Thenable; + + /** + * Adds a Server Group inside a CMS on a particular level + * + * @param {string} ownerUri + * @param {string} relativePath + * @param {string} groupName + * @param {string} groupDescription + * @param {azdata.ConnectionInfo} connectiondetails + */ + addServerGroup (ownerUri: string, relativePath: string, groupName: string, groupDescription:string): Thenable; + + /** + * Removes a Server Group inside a CMS on a particular level + * + * @param {string} ownerUri + * @param {string} relativePath + * @param {string} groupName + * @param {string} groupDescription + */ + removeServerGroup (ownerUri: string, relativePath: string, groupName: string): Thenable; +} + +/** + * CMS Result interfaces as passed back to Extensions + */ +export interface RegisteredServerResult { + name: string; + serverName: string; + description: string; + connectionDetails: azdata.ConnectionInfo; + relativePath: string; +} + +export interface RegisteredServerGroup { + name: string; + description: string; + relativePath: string; +} + +export interface ListRegisteredServersResult { + registeredServersList: Array; + registeredServerGroups: Array; +} + diff --git a/extensions/mssql/src/cms/cmsService.ts b/extensions/mssql/src/cms/cmsService.ts new file mode 100644 index 0000000000..0bab9fa730 --- /dev/null +++ b/extensions/mssql/src/cms/cmsService.ts @@ -0,0 +1,102 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the Source EULA. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ + +'use strict'; + +import * as azdata from 'azdata'; +import * as constants from '../constants'; +import * as contracts from '../contracts'; +import { AppContext } from '../appContext'; +import { ConnectParams } from 'dataprotocol-client/lib/protocol'; +import { SqlOpsDataClient } from 'dataprotocol-client'; +import { ListRegisteredServersResult } from '../api/mssqlapis'; + +export class CmsService { + + constructor(private appContext: AppContext, private client: SqlOpsDataClient) { + + this.appContext.registerService(constants.CmsService, this); + } + + createCmsServer(name: string, description:string, connectiondetails: azdata.ConnectionInfo, ownerUri: string): Thenable { + let connectparams: ConnectParams = { ownerUri: ownerUri, connection: connectiondetails }; + let cmsparams: contracts.CreateCentralManagementServerParams = { registeredServerName: name, registeredServerDescription: description, connectParams: connectparams}; + + return this.client.sendRequest(contracts.CreateCentralManagementServerRequest.type, cmsparams).then( + r => { + return r; + }, + e => { + this.client.logFailedRequest(contracts.CreateCentralManagementServerRequest.type, e); + return Promise.resolve(undefined); + } + ); + } + + getRegisteredServers(ownerUri: string, relativePath: string): Thenable { + let params: contracts.ListRegisteredServersParams = { parentOwnerUri: ownerUri, relativePath: relativePath }; + return this.client.sendRequest(contracts.ListRegisteredServersRequest.type, params).then( + r => { + return r; + }, + e => { + this.client.logFailedRequest(contracts.ListRegisteredServersRequest.type, e); + return Promise.resolve(undefined); + } + ); + } + + addRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string, registeredServerDescription:string, connectionDetails:azdata.ConnectionInfo): Thenable { + let params: contracts.AddRegisteredServerParams = { parentOwnerUri: ownerUri, relativePath: relativePath, registeredServerName: registeredServerName, registeredServerDescription: registeredServerDescription, registeredServerConnectionDetails: connectionDetails }; + return this.client.sendRequest(contracts.AddRegisteredServerRequest.type, params).then( + r => { + return r; + }, + e => { + this.client.logFailedRequest(contracts.AddRegisteredServerRequest.type, e); + return Promise.resolve(undefined); + } + ); + } + + removeRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string): Thenable { + let params: contracts.RemoveRegisteredServerParams = { parentOwnerUri: ownerUri, relativePath: relativePath, registeredServerName: registeredServerName }; + return this.client.sendRequest(contracts.RemoveRegisteredServerRequest.type, params).then( + r => { + return r; + }, + e => { + this.client.logFailedRequest(contracts.RemoveRegisteredServerRequest.type, e); + return Promise.resolve(undefined); + } + ); + } + + addServerGroup (ownerUri: string, relativePath: string, groupName: string, groupDescription:string): Thenable { + let params: contracts.AddServerGroupParams = { parentOwnerUri: ownerUri, relativePath: relativePath, groupName: groupName, groupDescription: groupDescription }; + return this.client.sendRequest(contracts.AddServerGroupRequest.type, params).then( + r => { + return r; + }, + e => { + this.client.logFailedRequest(contracts.AddServerGroupRequest.type, e); + return Promise.resolve(undefined); + } + ); + } + + removeServerGroup (ownerUri: string, relativePath: string, groupName: string): Thenable { + let params: contracts.RemoveServerGroupParams = { parentOwnerUri: ownerUri, relativePath: relativePath, groupName: groupName }; + return this.client.sendRequest(contracts.RemoveServerGroupRequest.type, params).then( + r => { + return r; + }, + e => { + this.client.logFailedRequest(contracts.RemoveServerGroupRequest.type, e); + return Promise.resolve(undefined); + } + ); + } +} \ No newline at end of file diff --git a/extensions/mssql/src/config.json b/extensions/mssql/src/config.json index 3fff5b87d1..038acb3420 100644 --- a/extensions/mssql/src/config.json +++ b/extensions/mssql/src/config.json @@ -1,6 +1,6 @@ { "downloadUrl": "https://github.com/Microsoft/sqltoolsservice/releases/download/v{#version#}/microsoft.sqltools.servicelayer-{#fileName#}", - "version": "1.5.0-alpha.71", + "version": "1.5.0-alpha.74", "downloadFileNames": { "Windows_86": "win-x86-netcoreapp2.2.zip", "Windows_64": "win-x64-netcoreapp2.2.zip", diff --git a/extensions/mssql/src/constants.ts b/extensions/mssql/src/constants.ts index 1f2a9a6fe3..ddc2a6507c 100644 --- a/extensions/mssql/src/constants.ts +++ b/extensions/mssql/src/constants.ts @@ -37,6 +37,7 @@ export const isBigDataClusterProperty = 'isBigDataCluster'; // SERVICE NAMES ////////////////////////////////////////////////////////// export const ObjectExplorerService = 'objectexplorer'; +export const CmsService = 'cmsService'; export const objectExplorerPrefix: string = 'objectexplorer://'; export const ViewType = 'view'; diff --git a/extensions/mssql/src/contracts.ts b/extensions/mssql/src/contracts.ts index 0cd7862814..53146fbed3 100644 --- a/extensions/mssql/src/contracts.ts +++ b/extensions/mssql/src/contracts.ts @@ -7,6 +7,8 @@ import { NotificationType, RequestType } from 'vscode-languageclient'; import { ITelemetryEventProperties, ITelemetryEventMeasures } from './telemetry'; import * as azdata from 'azdata'; +import { ConnectParams } from 'dataprotocol-client/lib/protocol'; +import { ListRegisteredServersResult } from './api/mssqlapis'; // ------------------------------- < Telemetry Sent Event > ------------------------------------ @@ -369,4 +371,66 @@ export namespace GenerateDeployScriptRequest { export namespace GenerateDeployPlanRequest { export const type = new RequestType('dacfx/generateDeployPlan'); } -// ------------------------------- < DacFx > ------------------------------------ \ No newline at end of file +// ------------------------------- < DacFx > ------------------------------------ + +// ------------------------------- ---------------------------------------- + + +export interface CreateCentralManagementServerParams { + registeredServerName: string; + registeredServerDescription : string; + connectParams: ConnectParams; +} + +export interface ListRegisteredServersParams extends RegisteredServerParamsBase { + // same as base +} + +export interface AddRegisteredServerParams extends RegisteredServerParamsBase { + registeredServerName: string; + registeredServerDescription : string; + registeredServerConnectionDetails: azdata.ConnectionInfo; +} + +export interface RemoveRegisteredServerParams extends RegisteredServerParamsBase { + registeredServerName: string; +} + +export interface AddServerGroupParams extends RegisteredServerParamsBase { + groupName: string; + groupDescription: string; +} + +export interface RemoveServerGroupParams extends RegisteredServerParamsBase { + groupName: string; +} + +export interface RegisteredServerParamsBase { + parentOwnerUri: string; + relativePath: string; +} + +export namespace CreateCentralManagementServerRequest { + export const type = new RequestType('cms/createCms'); +} + +export namespace ListRegisteredServersRequest { + export const type = new RequestType('cms/listRegisteredServers'); +} + +export namespace AddRegisteredServerRequest { + export const type = new RequestType('cms/addRegisteredServer'); +} + +export namespace RemoveRegisteredServerRequest { + export const type = new RequestType('cms/removeRegisteredServer'); +} + +export namespace AddServerGroupRequest { + export const type = new RequestType('cms/addCmsServerGroup'); +} + +export namespace RemoveServerGroupRequest { + export const type = new RequestType('cms/removeCmsServerGroup'); +} +// ------------------------------- ---------------------------------------- \ No newline at end of file diff --git a/extensions/mssql/src/features.ts b/extensions/mssql/src/features.ts index 71d017cf84..210a8820ba 100644 --- a/extensions/mssql/src/features.ts +++ b/extensions/mssql/src/features.ts @@ -12,6 +12,7 @@ import * as contracts from './contracts'; import * as azdata from 'azdata'; import * as Utils from './utils'; import * as UUID from 'vscode-languageclient/lib/utils/uuid'; +import { ConnectParams } from 'dataprotocol-client/lib/protocol'; export class TelemetryFeature implements StaticFeature { @@ -672,4 +673,4 @@ export class AgentServicesFeature extends SqlOpsFeature { registerOnUpdated }); } -} +} \ No newline at end of file diff --git a/extensions/mssql/src/main.ts b/extensions/mssql/src/main.ts index 67538d2bda..15d1478147 100644 --- a/extensions/mssql/src/main.ts +++ b/extensions/mssql/src/main.ts @@ -13,7 +13,7 @@ const localize = nls.loadMessageBundle(); import { SqlOpsDataClient, ClientOptions } from 'dataprotocol-client'; import { IConfig, ServerProvider, Events } from 'service-downloader'; -import { ServerOptions, TransportKind } from 'vscode-languageclient'; +import { ServerOptions, TransportKind, LanguageClient } from 'vscode-languageclient'; import * as Constants from './constants'; import ContextProvider from './contextProvider'; @@ -31,6 +31,7 @@ import { MssqlExtensionApi, MssqlObjectExplorerBrowser } from './api/mssqlapis'; import { OpenSparkJobSubmissionDialogCommand, OpenSparkJobSubmissionDialogFromFileCommand, OpenSparkJobSubmissionDialogTask } from './sparkFeature/dialog/dialogCommands'; import { OpenSparkYarnHistoryTask } from './sparkFeature/historyTask'; import { MssqlObjectExplorerNodeProvider, mssqlOutputChannel } from './objectExplorerNodeProvider/objectExplorerNodeProvider'; +import { CmsService } from './cms/cmsService'; const baseConfig = require('./config.json'); const outputChannel = vscode.window.createOutputChannel(Constants.serviceName); @@ -57,6 +58,7 @@ export async function activate(context: vscode.ExtensionContext): Promise { + let serverPromise = serverdownloader.getOrDownloadServer().then(e => { const installationComplete = Date.now(); let serverOptions = generateServerOptions(e); languageClient = new SqlOpsDataClient(Constants.serviceName, serverOptions, clientOptions); @@ -109,6 +111,9 @@ export async function activate(context: vscode.ExtensionContext): Promise { @@ -136,6 +141,9 @@ export async function activate(context: vscode.ExtensionContext): PromiseoeProvider.findSqlClusterNodeByContext(context); } }; + }, + getCmsServiceProvider(): Promise { + return serverPromise.then(() => cmsService); } }; return api; diff --git a/src/sql/sqlops.proposed.d.ts b/src/sql/sqlops.proposed.d.ts index f2a7c61f37..0c30730017 100644 --- a/src/sql/sqlops.proposed.d.ts +++ b/src/sql/sqlops.proposed.d.ts @@ -1601,7 +1601,7 @@ declare module 'sqlops' { AgentServicesProvider = 'AgentServicesProvider', CapabilitiesProvider = 'CapabilitiesProvider', DacFxServicesProvider = 'DacFxServicesProvider', - ObjectExplorerNodeProvider = 'ObjectExplorerNodeProvider', + ObjectExplorerNodeProvider = 'ObjectExplorerNodeProvider' } export namespace dataprotocol { diff --git a/src/sql/workbench/api/common/sqlExtHostTypes.ts b/src/sql/workbench/api/common/sqlExtHostTypes.ts index cdd85e230e..00b9ebe63d 100644 --- a/src/sql/workbench/api/common/sqlExtHostTypes.ts +++ b/src/sql/workbench/api/common/sqlExtHostTypes.ts @@ -290,7 +290,7 @@ export enum DataProviderType { AgentServicesProvider = 'AgentServicesProvider', CapabilitiesProvider = 'CapabilitiesProvider', DacFxServicesProvider = 'DacFxServicesProvider', - ObjectExplorerNodeProvider = 'ObjectExplorerNodeProvider', + ObjectExplorerNodeProvider = 'ObjectExplorerNodeProvider' } export enum DeclarativeDataType {