mirror of
https://github.com/ckaczor/azuredatastudio.git
synced 2026-02-17 02:51:36 -05:00
Remove dacfx and schema compare from the azdata api (#6684)
* refactor mssql extension to directly expose dacfx and schema compare * remove more code * fix compile errors
This commit is contained in:
111
extensions/mssql/src/api/mssqlapis.d.ts
vendored
111
extensions/mssql/src/api/mssqlapis.d.ts
vendored
@@ -1,111 +0,0 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
// This is the place for extensions to expose APIs.
|
||||
|
||||
import * as azdata from 'azdata';
|
||||
import * as vscode from 'vscode';
|
||||
|
||||
/**
|
||||
* The APIs provided by Mssql extension
|
||||
*/
|
||||
export interface MssqlExtensionApi {
|
||||
/**
|
||||
* Gets the object explorer API that supports querying over the connections supported by this extension
|
||||
*
|
||||
*/
|
||||
getMssqlObjectExplorerBrowser(): MssqlObjectExplorerBrowser;
|
||||
|
||||
/**
|
||||
* Get the Cms Service APIs to communicate with CMS connections supported by this extension
|
||||
*
|
||||
*/
|
||||
getCmsServiceProvider(): Promise<CmsService>;
|
||||
}
|
||||
|
||||
/**
|
||||
* A browser supporting actions over the object explorer connections provided by this extension.
|
||||
* Currently this is the
|
||||
*/
|
||||
export interface MssqlObjectExplorerBrowser {
|
||||
/**
|
||||
* Gets the matching node given a context object, e.g. one from a right-click on a node in Object Explorer
|
||||
*/
|
||||
getNode<T extends ITreeNode>(objectExplorerContext: azdata.ObjectExplorerContext): Promise<T>;
|
||||
}
|
||||
|
||||
/**
|
||||
* A tree node in the object explorer tree
|
||||
*/
|
||||
export interface ITreeNode {
|
||||
getNodeInfo(): azdata.NodeInfo;
|
||||
getChildren(refreshChildren: boolean): ITreeNode[] | Promise<ITreeNode[]>;
|
||||
}
|
||||
|
||||
/**
|
||||
* A HDFS file node. This is a leaf node in the object explorer tree, and its contents
|
||||
* can be queried
|
||||
*/
|
||||
export interface IFileNode extends ITreeNode {
|
||||
getFileContentsAsString(maxBytes?: number): Promise<string>;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Interface containing all CMS related operations
|
||||
*/
|
||||
export interface CmsService {
|
||||
/**
|
||||
* Connects to or creates a Central management Server
|
||||
*/
|
||||
createCmsServer(name: string, description:string, connectiondetails: azdata.ConnectionInfo, ownerUri: string): Thenable<ListRegisteredServersResult>;
|
||||
|
||||
/**
|
||||
* gets all Registered Servers inside a CMS on a particular level
|
||||
*/
|
||||
getRegisteredServers(ownerUri: string, relativePath: string): Thenable<ListRegisteredServersResult>;
|
||||
|
||||
/**
|
||||
* Adds a Registered Server inside a CMS on a particular level
|
||||
*/
|
||||
addRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string, registeredServerDescription:string, connectionDetails:azdata.ConnectionInfo): Thenable<boolean>;
|
||||
|
||||
/**
|
||||
* Removes a Registered Server inside a CMS on a particular level
|
||||
*/
|
||||
removeRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string): Thenable<boolean>;
|
||||
|
||||
/**
|
||||
* Adds a Server Group inside a CMS on a particular level
|
||||
*/
|
||||
addServerGroup (ownerUri: string, relativePath: string, groupName: string, groupDescription:string): Thenable<boolean>;
|
||||
|
||||
/**
|
||||
* Removes a Server Group inside a CMS on a particular level
|
||||
*/
|
||||
removeServerGroup (ownerUri: string, relativePath: string, groupName: string): Thenable<boolean>;
|
||||
}
|
||||
|
||||
/**
|
||||
* 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<RegisteredServerResult>;
|
||||
registeredServerGroups: Array<RegisteredServerGroup>;
|
||||
}
|
||||
@@ -14,15 +14,24 @@ import { ApiWrapper } from './apiWrapper';
|
||||
export class AppContext {
|
||||
|
||||
private serviceMap: Map<string, any> = new Map();
|
||||
|
||||
constructor(public readonly extensionContext: vscode.ExtensionContext, public readonly apiWrapper: ApiWrapper) {
|
||||
this.apiWrapper = apiWrapper || new ApiWrapper();
|
||||
}
|
||||
|
||||
public getService<T>(serviceName: string): T {
|
||||
return this.serviceMap.get(serviceName) as T;
|
||||
const service = this.serviceMap.get(serviceName) as T;
|
||||
if (!service) {
|
||||
console.warn('Service ', serviceName, ' is not registered');
|
||||
}
|
||||
return service;
|
||||
}
|
||||
|
||||
public registerService<T>(serviceName: string, service: T): void {
|
||||
this.serviceMap.set(serviceName, service);
|
||||
if (this.serviceMap.has(serviceName)) {
|
||||
console.warn('Multiple services ', serviceName, ' registered!');
|
||||
} else {
|
||||
this.serviceMap.set(serviceName, service);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,14 +9,29 @@ 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';
|
||||
import { ConnectParams, ClientCapabilities } from 'dataprotocol-client/lib/protocol';
|
||||
import { SqlOpsDataClient, ISqlOpsFeature } from 'dataprotocol-client';
|
||||
import { ListRegisteredServersResult, ICmsService } from '../mssql';
|
||||
import * as Utils from '../utils';
|
||||
|
||||
export class CmsService {
|
||||
export class CmsService implements ICmsService {
|
||||
public static asFeature(context: AppContext): ISqlOpsFeature {
|
||||
return class extends CmsService {
|
||||
constructor(client: SqlOpsDataClient) {
|
||||
super(context, client);
|
||||
}
|
||||
|
||||
constructor(private appContext: AppContext, private client: SqlOpsDataClient) {
|
||||
this.appContext.registerService<CmsService>(constants.CmsService, this);
|
||||
fillClientCapabilities(capabilities: ClientCapabilities): void {
|
||||
Utils.ensure(capabilities, 'cms')!.cms = true;
|
||||
}
|
||||
|
||||
initialize(): void {
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private constructor(context: AppContext, protected readonly client: SqlOpsDataClient) {
|
||||
context.registerService(constants.CmsService, this);
|
||||
}
|
||||
|
||||
createCmsServer(name: string, description: string, connectiondetails: azdata.ConnectionInfo, ownerUri: string): Thenable<ListRegisteredServersResult> {
|
||||
@@ -98,4 +113,8 @@ export class CmsService {
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
dispose() {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -38,6 +38,8 @@ export const isBigDataClusterProperty = 'isBigDataCluster';
|
||||
// SERVICE NAMES //////////////////////////////////////////////////////////
|
||||
export const ObjectExplorerService = 'objectexplorer';
|
||||
export const CmsService = 'cmsService';
|
||||
export const DacFxService = 'dacfxService';
|
||||
export const SchemaCompareService = 'schemaCompareService';
|
||||
export const objectExplorerPrefix: string = 'objectexplorer://';
|
||||
export const ViewType = 'view';
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@ 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';
|
||||
import * as mssql from './mssql';
|
||||
|
||||
// ------------------------------- < Telemetry Sent Event > ------------------------------------
|
||||
|
||||
@@ -347,27 +347,27 @@ export interface GenerateDeployPlanParams {
|
||||
}
|
||||
|
||||
export namespace ExportRequest {
|
||||
export const type = new RequestType<ExportParams, azdata.DacFxResult, void, void>('dacfx/export');
|
||||
export const type = new RequestType<ExportParams, mssql.DacFxResult, void, void>('dacfx/export');
|
||||
}
|
||||
|
||||
export namespace ImportRequest {
|
||||
export const type = new RequestType<ImportParams, azdata.DacFxResult, void, void>('dacfx/import');
|
||||
export const type = new RequestType<ImportParams, mssql.DacFxResult, void, void>('dacfx/import');
|
||||
}
|
||||
|
||||
export namespace ExtractRequest {
|
||||
export const type = new RequestType<ExtractParams, azdata.DacFxResult, void, void>('dacfx/extract');
|
||||
export const type = new RequestType<ExtractParams, mssql.DacFxResult, void, void>('dacfx/extract');
|
||||
}
|
||||
|
||||
export namespace DeployRequest {
|
||||
export const type = new RequestType<DeployParams, azdata.DacFxResult, void, void>('dacfx/deploy');
|
||||
export const type = new RequestType<DeployParams, mssql.DacFxResult, void, void>('dacfx/deploy');
|
||||
}
|
||||
|
||||
export namespace GenerateDeployScriptRequest {
|
||||
export const type = new RequestType<GenerateDeployScriptParams, azdata.DacFxResult, void, void>('dacfx/generateDeploymentScript');
|
||||
export const type = new RequestType<GenerateDeployScriptParams, mssql.DacFxResult, void, void>('dacfx/generateDeploymentScript');
|
||||
}
|
||||
|
||||
export namespace GenerateDeployPlanRequest {
|
||||
export const type = new RequestType<GenerateDeployPlanParams, azdata.GenerateDeployPlanResult, void, void>('dacfx/generateDeployPlan');
|
||||
export const type = new RequestType<GenerateDeployPlanParams, mssql.GenerateDeployPlanResult, void, void>('dacfx/generateDeployPlan');
|
||||
}
|
||||
// ------------------------------- < DacFx > ------------------------------------
|
||||
|
||||
@@ -409,11 +409,11 @@ export interface RegisteredServerParamsBase {
|
||||
}
|
||||
|
||||
export namespace CreateCentralManagementServerRequest {
|
||||
export const type = new RequestType<CreateCentralManagementServerParams, ListRegisteredServersResult, void, void>('cms/createCms');
|
||||
export const type = new RequestType<CreateCentralManagementServerParams, mssql.ListRegisteredServersResult, void, void>('cms/createCms');
|
||||
}
|
||||
|
||||
export namespace ListRegisteredServersRequest {
|
||||
export const type = new RequestType<ListRegisteredServersParams, ListRegisteredServersResult, void, void>('cms/listRegisteredServers');
|
||||
export const type = new RequestType<ListRegisteredServersParams, mssql.ListRegisteredServersResult, void, void>('cms/listRegisteredServers');
|
||||
}
|
||||
|
||||
export namespace AddRegisteredServerRequest {
|
||||
@@ -436,10 +436,10 @@ export namespace RemoveServerGroupRequest {
|
||||
// ------------------------------- <Schema Compare> -----------------------------
|
||||
export interface SchemaCompareParams {
|
||||
operationId: string;
|
||||
sourceEndpointInfo: azdata.SchemaCompareEndpointInfo;
|
||||
targetEndpointInfo: azdata.SchemaCompareEndpointInfo;
|
||||
sourceEndpointInfo: mssql.SchemaCompareEndpointInfo;
|
||||
targetEndpointInfo: mssql.SchemaCompareEndpointInfo;
|
||||
taskExecutionMode: TaskExecutionMode;
|
||||
deploymentOptions: azdata.DeploymentOptions;
|
||||
deploymentOptions: mssql.DeploymentOptions;
|
||||
}
|
||||
|
||||
export interface SchemaCompareGenerateScriptParams {
|
||||
@@ -462,7 +462,7 @@ export interface SchemaCompareGetOptionsParams {
|
||||
|
||||
export interface SchemaCompareNodeParams {
|
||||
operationId: string;
|
||||
diffEntry: azdata.DiffEntry;
|
||||
diffEntry: mssql.DiffEntry;
|
||||
includeRequest: boolean;
|
||||
taskExecutionMode: TaskExecutionMode;
|
||||
}
|
||||
@@ -472,13 +472,13 @@ export interface SchemaCompareOpenScmpParams {
|
||||
}
|
||||
|
||||
export interface SchemaCompareSaveScmpParams {
|
||||
sourceEndpointInfo: azdata.SchemaCompareEndpointInfo;
|
||||
targetEndpointInfo: azdata.SchemaCompareEndpointInfo;
|
||||
sourceEndpointInfo: mssql.SchemaCompareEndpointInfo;
|
||||
targetEndpointInfo: mssql.SchemaCompareEndpointInfo;
|
||||
taskExecutionMode: TaskExecutionMode;
|
||||
deploymentOptions: azdata.DeploymentOptions;
|
||||
deploymentOptions: mssql.DeploymentOptions;
|
||||
scmpFilePath: string;
|
||||
excludedSourceObjects: azdata.SchemaCompareObjectId[];
|
||||
excludedTargetObjects: azdata.SchemaCompareObjectId[];
|
||||
excludedSourceObjects: mssql.SchemaCompareObjectId[];
|
||||
excludedTargetObjects: mssql.SchemaCompareObjectId[];
|
||||
}
|
||||
|
||||
export interface SchemaCompareCancelParams {
|
||||
@@ -486,7 +486,7 @@ export interface SchemaCompareCancelParams {
|
||||
}
|
||||
|
||||
export namespace SchemaCompareRequest {
|
||||
export const type = new RequestType<SchemaCompareParams, azdata.SchemaCompareResult, void, void>('schemaCompare/compare');
|
||||
export const type = new RequestType<SchemaCompareParams, mssql.SchemaCompareResult, void, void>('schemaCompare/compare');
|
||||
}
|
||||
|
||||
export namespace SchemaCompareGenerateScriptRequest {
|
||||
@@ -498,7 +498,7 @@ export namespace SchemaComparePublishChangesRequest {
|
||||
}
|
||||
|
||||
export namespace SchemaCompareGetDefaultOptionsRequest {
|
||||
export const type = new RequestType<SchemaCompareGetOptionsParams, azdata.SchemaCompareOptionsResult, void, void>('schemaCompare/getDefaultOptions');
|
||||
export const type = new RequestType<SchemaCompareGetOptionsParams, mssql.SchemaCompareOptionsResult, void, void>('schemaCompare/getDefaultOptions');
|
||||
}
|
||||
|
||||
export namespace SchemaCompareIncludeExcludeNodeRequest {
|
||||
|
||||
@@ -83,7 +83,7 @@ export class CredentialStore {
|
||||
providerId: Constants.providerId,
|
||||
features: [CredentialsFeature]
|
||||
};
|
||||
serverdownloader.getOrDownloadServer().then(e => {
|
||||
return serverdownloader.getOrDownloadServer().then(e => {
|
||||
let serverOptions = this.generateServerOptions(e);
|
||||
this._client = new SqlOpsDataClient(Constants.serviceName, serverOptions, clientOptions);
|
||||
this._client.start();
|
||||
|
||||
100
extensions/mssql/src/dacfx/dacFxService.ts
Normal file
100
extensions/mssql/src/dacfx/dacFxService.ts
Normal file
@@ -0,0 +1,100 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as mssql from '../mssql';
|
||||
import { AppContext } from '../appContext';
|
||||
import { ISqlOpsFeature, SqlOpsDataClient } from 'dataprotocol-client';
|
||||
import { ClientCapabilities } from 'vscode-languageclient';
|
||||
import * as constants from '../constants';
|
||||
import * as Utils from '../utils';
|
||||
import * as azdata from 'azdata';
|
||||
import * as contracts from '../contracts';
|
||||
|
||||
export class DacFxService implements mssql.IDacFxService {
|
||||
public static asFeature(context: AppContext): ISqlOpsFeature {
|
||||
return class extends DacFxService {
|
||||
constructor(client: SqlOpsDataClient) {
|
||||
super(context, client);
|
||||
}
|
||||
|
||||
fillClientCapabilities(capabilities: ClientCapabilities): void {
|
||||
Utils.ensure(capabilities, 'dacfx')!.dacfx = true;
|
||||
}
|
||||
|
||||
initialize(): void {
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private constructor(context: AppContext, protected readonly client: SqlOpsDataClient) {
|
||||
context.registerService(constants.DacFxService, this);
|
||||
}
|
||||
|
||||
public exportBacpac(databaseName: string, packageFilePath: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<mssql.DacFxResult> {
|
||||
const params: contracts.ExportParams = { databaseName: databaseName, packageFilePath: packageFilePath, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.ExportRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.ExportRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public importBacpac(packageFilePath: string, databaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<mssql.DacFxResult> {
|
||||
const params: contracts.ImportParams = { packageFilePath: packageFilePath, databaseName: databaseName, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.ImportRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.ImportRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public extractDacpac(databaseName: string, packageFilePath: string, applicationName: string, applicationVersion: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<mssql.DacFxResult> {
|
||||
const params: contracts.ExtractParams = { databaseName: databaseName, packageFilePath: packageFilePath, applicationName: applicationName, applicationVersion: applicationVersion, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.ExtractRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.ExtractRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public deployDacpac(packageFilePath: string, targetDatabaseName: string, upgradeExisting: boolean, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<mssql.DacFxResult> {
|
||||
const params: contracts.DeployParams = { packageFilePath: packageFilePath, databaseName: targetDatabaseName, upgradeExisting: upgradeExisting, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.DeployRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.DeployRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public generateDeployScript(packageFilePath: string, targetDatabaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<mssql.DacFxResult> {
|
||||
const params: contracts.GenerateDeployScriptParams = { packageFilePath: packageFilePath, databaseName: targetDatabaseName, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.GenerateDeployScriptRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.GenerateDeployScriptRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public generateDeployPlan(packageFilePath: string, targetDatabaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<mssql.GenerateDeployPlanResult> {
|
||||
const params: contracts.GenerateDeployPlanParams = { packageFilePath: packageFilePath, databaseName: targetDatabaseName, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.GenerateDeployPlanRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.GenerateDeployPlanRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -27,267 +27,6 @@ export class TelemetryFeature implements StaticFeature {
|
||||
}
|
||||
}
|
||||
|
||||
export class DacFxServicesFeature extends SqlOpsFeature<undefined> {
|
||||
private static readonly messageTypes: RPCMessageType[] = [
|
||||
contracts.ExportRequest.type,
|
||||
contracts.ImportRequest.type,
|
||||
contracts.ExtractRequest.type,
|
||||
contracts.DeployRequest.type
|
||||
];
|
||||
|
||||
constructor(client: SqlOpsDataClient) {
|
||||
super(client, DacFxServicesFeature.messageTypes);
|
||||
}
|
||||
|
||||
public fillClientCapabilities(capabilities: ClientCapabilities): void {
|
||||
}
|
||||
|
||||
public initialize(capabilities: ServerCapabilities): void {
|
||||
this.register(this.messages, {
|
||||
id: UUID.generateUuid(),
|
||||
registerOptions: undefined
|
||||
});
|
||||
}
|
||||
|
||||
protected registerProvider(options: undefined): Disposable {
|
||||
const client = this._client;
|
||||
|
||||
let exportBacpac = (databaseName: string, packageFilePath: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.DacFxResult> => {
|
||||
let params: contracts.ExportParams = { databaseName: databaseName, packageFilePath: packageFilePath, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.ExportRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.ExportRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let importBacpac = (packageFilePath: string, databaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.DacFxResult> => {
|
||||
let params: contracts.ImportParams = { packageFilePath: packageFilePath, databaseName: databaseName, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.ImportRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.ImportRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let extractDacpac = (databaseName: string, packageFilePath: string, applicationName: string, applicationVersion: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.DacFxResult> => {
|
||||
let params: contracts.ExtractParams = { databaseName: databaseName, packageFilePath: packageFilePath, applicationName: applicationName, applicationVersion: applicationVersion, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.ExtractRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.ExtractRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let deployDacpac = (packageFilePath: string, targetDatabaseName: string, upgradeExisting: boolean, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.DacFxResult> => {
|
||||
let params: contracts.DeployParams = { packageFilePath: packageFilePath, databaseName: targetDatabaseName, upgradeExisting: upgradeExisting, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.DeployRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.DeployRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let generateDeployScript = (packageFilePath: string, targetDatabaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.DacFxResult> => {
|
||||
let params: contracts.GenerateDeployScriptParams = { packageFilePath: packageFilePath, databaseName: targetDatabaseName, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.GenerateDeployScriptRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.GenerateDeployScriptRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let generateDeployPlan = (packageFilePath: string, targetDatabaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.GenerateDeployPlanResult> => {
|
||||
let params: contracts.GenerateDeployPlanParams = { packageFilePath: packageFilePath, databaseName: targetDatabaseName, ownerUri: ownerUri, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.GenerateDeployPlanRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.GenerateDeployPlanRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
return azdata.dataprotocol.registerDacFxServicesProvider({
|
||||
providerId: client.providerId,
|
||||
exportBacpac,
|
||||
importBacpac,
|
||||
extractDacpac,
|
||||
deployDacpac,
|
||||
generateDeployScript,
|
||||
generateDeployPlan
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
export class SchemaCompareServicesFeature extends SqlOpsFeature<undefined> {
|
||||
private static readonly messageTypes: RPCMessageType[] = [
|
||||
contracts.SchemaCompareRequest.type,
|
||||
contracts.SchemaCompareGenerateScriptRequest.type,
|
||||
contracts.SchemaComparePublishChangesRequest.type,
|
||||
contracts.SchemaCompareGetDefaultOptionsRequest.type,
|
||||
contracts.SchemaCompareIncludeExcludeNodeRequest.type,
|
||||
contracts.SchemaCompareOpenScmpRequest.type,
|
||||
contracts.SchemaCompareSaveScmpRequest.type
|
||||
];
|
||||
|
||||
constructor(client: SqlOpsDataClient) {
|
||||
super(client, SchemaCompareServicesFeature.messageTypes);
|
||||
}
|
||||
|
||||
public fillClientCapabilities(capabilities: ClientCapabilities): void {
|
||||
}
|
||||
|
||||
public initialize(capabilities: ServerCapabilities): void {
|
||||
this.register(this.messages, {
|
||||
id: UUID.generateUuid(),
|
||||
registerOptions: undefined
|
||||
});
|
||||
}
|
||||
|
||||
protected registerProvider(options: undefined): Disposable {
|
||||
const client = this._client;
|
||||
|
||||
let schemaCompare = (operationId: string, sourceEndpointInfo: azdata.SchemaCompareEndpointInfo, targetEndpointInfo: azdata.SchemaCompareEndpointInfo, taskExecutionMode: azdata.TaskExecutionMode, deploymentOptions: azdata.DeploymentOptions): Thenable<azdata.SchemaCompareResult> => {
|
||||
let params: contracts.SchemaCompareParams = { operationId: operationId, sourceEndpointInfo: sourceEndpointInfo, targetEndpointInfo: targetEndpointInfo, taskExecutionMode: taskExecutionMode, deploymentOptions: deploymentOptions };
|
||||
return client.sendRequest(contracts.SchemaCompareRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaCompareRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let schemaCompareGenerateScript = (operationId: string, targetServerName: string, targetDatabaseName: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus> => {
|
||||
let params: contracts.SchemaCompareGenerateScriptParams = { operationId: operationId, targetServerName: targetServerName, targetDatabaseName: targetDatabaseName, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.SchemaCompareGenerateScriptRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaCompareGenerateScriptRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let schemaComparePublishChanges = (operationId: string, targetServerName: string, targetDatabaseName: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus> => {
|
||||
let params: contracts.SchemaComparePublishChangesParams = { operationId: operationId, targetServerName: targetServerName, targetDatabaseName: targetDatabaseName, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.SchemaComparePublishChangesRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaComparePublishChangesRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let schemaCompareGetDefaultOptions = (): Thenable<azdata.SchemaCompareOptionsResult> => {
|
||||
let params: contracts.SchemaCompareGetOptionsParams = {};
|
||||
return client.sendRequest(contracts.SchemaCompareGetDefaultOptionsRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaCompareGetDefaultOptionsRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let schemaCompareIncludeExcludeNode = (operationId: string, diffEntry: azdata.DiffEntry, includeRequest: boolean, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus> => {
|
||||
let params: contracts.SchemaCompareNodeParams = { operationId: operationId, diffEntry, includeRequest, taskExecutionMode: taskExecutionMode };
|
||||
return client.sendRequest(contracts.SchemaCompareIncludeExcludeNodeRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaCompareIncludeExcludeNodeRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let schemaCompareOpenScmp = (filePath: string): Thenable<azdata.SchemaCompareOpenScmpResult> => {
|
||||
let params: contracts.SchemaCompareOpenScmpParams = { filePath: filePath };
|
||||
return client.sendRequest(contracts.SchemaCompareOpenScmpRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaCompareOpenScmpRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let schemaCompareSaveScmp = (sourceEndpointInfo: azdata.SchemaCompareEndpointInfo, targetEndpointInfo: azdata.SchemaCompareEndpointInfo, taskExecutionMode: azdata.TaskExecutionMode, deploymentOptions: azdata.DeploymentOptions, scmpFilePath: string, excludedSourceObjects: azdata.SchemaCompareObjectId[], excludedTargetObjects: azdata.SchemaCompareObjectId[]): Thenable<azdata.ResultStatus> => {
|
||||
let params: contracts.SchemaCompareSaveScmpParams = { sourceEndpointInfo: sourceEndpointInfo, targetEndpointInfo: targetEndpointInfo, taskExecutionMode: taskExecutionMode, deploymentOptions: deploymentOptions, scmpFilePath: scmpFilePath, excludedSourceObjects: excludedSourceObjects, excludedTargetObjects: excludedTargetObjects };
|
||||
return client.sendRequest(contracts.SchemaCompareSaveScmpRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaCompareSaveScmpRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
let schemaCompareCancel = (operationId: string): Thenable<azdata.ResultStatus> => {
|
||||
let params: contracts.SchemaCompareCancelParams = { operationId: operationId };
|
||||
return client.sendRequest(contracts.SchemaCompareCancellationRequest.type, params).then(
|
||||
r => {
|
||||
return r;
|
||||
},
|
||||
e => {
|
||||
client.logFailedRequest(contracts.SchemaCompareCancellationRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
return azdata.dataprotocol.registerSchemaCompareServicesProvider({
|
||||
providerId: client.providerId,
|
||||
schemaCompare,
|
||||
schemaCompareGenerateScript,
|
||||
schemaComparePublishChanges,
|
||||
schemaCompareGetDefaultOptions,
|
||||
schemaCompareIncludeExcludeNode,
|
||||
schemaCompareOpenScmp,
|
||||
schemaCompareSaveScmp,
|
||||
schemaCompareCancel
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
export class AgentServicesFeature extends SqlOpsFeature<undefined> {
|
||||
private static readonly messagesTypes: RPCMessageType[] = [
|
||||
contracts.AgentJobsRequest.type,
|
||||
|
||||
8
extensions/mssql/src/localize.ts
Normal file
8
extensions/mssql/src/localize.ts
Normal file
@@ -0,0 +1,8 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as nls from 'vscode-nls';
|
||||
|
||||
export const localize = nls.loadMessageBundle();
|
||||
@@ -7,44 +7,32 @@ import * as vscode from 'vscode';
|
||||
import * as azdata from 'azdata';
|
||||
import * as path from 'path';
|
||||
import * as os from 'os';
|
||||
import * as nls from 'vscode-nls';
|
||||
|
||||
const localize = nls.loadMessageBundle();
|
||||
|
||||
import { SqlOpsDataClient, ClientOptions } from 'dataprotocol-client';
|
||||
import { IConfig, ServerProvider, Events } from 'service-downloader';
|
||||
import { ServerOptions, TransportKind } from 'vscode-languageclient';
|
||||
|
||||
import * as Constants from './constants';
|
||||
import ContextProvider from './contextProvider';
|
||||
import { CredentialStore } from './credentialstore/credentialstore';
|
||||
import { AzureResourceProvider } from './resourceProvider/resourceProvider';
|
||||
import * as Utils from './utils';
|
||||
import { Telemetry, LanguageClientErrorHandler } from './telemetry';
|
||||
import { TelemetryFeature, AgentServicesFeature, DacFxServicesFeature, SchemaCompareServicesFeature, SerializationFeature } from './features';
|
||||
import { AppContext } from './appContext';
|
||||
import { ApiWrapper } from './apiWrapper';
|
||||
import { UploadFilesCommand, MkDirCommand, SaveFileCommand, PreviewFileCommand, CopyPathCommand, DeleteFilesCommand } from './objectExplorerNodeProvider/hdfsCommands';
|
||||
import { IPrompter } from './prompts/question';
|
||||
import CodeAdapter from './prompts/adapter';
|
||||
import { MssqlExtensionApi, MssqlObjectExplorerBrowser } from './api/mssqlapis';
|
||||
import { mssql } from './mssql';
|
||||
import { OpenSparkJobSubmissionDialogCommand, OpenSparkJobSubmissionDialogFromFileCommand, OpenSparkJobSubmissionDialogTask } from './sparkFeature/dialog/dialogCommands';
|
||||
import { OpenSparkYarnHistoryTask } from './sparkFeature/historyTask';
|
||||
import { MssqlObjectExplorerNodeProvider, mssqlOutputChannel } from './objectExplorerNodeProvider/objectExplorerNodeProvider';
|
||||
import { CmsService } from './cms/cmsService';
|
||||
import { registerSearchServerCommand } from './objectExplorerNodeProvider/command';
|
||||
import { MssqlIconProvider } from './iconProvider';
|
||||
import { registerServiceEndpoints } from './dashboard/serviceEndpoints';
|
||||
import { getBookExtensionContributions } from './dashboard/bookExtensions';
|
||||
import { registerBooksWidget } from './dashboard/bookWidget';
|
||||
import { createMssqlApi } from './mssqlApiFactory';
|
||||
import { localize } from './localize';
|
||||
import { SqlToolsServer } from './sqlToolsServer';
|
||||
|
||||
const baseConfig = require('./config.json');
|
||||
const outputChannel = vscode.window.createOutputChannel(Constants.serviceName);
|
||||
const statusView = vscode.window.createStatusBarItem(vscode.StatusBarAlignment.Left);
|
||||
const msgSampleCodeDataFrame = localize('msgSampleCodeDataFrame', 'This sample code loads the file into a data frame and shows the first 10 results.');
|
||||
|
||||
|
||||
export async function activate(context: vscode.ExtensionContext): Promise<MssqlExtensionApi> {
|
||||
export async function activate(context: vscode.ExtensionContext): Promise<mssql> {
|
||||
// lets make sure we support this platform first
|
||||
let supported = await Utils.verifyPlatform();
|
||||
|
||||
@@ -53,74 +41,25 @@ export async function activate(context: vscode.ExtensionContext): Promise<MssqlE
|
||||
return undefined;
|
||||
}
|
||||
|
||||
// ensure our log path exists
|
||||
if (!(await Utils.pfs.exists(context.logPath))) {
|
||||
await Utils.pfs.mkdir(context.logPath);
|
||||
}
|
||||
|
||||
let config: IConfig = JSON.parse(JSON.stringify(baseConfig));
|
||||
config.installDirectory = path.join(__dirname, config.installDirectory);
|
||||
config.proxy = vscode.workspace.getConfiguration('http').get('proxy');
|
||||
config.strictSSL = vscode.workspace.getConfiguration('http').get('proxyStrictSSL') || true;
|
||||
|
||||
const credentialsStore = new CredentialStore(context.logPath, config);
|
||||
const resourceProvider = new AzureResourceProvider(context.logPath, config);
|
||||
let languageClient: SqlOpsDataClient;
|
||||
let cmsService: CmsService;
|
||||
|
||||
const serverdownloader = new ServerProvider(config);
|
||||
|
||||
serverdownloader.eventEmitter.onAny(generateHandleServerProviderEvent());
|
||||
|
||||
let clientOptions: ClientOptions = getClientOptions();
|
||||
|
||||
let prompter: IPrompter = new CodeAdapter();
|
||||
let appContext = new AppContext(context, new ApiWrapper());
|
||||
|
||||
const installationStart = Date.now();
|
||||
let serverPromise = serverdownloader.getOrDownloadServer().then(e => {
|
||||
const installationComplete = Date.now();
|
||||
let serverOptions = generateServerOptions(context.logPath, e);
|
||||
languageClient = new SqlOpsDataClient(Constants.serviceName, serverOptions, clientOptions);
|
||||
const processStart = Date.now();
|
||||
languageClient.onReady().then(() => {
|
||||
const processEnd = Date.now();
|
||||
statusView.text = 'Service Started';
|
||||
setTimeout(() => {
|
||||
statusView.hide();
|
||||
}, 1500);
|
||||
Telemetry.sendTelemetryEvent('startup/LanguageClientStarted', {
|
||||
installationTime: String(installationComplete - installationStart),
|
||||
processStartupTime: String(processEnd - processStart),
|
||||
totalTime: String(processEnd - installationStart),
|
||||
beginningTimestamp: String(installationStart)
|
||||
});
|
||||
let nodeProvider = new MssqlObjectExplorerNodeProvider(prompter, appContext);
|
||||
azdata.dataprotocol.registerObjectExplorerNodeProvider(nodeProvider);
|
||||
let iconProvider = new MssqlIconProvider();
|
||||
azdata.dataprotocol.registerIconProvider(iconProvider);
|
||||
|
||||
});
|
||||
statusView.show();
|
||||
statusView.text = 'Starting service';
|
||||
languageClient.start();
|
||||
credentialsStore.start();
|
||||
resourceProvider.start();
|
||||
activateSparkFeatures(appContext);
|
||||
activateNotebookTask(appContext);
|
||||
|
||||
let nodeProvider = new MssqlObjectExplorerNodeProvider(prompter, appContext);
|
||||
azdata.dataprotocol.registerObjectExplorerNodeProvider(nodeProvider);
|
||||
let iconProvider = new MssqlIconProvider();
|
||||
azdata.dataprotocol.registerIconProvider(iconProvider);
|
||||
cmsService = new CmsService(appContext, languageClient);
|
||||
|
||||
activateSparkFeatures(appContext);
|
||||
activateNotebookTask(appContext);
|
||||
}, e => {
|
||||
Telemetry.sendTelemetryEvent('ServiceInitializingFailed');
|
||||
vscode.window.showErrorMessage('Failed to start Sql tools service');
|
||||
});
|
||||
registerSearchServerCommand(appContext);
|
||||
let contextProvider = new ContextProvider();
|
||||
context.subscriptions.push(contextProvider);
|
||||
context.subscriptions.push(credentialsStore);
|
||||
context.subscriptions.push(resourceProvider);
|
||||
context.subscriptions.push(new ContextProvider());
|
||||
registerHdfsCommands(context, prompter, appContext);
|
||||
context.subscriptions.push({ dispose: () => languageClient.stop() });
|
||||
|
||||
registerLogCommand(context);
|
||||
|
||||
@@ -131,20 +70,12 @@ export async function activate(context: vscode.ExtensionContext): Promise<MssqlE
|
||||
|
||||
registerBooksWidget(bookContributionProvider);
|
||||
|
||||
let api: MssqlExtensionApi = {
|
||||
getMssqlObjectExplorerBrowser(): MssqlObjectExplorerBrowser {
|
||||
return {
|
||||
getNode: (context: azdata.ObjectExplorerContext) => {
|
||||
let oeProvider = appContext.getService<MssqlObjectExplorerNodeProvider>(Constants.ObjectExplorerService);
|
||||
return <any>oeProvider.findSqlClusterNodeByContext(context);
|
||||
}
|
||||
};
|
||||
},
|
||||
getCmsServiceProvider(): Promise<CmsService> {
|
||||
return serverPromise.then(() => cmsService);
|
||||
}
|
||||
};
|
||||
return api;
|
||||
// initalize client last so we don't have features stuck behind it
|
||||
const server = new SqlToolsServer();
|
||||
context.subscriptions.push(server);
|
||||
await server.start(appContext);
|
||||
|
||||
return createMssqlApi(appContext);
|
||||
}
|
||||
|
||||
const logFiles = ['resourceprovider.log', 'sqltools.log', 'credentialstore.log'];
|
||||
@@ -160,27 +91,6 @@ function registerLogCommand(context: vscode.ExtensionContext) {
|
||||
}));
|
||||
}
|
||||
|
||||
function getClientOptions(): ClientOptions {
|
||||
return {
|
||||
documentSelector: ['sql'],
|
||||
synchronize: {
|
||||
configurationSection: Constants.extensionConfigSectionName
|
||||
},
|
||||
providerId: Constants.providerId,
|
||||
errorHandler: new LanguageClientErrorHandler(),
|
||||
features: [
|
||||
// we only want to add new features
|
||||
...SqlOpsDataClient.defaultFeatures,
|
||||
TelemetryFeature,
|
||||
AgentServicesFeature,
|
||||
DacFxServicesFeature,
|
||||
SchemaCompareServicesFeature,
|
||||
SerializationFeature
|
||||
],
|
||||
outputChannel: new CustomOutputChannel()
|
||||
};
|
||||
}
|
||||
|
||||
function registerHdfsCommands(context: vscode.ExtensionContext, prompter: IPrompter, appContext: AppContext) {
|
||||
context.subscriptions.push(new UploadFilesCommand(prompter, appContext));
|
||||
context.subscriptions.push(new MkDirCommand(prompter, appContext));
|
||||
@@ -306,66 +216,7 @@ async function handleOpenClusterStatusNotebookTask(profile: azdata.IConnectionPr
|
||||
});
|
||||
}
|
||||
}
|
||||
function generateServerOptions(logPath: string, executablePath: string): ServerOptions {
|
||||
let launchArgs = Utils.getCommonLaunchArgsAndCleanupOldLogFiles(logPath, 'sqltools.log', executablePath);
|
||||
return { command: executablePath, args: launchArgs, transport: TransportKind.stdio };
|
||||
}
|
||||
|
||||
function generateHandleServerProviderEvent() {
|
||||
let dots = 0;
|
||||
return (e: string, ...args: any[]) => {
|
||||
switch (e) {
|
||||
case Events.INSTALL_START:
|
||||
outputChannel.show(true);
|
||||
statusView.show();
|
||||
outputChannel.appendLine(localize('installingServiceChannelMsg', 'Installing {0} service to {1}', Constants.serviceName, args[0]));
|
||||
statusView.text = localize('installingServiceStatusMsg', 'Installing Service');
|
||||
break;
|
||||
case Events.INSTALL_END:
|
||||
outputChannel.appendLine(localize('installedServiceChannelMsg', 'Installed'));
|
||||
break;
|
||||
case Events.DOWNLOAD_START:
|
||||
outputChannel.appendLine(localize('downloadingServiceChannelMsg', 'Downloading {0}', args[0]));
|
||||
outputChannel.append(localize('downloadingServiceSizeChannelMsg', '({0} KB)', Math.ceil(args[1] / 1024).toLocaleString(vscode.env.language)));
|
||||
statusView.text = localize('downloadingServiceStatusMsg', 'Downloading Service');
|
||||
break;
|
||||
case Events.DOWNLOAD_PROGRESS:
|
||||
let newDots = Math.ceil(args[0] / 5);
|
||||
if (newDots > dots) {
|
||||
outputChannel.append('.'.repeat(newDots - dots));
|
||||
dots = newDots;
|
||||
}
|
||||
break;
|
||||
case Events.DOWNLOAD_END:
|
||||
outputChannel.appendLine(localize('downloadServiceDoneChannelMsg', 'Done!'));
|
||||
break;
|
||||
default:
|
||||
console.error(`Unknown event from Server Provider ${e}`);
|
||||
break;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
// this method is called when your extension is deactivated
|
||||
export function deactivate(): void {
|
||||
}
|
||||
|
||||
class CustomOutputChannel implements vscode.OutputChannel {
|
||||
name: string;
|
||||
append(value: string): void {
|
||||
console.log(value);
|
||||
}
|
||||
appendLine(value: string): void {
|
||||
console.log(value);
|
||||
}
|
||||
clear(): void {
|
||||
}
|
||||
show(preserveFocus?: boolean): void;
|
||||
show(column?: vscode.ViewColumn, preserveFocus?: boolean): void;
|
||||
show(column?: any, preserveFocus?: any) {
|
||||
}
|
||||
hide(): void {
|
||||
}
|
||||
dispose(): void {
|
||||
}
|
||||
}
|
||||
|
||||
433
extensions/mssql/src/mssql.d.ts
vendored
Normal file
433
extensions/mssql/src/mssql.d.ts
vendored
Normal file
@@ -0,0 +1,433 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
// This is the place for extensions to expose APIs.
|
||||
|
||||
import * as azdata from 'azdata';
|
||||
import * as vscode from 'vscode';
|
||||
|
||||
/**
|
||||
* Covers defining what the mssql extension exports to other extensions
|
||||
*
|
||||
* IMPORTANT: THIS IS NOT A HARD DEFINITION unlike vscode; therefore no enums or classes should be defined here
|
||||
* (const enums get evaluated when typescript -> javascript so those are fine)
|
||||
*/
|
||||
|
||||
|
||||
export const enum extension {
|
||||
name = 'Microsoft.mssql'
|
||||
}
|
||||
|
||||
/**
|
||||
* The APIs provided by Mssql extension
|
||||
*/
|
||||
export interface mssql {
|
||||
/**
|
||||
* Gets the object explorer API that supports querying over the connections supported by this extension
|
||||
*
|
||||
*/
|
||||
getMssqlObjectExplorerBrowser(): MssqlObjectExplorerBrowser;
|
||||
|
||||
/**
|
||||
* Get the Cms Service APIs to communicate with CMS connections supported by this extension
|
||||
*
|
||||
*/
|
||||
readonly cmsService: ICmsService;
|
||||
|
||||
readonly schemaCompare: ISchemaCompareService;
|
||||
|
||||
readonly dacFx: IDacFxService;
|
||||
}
|
||||
|
||||
/**
|
||||
* A browser supporting actions over the object explorer connections provided by this extension.
|
||||
* Currently this is the
|
||||
*/
|
||||
export interface MssqlObjectExplorerBrowser {
|
||||
/**
|
||||
* Gets the matching node given a context object, e.g. one from a right-click on a node in Object Explorer
|
||||
*/
|
||||
getNode<T extends ITreeNode>(objectExplorerContext: azdata.ObjectExplorerContext): Thenable<T>;
|
||||
}
|
||||
|
||||
/**
|
||||
* A tree node in the object explorer tree
|
||||
*/
|
||||
export interface ITreeNode {
|
||||
getNodeInfo(): azdata.NodeInfo;
|
||||
getChildren(refreshChildren: boolean): ITreeNode[] | Thenable<ITreeNode[]>;
|
||||
}
|
||||
|
||||
/**
|
||||
* A HDFS file node. This is a leaf node in the object explorer tree, and its contents
|
||||
* can be queried
|
||||
*/
|
||||
export interface IFileNode extends ITreeNode {
|
||||
getFileContentsAsString(maxBytes?: number): Thenable<string>;
|
||||
}
|
||||
|
||||
//#region --- schema compare
|
||||
export interface SchemaCompareResult extends azdata.ResultStatus {
|
||||
operationId: string;
|
||||
areEqual: boolean;
|
||||
differences: DiffEntry[];
|
||||
}
|
||||
|
||||
export interface SchemaCompareCompletionResult extends azdata.ResultStatus {
|
||||
operationId: string;
|
||||
areEqual: boolean;
|
||||
differences: DiffEntry[];
|
||||
}
|
||||
|
||||
export interface DiffEntry {
|
||||
updateAction: SchemaUpdateAction;
|
||||
differenceType: SchemaDifferenceType;
|
||||
name: string;
|
||||
sourceValue: string[];
|
||||
targetValue: string[];
|
||||
parent: DiffEntry;
|
||||
children: DiffEntry[];
|
||||
sourceScript: string;
|
||||
targetScript: string;
|
||||
}
|
||||
|
||||
export const enum SchemaUpdateAction {
|
||||
Delete = 0,
|
||||
Change = 1,
|
||||
Add = 2
|
||||
}
|
||||
|
||||
export const enum SchemaDifferenceType {
|
||||
Object = 0,
|
||||
Property = 1
|
||||
}
|
||||
|
||||
export const enum SchemaCompareEndpointType {
|
||||
Database = 0,
|
||||
Dacpac = 1
|
||||
}
|
||||
|
||||
export interface SchemaCompareEndpointInfo {
|
||||
endpointType: SchemaCompareEndpointType;
|
||||
packageFilePath: string;
|
||||
serverDisplayName: string;
|
||||
serverName: string;
|
||||
databaseName: string;
|
||||
ownerUri: string;
|
||||
connectionDetails: azdata.ConnectionInfo;
|
||||
}
|
||||
|
||||
export interface SchemaCompareObjectId {
|
||||
nameParts: string[];
|
||||
sqlObjectType: string;
|
||||
}
|
||||
|
||||
export interface SchemaCompareOptionsResult extends azdata.ResultStatus {
|
||||
defaultDeploymentOptions: DeploymentOptions;
|
||||
}
|
||||
|
||||
export interface DeploymentOptions {
|
||||
ignoreTableOptions: boolean;
|
||||
ignoreSemicolonBetweenStatements: boolean;
|
||||
ignoreRouteLifetime: boolean;
|
||||
ignoreRoleMembership: boolean;
|
||||
ignoreQuotedIdentifiers: boolean;
|
||||
ignorePermissions: boolean;
|
||||
ignorePartitionSchemes: boolean;
|
||||
ignoreObjectPlacementOnPartitionScheme: boolean;
|
||||
ignoreNotForReplication: boolean;
|
||||
ignoreLoginSids: boolean;
|
||||
ignoreLockHintsOnIndexes: boolean;
|
||||
ignoreKeywordCasing: boolean;
|
||||
ignoreIndexPadding: boolean;
|
||||
ignoreIndexOptions: boolean;
|
||||
ignoreIncrement: boolean;
|
||||
ignoreIdentitySeed: boolean;
|
||||
ignoreUserSettingsObjects: boolean;
|
||||
ignoreFullTextCatalogFilePath: boolean;
|
||||
ignoreWhitespace: boolean;
|
||||
ignoreWithNocheckOnForeignKeys: boolean;
|
||||
verifyCollationCompatibility: boolean;
|
||||
unmodifiableObjectWarnings: boolean;
|
||||
treatVerificationErrorsAsWarnings: boolean;
|
||||
scriptRefreshModule: boolean;
|
||||
scriptNewConstraintValidation: boolean;
|
||||
scriptFileSize: boolean;
|
||||
scriptDeployStateChecks: boolean;
|
||||
scriptDatabaseOptions: boolean;
|
||||
scriptDatabaseCompatibility: boolean;
|
||||
scriptDatabaseCollation: boolean;
|
||||
runDeploymentPlanExecutors: boolean;
|
||||
registerDataTierApplication: boolean;
|
||||
populateFilesOnFileGroups: boolean;
|
||||
noAlterStatementsToChangeClrTypes: boolean;
|
||||
includeTransactionalScripts: boolean;
|
||||
includeCompositeObjects: boolean;
|
||||
allowUnsafeRowLevelSecurityDataMovement: boolean;
|
||||
ignoreWithNocheckOnCheckConstraints: boolean;
|
||||
ignoreFillFactor: boolean;
|
||||
ignoreFileSize: boolean;
|
||||
ignoreFilegroupPlacement: boolean;
|
||||
doNotAlterReplicatedObjects: boolean;
|
||||
doNotAlterChangeDataCaptureObjects: boolean;
|
||||
disableAndReenableDdlTriggers: boolean;
|
||||
deployDatabaseInSingleUserMode: boolean;
|
||||
createNewDatabase: boolean;
|
||||
compareUsingTargetCollation: boolean;
|
||||
commentOutSetVarDeclarations: boolean;
|
||||
blockWhenDriftDetected: boolean;
|
||||
blockOnPossibleDataLoss: boolean;
|
||||
backupDatabaseBeforeChanges: boolean;
|
||||
allowIncompatiblePlatform: boolean;
|
||||
allowDropBlockingAssemblies: boolean;
|
||||
dropConstraintsNotInSource: boolean;
|
||||
dropDmlTriggersNotInSource: boolean;
|
||||
dropExtendedPropertiesNotInSource: boolean;
|
||||
dropIndexesNotInSource: boolean;
|
||||
ignoreFileAndLogFilePath: boolean;
|
||||
ignoreExtendedProperties: boolean;
|
||||
ignoreDmlTriggerState: boolean;
|
||||
ignoreDmlTriggerOrder: boolean;
|
||||
ignoreDefaultSchema: boolean;
|
||||
ignoreDdlTriggerState: boolean;
|
||||
ignoreDdlTriggerOrder: boolean;
|
||||
ignoreCryptographicProviderFilePath: boolean;
|
||||
verifyDeployment: boolean;
|
||||
ignoreComments: boolean;
|
||||
ignoreColumnCollation: boolean;
|
||||
ignoreAuthorizer: boolean;
|
||||
ignoreAnsiNulls: boolean;
|
||||
generateSmartDefaults: boolean;
|
||||
dropStatisticsNotInSource: boolean;
|
||||
dropRoleMembersNotInSource: boolean;
|
||||
dropPermissionsNotInSource: boolean;
|
||||
dropObjectsNotInSource: boolean;
|
||||
ignoreColumnOrder: boolean;
|
||||
doNotDropObjectTypes: SchemaObjectType[];
|
||||
excludeObjectTypes: SchemaObjectType[];
|
||||
}
|
||||
|
||||
export const enum SchemaObjectType {
|
||||
Aggregates = 0,
|
||||
ApplicationRoles = 1,
|
||||
Assemblies = 2,
|
||||
AssemblyFiles = 3,
|
||||
AsymmetricKeys = 4,
|
||||
BrokerPriorities = 5,
|
||||
Certificates = 6,
|
||||
ColumnEncryptionKeys = 7,
|
||||
ColumnMasterKeys = 8,
|
||||
Contracts = 9,
|
||||
DatabaseOptions = 10,
|
||||
DatabaseRoles = 11,
|
||||
DatabaseTriggers = 12,
|
||||
Defaults = 13,
|
||||
ExtendedProperties = 14,
|
||||
ExternalDataSources = 15,
|
||||
ExternalFileFormats = 16,
|
||||
ExternalTables = 17,
|
||||
Filegroups = 18,
|
||||
Files = 19,
|
||||
FileTables = 20,
|
||||
FullTextCatalogs = 21,
|
||||
FullTextStoplists = 22,
|
||||
MessageTypes = 23,
|
||||
PartitionFunctions = 24,
|
||||
PartitionSchemes = 25,
|
||||
Permissions = 26,
|
||||
Queues = 27,
|
||||
RemoteServiceBindings = 28,
|
||||
RoleMembership = 29,
|
||||
Rules = 30,
|
||||
ScalarValuedFunctions = 31,
|
||||
SearchPropertyLists = 32,
|
||||
SecurityPolicies = 33,
|
||||
Sequences = 34,
|
||||
Services = 35,
|
||||
Signatures = 36,
|
||||
StoredProcedures = 37,
|
||||
SymmetricKeys = 38,
|
||||
Synonyms = 39,
|
||||
Tables = 40,
|
||||
TableValuedFunctions = 41,
|
||||
UserDefinedDataTypes = 42,
|
||||
UserDefinedTableTypes = 43,
|
||||
ClrUserDefinedTypes = 44,
|
||||
Users = 45,
|
||||
Views = 46,
|
||||
XmlSchemaCollections = 47,
|
||||
Audits = 48,
|
||||
Credentials = 49,
|
||||
CryptographicProviders = 50,
|
||||
DatabaseAuditSpecifications = 51,
|
||||
DatabaseEncryptionKeys = 52,
|
||||
DatabaseScopedCredentials = 53,
|
||||
Endpoints = 54,
|
||||
ErrorMessages = 55,
|
||||
EventNotifications = 56,
|
||||
EventSessions = 57,
|
||||
LinkedServerLogins = 58,
|
||||
LinkedServers = 59,
|
||||
Logins = 60,
|
||||
MasterKeys = 61,
|
||||
Routes = 62,
|
||||
ServerAuditSpecifications = 63,
|
||||
ServerRoleMembership = 64,
|
||||
ServerRoles = 65,
|
||||
ServerTriggers = 66
|
||||
}
|
||||
|
||||
export interface SchemaCompareObjectId {
|
||||
nameParts: string[];
|
||||
sqlObjectType: string;
|
||||
}
|
||||
|
||||
export interface ISchemaCompareService {
|
||||
|
||||
schemaCompare(operationId: string, sourceEndpointInfo: SchemaCompareEndpointInfo, targetEndpointInfo: SchemaCompareEndpointInfo, taskExecutionMode: azdata.TaskExecutionMode, deploymentOptions: DeploymentOptions): Thenable<SchemaCompareResult>;
|
||||
schemaCompareGenerateScript(operationId: string, targetServerName: string, targetDatabaseName: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus>;
|
||||
schemaComparePublishChanges(operationId: string, targetServerName: string, targetDatabaseName: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus>;
|
||||
schemaCompareGetDefaultOptions(): Thenable<SchemaCompareOptionsResult>;
|
||||
schemaCompareIncludeExcludeNode(operationId: string, diffEntry: DiffEntry, IncludeRequest: boolean, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus>;
|
||||
schemaCompareOpenScmp(filePath: string): Thenable<SchemaCompareOpenScmpResult>;
|
||||
schemaCompareSaveScmp(sourceEndpointInfo: SchemaCompareEndpointInfo, targetEndpointInfo: SchemaCompareEndpointInfo, taskExecutionMode: azdata.TaskExecutionMode, deploymentOptions: DeploymentOptions, scmpFilePath: string, excludedSourceObjects: SchemaCompareObjectId[], excludedTargetObjects: SchemaCompareObjectId[]): Thenable<azdata.ResultStatus>;
|
||||
schemaCompareCancel(operationId: string): Thenable<azdata.ResultStatus>;
|
||||
}
|
||||
|
||||
export interface SchemaCompareOpenScmpResult extends azdata.ResultStatus {
|
||||
sourceEndpointInfo: SchemaCompareEndpointInfo;
|
||||
targetEndpointInfo: SchemaCompareEndpointInfo;
|
||||
originalTargetName: string;
|
||||
originalConnectionString: string;
|
||||
deploymentOptions: DeploymentOptions;
|
||||
excludedSourceElements: SchemaCompareObjectId[];
|
||||
excludedTargetElements: SchemaCompareObjectId[];
|
||||
}
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region --- dacfx
|
||||
export interface IDacFxService {
|
||||
exportBacpac(databaseName: string, packageFilePath: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<DacFxResult>;
|
||||
importBacpac(packageFilePath: string, databaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<DacFxResult>;
|
||||
extractDacpac(databaseName: string, packageFilePath: string, applicationName: string, applicationVersion: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<DacFxResult>;
|
||||
deployDacpac(packageFilePath: string, databaseName: string, upgradeExisting: boolean, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<DacFxResult>;
|
||||
generateDeployScript(packageFilePath: string, databaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<DacFxResult>;
|
||||
generateDeployPlan(packageFilePath: string, databaseName: string, ownerUri: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<GenerateDeployPlanResult>;
|
||||
}
|
||||
|
||||
export interface DacFxResult extends azdata.ResultStatus {
|
||||
operationId: string;
|
||||
}
|
||||
|
||||
export interface GenerateDeployPlanResult extends DacFxResult {
|
||||
report: string;
|
||||
}
|
||||
|
||||
export interface ExportParams {
|
||||
databaseName: string;
|
||||
packageFilePath: string;
|
||||
ownerUri: string;
|
||||
taskExecutionMode: azdata.TaskExecutionMode;
|
||||
}
|
||||
|
||||
export interface ImportParams {
|
||||
packageFilePath: string;
|
||||
databaseName: string;
|
||||
ownerUri: string;
|
||||
taskExecutionMode: azdata.TaskExecutionMode;
|
||||
}
|
||||
|
||||
export interface ExtractParams {
|
||||
databaseName: string;
|
||||
packageFilePath: string;
|
||||
applicationName: string;
|
||||
applicationVersion: string;
|
||||
ownerUri: string;
|
||||
taskExecutionMode: azdata.TaskExecutionMode;
|
||||
}
|
||||
|
||||
export interface DeployParams {
|
||||
packageFilePath: string;
|
||||
databaseName: string;
|
||||
upgradeExisting: boolean;
|
||||
ownerUri: string;
|
||||
taskExecutionMode: azdata.TaskExecutionMode;
|
||||
}
|
||||
|
||||
export interface GenerateDeployScriptParams {
|
||||
packageFilePath: string;
|
||||
databaseName: string;
|
||||
ownerUri: string;
|
||||
taskExecutionMode: azdata.TaskExecutionMode;
|
||||
}
|
||||
|
||||
export interface GenerateDeployPlan {
|
||||
packageFilePath: string;
|
||||
databaseName: string;
|
||||
ownerUri: string;
|
||||
taskExecutionMode: azdata.TaskExecutionMode;
|
||||
}
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region --- cms
|
||||
/**
|
||||
*
|
||||
* Interface containing all CMS related operations
|
||||
*/
|
||||
export interface ICmsService {
|
||||
/**
|
||||
* Connects to or creates a Central management Server
|
||||
*/
|
||||
createCmsServer(name: string, description:string, connectiondetails: azdata.ConnectionInfo, ownerUri: string): Thenable<ListRegisteredServersResult>;
|
||||
|
||||
/**
|
||||
* gets all Registered Servers inside a CMS on a particular level
|
||||
*/
|
||||
getRegisteredServers(ownerUri: string, relativePath: string): Thenable<ListRegisteredServersResult>;
|
||||
|
||||
/**
|
||||
* Adds a Registered Server inside a CMS on a particular level
|
||||
*/
|
||||
addRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string, registeredServerDescription:string, connectionDetails:azdata.ConnectionInfo): Thenable<boolean>;
|
||||
|
||||
/**
|
||||
* Removes a Registered Server inside a CMS on a particular level
|
||||
*/
|
||||
removeRegisteredServer (ownerUri: string, relativePath: string, registeredServerName: string): Thenable<boolean>;
|
||||
|
||||
/**
|
||||
* Adds a Server Group inside a CMS on a particular level
|
||||
*/
|
||||
addServerGroup (ownerUri: string, relativePath: string, groupName: string, groupDescription:string): Thenable<boolean>;
|
||||
|
||||
/**
|
||||
* Removes a Server Group inside a CMS on a particular level
|
||||
*/
|
||||
removeServerGroup (ownerUri: string, relativePath: string, groupName: string): Thenable<boolean>;
|
||||
}
|
||||
/**
|
||||
* 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<RegisteredServerResult>;
|
||||
registeredServerGroups: Array<RegisteredServerGroup>;
|
||||
}
|
||||
//#endregion
|
||||
32
extensions/mssql/src/mssqlApiFactory.ts
Normal file
32
extensions/mssql/src/mssqlApiFactory.ts
Normal file
@@ -0,0 +1,32 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { AppContext } from './appContext';
|
||||
import { mssql, ICmsService, IDacFxService, ISchemaCompareService, MssqlObjectExplorerBrowser } from './mssql';
|
||||
import * as constants from './constants';
|
||||
import { MssqlObjectExplorerNodeProvider } from './objectExplorerNodeProvider/objectExplorerNodeProvider';
|
||||
import * as azdata from 'azdata';
|
||||
|
||||
export function createMssqlApi(context: AppContext): mssql {
|
||||
return {
|
||||
get cmsService() {
|
||||
return context.getService<ICmsService>(constants.CmsService);
|
||||
},
|
||||
get dacFx() {
|
||||
return context.getService<IDacFxService>(constants.DacFxService);
|
||||
},
|
||||
get schemaCompare() {
|
||||
return context.getService<ISchemaCompareService>(constants.SchemaCompareService);
|
||||
},
|
||||
getMssqlObjectExplorerBrowser(): MssqlObjectExplorerBrowser {
|
||||
return {
|
||||
getNode: (explorerContext: azdata.ObjectExplorerContext) => {
|
||||
let oeProvider = context.getService<MssqlObjectExplorerNodeProvider>(constants.ObjectExplorerService);
|
||||
return <any>oeProvider.findSqlClusterNodeByContext(explorerContext);
|
||||
}
|
||||
};
|
||||
},
|
||||
};
|
||||
}
|
||||
@@ -9,8 +9,6 @@ import { IQuestion, IPrompter, IPromptCallback } from './question';
|
||||
// Supports simple pattern for prompting for user input and acting on this
|
||||
export default class CodeAdapter implements IPrompter {
|
||||
|
||||
constructor() { }
|
||||
|
||||
// TODO define question interface
|
||||
private fixQuestion(question: any): any {
|
||||
if (question.type === 'checkbox' && Array.isArray(question.choices)) {
|
||||
|
||||
@@ -88,7 +88,7 @@ export class AzureResourceProvider {
|
||||
providerId: Constants.providerId,
|
||||
features: [FireWallFeature]
|
||||
};
|
||||
serverdownloader.getOrDownloadServer().then(e => {
|
||||
return serverdownloader.getOrDownloadServer().then(e => {
|
||||
let serverOptions = this.generateServerOptions(e);
|
||||
this._client = new SqlOpsDataClient(Constants.serviceName, serverOptions, clientOptions);
|
||||
this._client.start();
|
||||
|
||||
122
extensions/mssql/src/schemaCompare/schemaCompareService.ts
Normal file
122
extensions/mssql/src/schemaCompare/schemaCompareService.ts
Normal file
@@ -0,0 +1,122 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { AppContext } from '../appContext';
|
||||
import { SqlOpsDataClient, ISqlOpsFeature } from 'dataprotocol-client';
|
||||
import * as constants from '../constants';
|
||||
import * as mssql from '../mssql';
|
||||
import * as Utils from '../utils';
|
||||
import { ClientCapabilities } from 'vscode-languageclient';
|
||||
import * as azdata from 'azdata';
|
||||
import * as contracts from '../contracts';
|
||||
|
||||
export class SchemaCompareService implements mssql.ISchemaCompareService {
|
||||
public static asFeature(context: AppContext): ISqlOpsFeature {
|
||||
return class extends SchemaCompareService {
|
||||
constructor(client: SqlOpsDataClient) {
|
||||
super(context, client);
|
||||
}
|
||||
|
||||
fillClientCapabilities(capabilities: ClientCapabilities): void {
|
||||
Utils.ensure(capabilities, 'schemaCompare')!.schemaCompare = true;
|
||||
}
|
||||
|
||||
initialize(): void {
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private constructor(context: AppContext, protected readonly client: SqlOpsDataClient) {
|
||||
context.registerService(constants.SchemaCompareService, this);
|
||||
}
|
||||
|
||||
public schemaCompare(operationId: string, sourceEndpointInfo: mssql.SchemaCompareEndpointInfo, targetEndpointInfo: mssql.SchemaCompareEndpointInfo, taskExecutionMode: azdata.TaskExecutionMode, deploymentOptions: mssql.DeploymentOptions): Thenable<mssql.SchemaCompareResult> {
|
||||
const params: contracts.SchemaCompareParams = { operationId: operationId, sourceEndpointInfo: sourceEndpointInfo, targetEndpointInfo: targetEndpointInfo, taskExecutionMode: taskExecutionMode, deploymentOptions: deploymentOptions };
|
||||
return this.client.sendRequest(contracts.SchemaCompareRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaCompareRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public schemaCompareGenerateScript(operationId: string, targetServerName: string, targetDatabaseName: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus> {
|
||||
const params: contracts.SchemaCompareGenerateScriptParams = { operationId: operationId, targetServerName: targetServerName, targetDatabaseName: targetDatabaseName, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.SchemaCompareGenerateScriptRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaCompareGenerateScriptRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public schemaComparePublishChanges(operationId: string, targetServerName: string, targetDatabaseName: string, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus> {
|
||||
const params: contracts.SchemaComparePublishChangesParams = { operationId: operationId, targetServerName: targetServerName, targetDatabaseName: targetDatabaseName, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.SchemaComparePublishChangesRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaComparePublishChangesRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public schemaCompareGetDefaultOptions(): Thenable<mssql.SchemaCompareOptionsResult> {
|
||||
const params: contracts.SchemaCompareGetOptionsParams = {};
|
||||
return this.client.sendRequest(contracts.SchemaCompareGetDefaultOptionsRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaCompareGetDefaultOptionsRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public schemaCompareIncludeExcludeNode(operationId: string, diffEntry: mssql.DiffEntry, includeRequest: boolean, taskExecutionMode: azdata.TaskExecutionMode): Thenable<azdata.ResultStatus> {
|
||||
const params: contracts.SchemaCompareNodeParams = { operationId: operationId, diffEntry, includeRequest, taskExecutionMode: taskExecutionMode };
|
||||
return this.client.sendRequest(contracts.SchemaCompareIncludeExcludeNodeRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaCompareIncludeExcludeNodeRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public schemaCompareOpenScmp(filePath: string): Thenable<mssql.SchemaCompareOpenScmpResult> {
|
||||
const params: contracts.SchemaCompareOpenScmpParams = { filePath: filePath };
|
||||
return this.client.sendRequest(contracts.SchemaCompareOpenScmpRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaCompareOpenScmpRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public schemaCompareSaveScmp(sourceEndpointInfo: mssql.SchemaCompareEndpointInfo, targetEndpointInfo: mssql.SchemaCompareEndpointInfo, taskExecutionMode: azdata.TaskExecutionMode, deploymentOptions: mssql.DeploymentOptions, scmpFilePath: string, excludedSourceObjects: mssql.SchemaCompareObjectId[], excludedTargetObjects: mssql.SchemaCompareObjectId[]): Thenable<azdata.ResultStatus> {
|
||||
const params: contracts.SchemaCompareSaveScmpParams = { sourceEndpointInfo: sourceEndpointInfo, targetEndpointInfo: targetEndpointInfo, taskExecutionMode: taskExecutionMode, deploymentOptions: deploymentOptions, scmpFilePath: scmpFilePath, excludedSourceObjects: excludedSourceObjects, excludedTargetObjects: excludedTargetObjects };
|
||||
return this.client.sendRequest(contracts.SchemaCompareSaveScmpRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaCompareSaveScmpRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public schemaCompareCancel(operationId: string): Thenable<azdata.ResultStatus> {
|
||||
const params: contracts.SchemaCompareCancelParams = { operationId: operationId };
|
||||
return this.client.sendRequest(contracts.SchemaCompareCancellationRequest.type, params).then(
|
||||
undefined,
|
||||
e => {
|
||||
this.client.logFailedRequest(contracts.SchemaCompareCancellationRequest.type, e);
|
||||
return Promise.resolve(undefined);
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
175
extensions/mssql/src/sqlToolsServer.ts
Normal file
175
extensions/mssql/src/sqlToolsServer.ts
Normal file
@@ -0,0 +1,175 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { ServerProvider, IConfig, Events } from 'service-downloader';
|
||||
import { ServerOptions, TransportKind } from 'vscode-languageclient';
|
||||
import * as Constants from './constants';
|
||||
import * as vscode from 'vscode';
|
||||
import * as path from 'path';
|
||||
import { getCommonLaunchArgsAndCleanupOldLogFiles } from './utils';
|
||||
import { localize } from './localize';
|
||||
import { Telemetry, LanguageClientErrorHandler } from './telemetry';
|
||||
import { SqlOpsDataClient, ClientOptions } from 'dataprotocol-client';
|
||||
import { TelemetryFeature, AgentServicesFeature, SerializationFeature } from './features';
|
||||
import { CredentialStore } from './credentialstore/credentialstore';
|
||||
import { AzureResourceProvider } from './resourceProvider/resourceProvider';
|
||||
import { SchemaCompareService } from './schemaCompare/schemaCompareService';
|
||||
import { AppContext } from './appContext';
|
||||
import { DacFxService } from './dacfx/dacFxService';
|
||||
import { CmsService } from './cms/cmsService';
|
||||
|
||||
const baseConfig = require('./config.json');
|
||||
|
||||
const outputChannel = vscode.window.createOutputChannel(Constants.serviceName);
|
||||
const statusView = vscode.window.createStatusBarItem(vscode.StatusBarAlignment.Left);
|
||||
|
||||
export class SqlToolsServer {
|
||||
|
||||
private client: SqlOpsDataClient;
|
||||
private config: IConfig;
|
||||
private disposables = new Array<{ dispose: () => void }>();
|
||||
|
||||
public async start(context: AppContext): Promise<SqlOpsDataClient> {
|
||||
try {
|
||||
const installationStart = Date.now();
|
||||
const path = await this.download();
|
||||
const installationComplete = Date.now();
|
||||
let serverOptions = generateServerOptions(context.extensionContext.logPath, path);
|
||||
let clientOptions = getClientOptions(context);
|
||||
this.client = new SqlOpsDataClient(Constants.serviceName, serverOptions, clientOptions);
|
||||
const processStart = Date.now();
|
||||
this.client.onReady().then(() => {
|
||||
const processEnd = Date.now();
|
||||
statusView.text = 'Service Started';
|
||||
setTimeout(() => {
|
||||
statusView.hide();
|
||||
}, 1500);
|
||||
Telemetry.sendTelemetryEvent('startup/LanguageClientStarted', {
|
||||
installationTime: String(installationComplete - installationStart),
|
||||
processStartupTime: String(processEnd - processStart),
|
||||
totalTime: String(processEnd - installationStart),
|
||||
beginningTimestamp: String(installationStart)
|
||||
});
|
||||
});
|
||||
statusView.show();
|
||||
statusView.text = 'Starting service';
|
||||
this.client.start();
|
||||
await this.activateFeatures(context);
|
||||
return this.client;
|
||||
} catch (e) {
|
||||
Telemetry.sendTelemetryEvent('ServiceInitializingFailed');
|
||||
vscode.window.showErrorMessage('Failed to start Sql tools service');
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
|
||||
private download() {
|
||||
this.config = JSON.parse(JSON.stringify(baseConfig));
|
||||
this.config.installDirectory = path.join(__dirname, this.config.installDirectory);
|
||||
this.config.proxy = vscode.workspace.getConfiguration('http').get('proxy');
|
||||
this.config.strictSSL = vscode.workspace.getConfiguration('http').get('proxyStrictSSL') || true;
|
||||
|
||||
const serverdownloader = new ServerProvider(this.config);
|
||||
serverdownloader.eventEmitter.onAny(generateHandleServerProviderEvent());
|
||||
return serverdownloader.getOrDownloadServer();
|
||||
}
|
||||
|
||||
private activateFeatures(context: AppContext): Promise<void> {
|
||||
const credsStore = new CredentialStore(context.extensionContext.logPath, this.config);
|
||||
const resourceProvider = new AzureResourceProvider(context.extensionContext.logPath, this.config);
|
||||
this.disposables.push(credsStore);
|
||||
this.disposables.push(resourceProvider);
|
||||
return Promise.all([credsStore.start(), resourceProvider.start()]).then();
|
||||
}
|
||||
|
||||
dispose() {
|
||||
this.disposables.forEach(d => d.dispose());
|
||||
if (this.client) {
|
||||
this.client.stop();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function generateServerOptions(logPath: string, executablePath: string): ServerOptions {
|
||||
const launchArgs = getCommonLaunchArgsAndCleanupOldLogFiles(logPath, 'sqltools.log', executablePath);
|
||||
return { command: executablePath, args: launchArgs, transport: TransportKind.stdio };
|
||||
}
|
||||
|
||||
function generateHandleServerProviderEvent() {
|
||||
let dots = 0;
|
||||
return (e: string, ...args: any[]) => {
|
||||
switch (e) {
|
||||
case Events.INSTALL_START:
|
||||
outputChannel.show(true);
|
||||
statusView.show();
|
||||
outputChannel.appendLine(localize('installingServiceChannelMsg', 'Installing {0} service to {1}', Constants.serviceName, args[0]));
|
||||
statusView.text = localize('installingServiceStatusMsg', 'Installing Service');
|
||||
break;
|
||||
case Events.INSTALL_END:
|
||||
outputChannel.appendLine(localize('installedServiceChannelMsg', 'Installed'));
|
||||
break;
|
||||
case Events.DOWNLOAD_START:
|
||||
outputChannel.appendLine(localize('downloadingServiceChannelMsg', 'Downloading {0}', args[0]));
|
||||
outputChannel.append(localize('downloadingServiceSizeChannelMsg', '({0} KB)', Math.ceil(args[1] / 1024).toLocaleString(vscode.env.language)));
|
||||
statusView.text = localize('downloadingServiceStatusMsg', 'Downloading Service');
|
||||
break;
|
||||
case Events.DOWNLOAD_PROGRESS:
|
||||
let newDots = Math.ceil(args[0] / 5);
|
||||
if (newDots > dots) {
|
||||
outputChannel.append('.'.repeat(newDots - dots));
|
||||
dots = newDots;
|
||||
}
|
||||
break;
|
||||
case Events.DOWNLOAD_END:
|
||||
outputChannel.appendLine(localize('downloadServiceDoneChannelMsg', 'Done!'));
|
||||
break;
|
||||
default:
|
||||
console.error(`Unknown event from Server Provider ${e}`);
|
||||
break;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
function getClientOptions(context: AppContext): ClientOptions {
|
||||
return {
|
||||
documentSelector: ['sql'],
|
||||
synchronize: {
|
||||
configurationSection: Constants.extensionConfigSectionName
|
||||
},
|
||||
providerId: Constants.providerId,
|
||||
errorHandler: new LanguageClientErrorHandler(),
|
||||
features: [
|
||||
// we only want to add new features
|
||||
...SqlOpsDataClient.defaultFeatures,
|
||||
TelemetryFeature,
|
||||
AgentServicesFeature,
|
||||
SerializationFeature,
|
||||
SchemaCompareService.asFeature(context),
|
||||
DacFxService.asFeature(context),
|
||||
CmsService.asFeature(context)
|
||||
],
|
||||
outputChannel: new CustomOutputChannel()
|
||||
};
|
||||
}
|
||||
|
||||
class CustomOutputChannel implements vscode.OutputChannel {
|
||||
name: string;
|
||||
append(value: string): void {
|
||||
console.log(value);
|
||||
}
|
||||
appendLine(value: string): void {
|
||||
console.log(value);
|
||||
}
|
||||
clear(): void {
|
||||
}
|
||||
show(preserveFocus?: boolean): void;
|
||||
show(column?: vscode.ViewColumn, preserveFocus?: boolean): void;
|
||||
show(column?: any, preserveFocus?: any) {
|
||||
}
|
||||
hide(): void {
|
||||
}
|
||||
dispose(): void {
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user