Update arc api (#11932)

This commit is contained in:
Charles Gagnon
2020-08-23 07:23:14 -07:00
committed by GitHub
parent d8f9cdeacb
commit d96e83c3f0
7 changed files with 240 additions and 146 deletions

View File

@@ -80,7 +80,7 @@ export class ControllerModel {
}
}
await this._azdataApi.login(this.info.url, this.info.username, this._password);
await this._azdataApi.azdata.login(this.info.url, this.info.username, this._password);
}
/**
@@ -98,7 +98,7 @@ export class ControllerModel {
await this.azdataLogin(promptReconnect);
this._registrations = [];
await Promise.all([
this._azdataApi.dc.config.show().then(result => {
this._azdataApi.azdata.arc.dc.config.show().then(result => {
this._controllerConfig = result.result;
this.configLastUpdated = new Date();
this._onConfigUpdated.fire(this._controllerConfig);
@@ -112,7 +112,7 @@ export class ControllerModel {
this._onConfigUpdated.fire(this._controllerConfig);
throw err;
}),
this._azdataApi.dc.endpoint.list().then(result => {
this._azdataApi.azdata.arc.dc.endpoint.list().then(result => {
this._endpoints = result.result;
this.endpointsLastUpdated = new Date();
this._onEndpointsUpdated.fire(this._endpoints);
@@ -127,7 +127,7 @@ export class ControllerModel {
throw err;
}),
Promise.all([
this._azdataApi.postgres.server.list().then(result => {
this._azdataApi.azdata.arc.postgres.server.list().then(result => {
this._registrations.push(...result.result.map(r => {
return {
instanceName: r.name,
@@ -136,7 +136,7 @@ export class ControllerModel {
};
}));
}),
this._azdataApi.sql.mi.list().then(result => {
this._azdataApi.azdata.arc.sql.mi.list().then(result => {
this._registrations.push(...result.result.map(r => {
return {
instanceName: r.name,

View File

@@ -74,7 +74,7 @@ export class MiaaModel extends ResourceModel {
this._refreshPromise = new Deferred();
try {
await this._controllerModel.azdataLogin();
const instanceRefresh = this._azdataApi.sql.mi.show(this.info.name).then(result => {
const instanceRefresh = this._azdataApi.azdata.arc.sql.mi.show(this.info.name).then(result => {
this._config = result.result;
this.configLastUpdated = new Date();
this._onConfigUpdated.fire(this._config);

View File

@@ -188,7 +188,7 @@ export class MiaaDashboardOverviewPage extends DashboardPage {
deleteButton.enabled = false;
try {
if (await promptForResourceDeletion(this._miaaModel.info.name)) {
await this._azdataApi.sql.mi.delete(this._miaaModel.info.name);
await this._azdataApi.azdata.arc.sql.mi.delete(this._miaaModel.info.name);
await this._controllerModel.refreshTreeNode();
vscode.window.showInformationMessage(loc.resourceDeleted(this._miaaModel.info.name));
}

View File

@@ -3,32 +3,99 @@
* Licensed under the Source EULA. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
import { AzdataOutput } from 'azdata-ext';
import * as os from 'os';
import * as vscode from 'vscode';
import { HttpClient } from './common/httpClient';
import * as loc from './localizedConstants';
import { executeCommand, executeSudoCommand, ExitCodeError } from './common/childProcess';
import { searchForCmd } from './common/utils';
import * as azdataExt from 'azdata-ext';
export const azdataHostname = 'https://aka.ms';
export const azdataUri = 'azdata-msi';
export interface IAzdataTool {
export interface IAzdataTool extends azdataExt.IAzdataApi {
path: string,
version: string,
toolVersion: string,
/**
* Executes azdata with the specified arguments (e.g. --version) and returns the result
* @param args The args to pass to azdata
* @param parseResult A function used to parse out the raw result into the desired shape
*/
executeCommand<R>(args: string[], additionalEnvVars?: { [key: string]: string }): Promise<AzdataOutput<R>>
executeCommand<R>(args: string[], additionalEnvVars?: { [key: string]: string }): Promise<azdataExt.AzdataOutput<R>>
}
class AzdataTool implements IAzdataTool {
constructor(public path: string, public version: string, private _outputChannel: vscode.OutputChannel) { }
constructor(public path: string, public toolVersion: string, private _outputChannel: vscode.OutputChannel) { }
public async executeCommand<R>(args: string[], additionalEnvVars?: { [key: string]: string }): Promise<AzdataOutput<R>> {
public arc = {
dc: {
create: async (namespace: string, name: string, connectivityMode: string, resourceGroup: string, location: string, subscription: string, profileName?: string, storageClass?: string): Promise<azdataExt.AzdataOutput<void>> => {
const args = ['arc', 'dc', 'create',
'--namespace', namespace,
'--name', name,
'--connectivity-mode', connectivityMode,
'--resource-group', resourceGroup,
'--location', location,
'--subscription', subscription];
if (profileName) {
args.push('--profile-name', profileName);
}
if (storageClass) {
args.push('--storage-class', storageClass);
}
return this.executeCommand<void>(args);
},
endpoint: {
list: async () => {
return this.executeCommand<azdataExt.DcEndpointListResult[]>(['arc', 'dc', 'endpoint', 'list']);
}
},
config: {
list: async () => {
return this.executeCommand<azdataExt.DcConfigListResult[]>(['arc', 'dc', 'config', 'list']);
},
show: async () => {
return this.executeCommand<azdataExt.DcConfigShowResult>(['arc', 'dc', 'config', 'show']);
}
}
},
postgres: {
server: {
list: async () => {
return this.executeCommand<azdataExt.PostgresServerListResult[]>(['arc', 'postgres', 'server', 'list']);
},
show: async (name: string) => {
return this.executeCommand<azdataExt.PostgresServerShowResult>(['arc', 'postgres', 'server', 'show', '-n', name]);
}
}
},
sql: {
mi: {
delete: async (name: string) => {
return this.executeCommand<void>(['arc', 'sql', 'mi', 'delete', '-n', name]);
},
list: async () => {
return this.executeCommand<azdataExt.SqlMiListResult[]>(['arc', 'sql', 'mi', 'list']);
},
show: async (name: string) => {
return this.executeCommand<azdataExt.SqlMiShowResult>(['arc', 'sql', 'mi', 'show', '-n', name]);
}
}
}
};
public async login(endpoint: string, username: string, password: string): Promise<azdataExt.AzdataOutput<void>> {
return this.executeCommand<void>(['login', '-e', endpoint, '-u', username], { 'AZDATA_PASSWORD': password });
}
public async version(): Promise<azdataExt.AzdataOutput<string>> {
const output = await this.executeCommand<string>(['--version']);
this.toolVersion = parseVersion(output.stdout[0]);
return output;
}
public async executeCommand<R>(args: string[], additionalEnvVars?: { [key: string]: string }): Promise<azdataExt.AzdataOutput<R>> {
try {
const output = JSON.parse((await executeCommand(`"${this.path}"`, args.concat(['--output', 'json']), this._outputChannel, additionalEnvVars)).stdout);
return {
@@ -65,7 +132,7 @@ export async function findAzdata(outputChannel: vscode.OutputChannel): Promise<I
default:
azdata = await findSpecificAzdata('azdata', outputChannel);
}
outputChannel.appendLine(loc.foundExistingAzdata(azdata.path, azdata.version));
outputChannel.appendLine(loc.foundExistingAzdata(azdata.path, azdata.toolVersion));
return azdata;
} catch (err) {
outputChannel.appendLine(loc.couldNotFindAzdata(err));

View File

@@ -6,6 +6,7 @@
import * as azdataExt from 'azdata-ext';
import * as vscode from 'vscode';
import { findAzdata, IAzdataTool } from './azdata';
import * as loc from './localizedConstants';
let localAzdata: IAzdataTool | undefined = undefined;
@@ -13,52 +14,75 @@ export async function activate(): Promise<azdataExt.IExtension> {
const outputChannel = vscode.window.createOutputChannel('azdata');
localAzdata = await checkForAzdata(outputChannel);
return {
dc: {
endpoint: {
list: async () => {
return executeLocalAzdataCommand(['arc', 'dc', 'endpoint', 'list']);
azdata: {
arc: {
dc: {
create: async (namespace: string, name: string, connectivityMode: string, resourceGroup: string, location: string, subscription: string, profileName?: string, storageClass?: string) => {
throwIfNoAzdata();
return localAzdata!.arc.dc.create(namespace, name, connectivityMode, resourceGroup, location, subscription, profileName, storageClass);
},
endpoint: {
list: async () => {
throwIfNoAzdata();
return localAzdata!.arc.dc.endpoint.list();
}
},
config: {
list: async () => {
throwIfNoAzdata();
return localAzdata!.arc.dc.config.list();
},
show: async () => {
throwIfNoAzdata();
return localAzdata!.arc.dc.config.show();
}
}
},
postgres: {
server: {
list: async () => {
throwIfNoAzdata();
return localAzdata!.arc.postgres.server.list();
},
show: async (name: string) => {
throwIfNoAzdata();
return localAzdata!.arc.postgres.server.show(name);
}
}
},
sql: {
mi: {
delete: async (name: string) => {
throwIfNoAzdata();
return localAzdata!.arc.sql.mi.delete(name);
},
list: async () => {
throwIfNoAzdata();
return localAzdata!.arc.sql.mi.list();
},
show: async (name: string) => {
throwIfNoAzdata();
return localAzdata!.arc.sql.mi.show(name);
}
}
}
},
config: {
show: async () => {
return executeLocalAzdataCommand(['arc', 'dc', 'config', 'show']);
}
}
},
login: async (endpoint: string, username: string, password: string) => {
return executeLocalAzdataCommand(['login', '-e', endpoint, '-u', username], { 'AZDATA_PASSWORD': password });
},
postgres: {
server: {
list: async () => {
return executeLocalAzdataCommand(['arc', 'postgres', 'server', 'list']);
},
show: async (name: string) => {
return executeLocalAzdataCommand(['arc', 'postgres', 'server', 'show', '-n', name]);
}
}
},
sql: {
mi: {
delete: async (name: string) => {
return executeLocalAzdataCommand(['arc', 'sql', 'mi', 'delete', '-n', name]);
},
list: async () => {
return executeLocalAzdataCommand(['arc', 'sql', 'mi', 'list']);
},
show: async (name: string) => {
return executeLocalAzdataCommand(['arc', 'sql', 'mi', 'show', '-n', name]);
}
login: async (endpoint: string, username: string, password: string) => {
throwIfNoAzdata();
return localAzdata!.login(endpoint, username, password);
},
version: async () => {
throwIfNoAzdata();
return localAzdata!.version();
}
}
};
}
async function executeLocalAzdataCommand<R>(args: string[], additionalEnvVars?: { [key: string]: string }): Promise<azdataExt.AzdataOutput<R>> {
function throwIfNoAzdata(): void {
if (!localAzdata) {
throw new Error('No azdata');
throw new Error(loc.noAzdata);
}
return localAzdata.executeCommand(args, additionalEnvVars);
}
async function checkForAzdata(outputChannel: vscode.OutputChannel): Promise<IAzdataTool | undefined> {

View File

@@ -28,3 +28,4 @@ export function installError(err: any): string { return localize('azdata.install
export function platformUnsupported(platform: string): string { return localize('azdata.platformUnsupported', "Platform '{0}' is currently unsupported", platform); }
export function unexpectedCommandError(errMsg: string): string { return localize('azdata.unexpectedCommandError', "Unexpected error executing command : {0}", errMsg); }
export function unexpectedExitCode(code: number, err: string): string { return localize('azdata.unexpectedExitCode', "Unexpected exit code from command : {1} ({0})", code, err); }
export const noAzdata = localize('azdata.NoAzdata', "No azdata available");

View File

@@ -34,66 +34,68 @@ declare module 'azdata-ext' {
workers: number // 1
}
export type DcConfigListResult = string;
export interface DcConfigShowResult {
apiVersion: string, // "arcdata.microsoft.com/v1alpha1"
kind: string, // "DataController"
metadata: {
creationTimestamp: string, // "2020-08-19T17:05:39Z"
generation: number, // /1
name: string, // "arc"
namespace: string, // "arc"
resourceVersion: string, // "200369"
selfLink: string, // "/apis/arcdata.microsoft.com/v1alpha1/namespaces/arc/datacontrollers/arc"
uid: string// "da72ed34-ee51-4bf0-b5c9-b0753834c5c1"
creationTimestamp: string, // "2020-08-19T17:05:39Z"
generation: number, // /1
name: string, // "arc"
namespace: string, // "arc"
resourceVersion: string, // "200369"
selfLink: string, // "/apis/arcdata.microsoft.com/v1alpha1/namespaces/arc/datacontrollers/arc"
uid: string// "da72ed34-ee51-4bf0-b5c9-b0753834c5c1"
},
spec: {
credentials: {
controllerAdmin: string, // "controller-login-secret"
dockerRegistry: string, // "mssql-private-registry"
serviceAccount: string, // "sa-mssql-controller"
},
docker: {
imagePullPolicy: string, // "Always"
imageTag: string, // "15.0.2000.41811_5"
registry: string, // "hlsaris.azurecr.io"
repository: string // "aris-p-master-dsmain-standard"
},
security: {
allowDumps: boolean, // true,
allowNodeMetricsCollection: boolean // true
allowPodMetricsCollection: boolean, // true
allowRunAsRoot: boolean // false
},
services: {
name: string, // "controller"
port: number, // 30080
serviceType: string // "NodePort"
}[],
settings: {
ElasticSearch: {
'vm.max_map_count': string // "-1"
credentials: {
controllerAdmin: string, // "controller-login-secret"
dockerRegistry: string, // "mssql-private-registry"
serviceAccount: string, // "sa-mssql-controller"
},
controller: {
'enableBilling': string, // "True"
'logs.rotation.days': string, // "7"
'logs.rotation.size': string, // "5000"
}
},
storage: {
data: {
accessMode: string, // "ReadWriteOnce"
className: string, // "local-storage"
size: string, // "15Gi"
docker: {
imagePullPolicy: string, // "Always"
imageTag: string, // "15.0.2000.41811_5"
registry: string, // "hlsaris.azurecr.io"
repository: string // "aris-p-master-dsmain-standard"
},
logs: {
accessMode: string, // "ReadWriteOnce"
className: string, // "local-storage"
size: string, // "10Gi"
security: {
allowDumps: boolean, // true,
allowNodeMetricsCollection: boolean // true
allowPodMetricsCollection: boolean, // true
allowRunAsRoot: boolean // false
},
services: {
name: string, // "controller"
port: number, // 30080
serviceType: string // "NodePort"
}[],
settings: {
ElasticSearch: {
'vm.max_map_count': string // "-1"
},
controller: {
'enableBilling': string, // "True"
'logs.rotation.days': string, // "7"
'logs.rotation.size': string, // "5000"
}
},
storage: {
data: {
accessMode: string, // "ReadWriteOnce"
className: string, // "local-storage"
size: string, // "15Gi"
},
logs: {
accessMode: string, // "ReadWriteOnce"
className: string, // "local-storage"
size: string, // "10Gi"
}
}
}
},
status: {
state: string, // "Ready"
state: string, // "Ready"
}
}
@@ -127,6 +129,20 @@ declare module 'azdata-ext' {
}
}
export interface PostgresServerShowResult {
apiVersion: string, // "arcdata.microsoft.com/v1alpha1"
kind: string, // "postgresql-12"
metadata: {
creationTimestamp: string, // "2020-08-19T20:25:11Z"
generation: number, // 1
name: string, // "chgagnon-pg"
namespace: string, // "arc",
resourceVersion: string, // "214944",
selfLink: string, // "/apis/arcdata.microsoft.com/v1alpha1/namespaces/arc/postgresql-12s/chgagnon-pg",
uid: string, // "26d0f5bb-0c0b-4225-a6b5-5be2bf6feac0"
}
}
export interface PostgresServerShowResult {
apiVersion: string, // "arcdata.microsoft.com/v1alpha1"
kind: string, // "postgresql-12"
@@ -155,32 +171,10 @@ declare module 'azdata-ext' {
}
]
},
scale: {
shards: number // 1
},
scheduling: {
default: {
resources: {
requests: {
memory: string, // "256Mi"
}
}
}
},
storage: {
data: {
className: string, // "local-storage",
size: string // "5Gi"
},
logs: {
className: string, // "local-storage",
size: string // "5Gi"
}
status: {
readyPods: string, // "1/1",
state: string // "Ready"
}
},
status: {
readyPods: string, // "1/1",
state: string // "Ready"
}
}
@@ -192,29 +186,37 @@ declare module 'azdata-ext' {
code?: number
}
export interface IExtension {
dc: {
endpoint: {
list(): Promise<AzdataOutput<DcEndpointListResult[]>>
export interface IAzdataApi {
arc: {
dc: {
create(namespace: string, name: string, connectivityMode: string, resourceGroup: string, location: string, subscription: string, profileName?: string, storageClass?: string): Promise<AzdataOutput<void>>,
endpoint: {
list(): Promise<AzdataOutput<DcEndpointListResult[]>>
},
config: {
list(): Promise<AzdataOutput<DcConfigListResult[]>>,
show(): Promise<AzdataOutput<DcConfigShowResult>>
}
},
config: {
show(): Promise<AzdataOutput<DcConfigShowResult>>
}
},
login(endpoint: string, username: string, password: string): Promise<AzdataOutput<void>>,
postgres: {
server: {
list(): Promise<AzdataOutput<PostgresServerListResult[]>>,
show(name: string): Promise<AzdataOutput<PostgresServerShowResult>>
}
},
sql: {
mi: {
delete(name: string): Promise<AzdataOutput<void>>,
list(): Promise<AzdataOutput<SqlMiListResult[]>>,
show(name: string): Promise<AzdataOutput<SqlMiShowResult>>
postgres: {
server: {
list(): Promise<AzdataOutput<PostgresServerListResult[]>>,
show(name: string): Promise<AzdataOutput<PostgresServerShowResult>>
}
},
sql: {
mi: {
delete(name: string): Promise<AzdataOutput<void>>,
list(): Promise<AzdataOutput<SqlMiListResult[]>>,
show(name: string): Promise<AzdataOutput<SqlMiShowResult>>
}
}
}
login(endpoint: string, username: string, password: string): Promise<AzdataOutput<any>>,
version(): Promise<AzdataOutput<string>>
}
export interface IExtension {
azdata: IAzdataApi;
}
}