diff --git a/components/gitpod-db/src/typeorm/entity/db-workspace-cluster.ts b/components/gitpod-db/src/typeorm/entity/db-workspace-cluster.ts index e85cb9b5fcfa57..33fa46e0e8b948 100644 --- a/components/gitpod-db/src/typeorm/entity/db-workspace-cluster.ts +++ b/components/gitpod-db/src/typeorm/entity/db-workspace-cluster.ts @@ -5,7 +5,7 @@ */ import { PrimaryColumn, Column, Entity, Index } from "typeorm"; -import { TLSConfig, WorkspaceCluster, WorkspaceClusterState } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; +import { AdmissionConstraint, TLSConfig, WorkspaceCluster, WorkspaceClusterState } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; import { ValueTransformer } from "typeorm/decorator/options/ValueTransformer"; @Entity() @@ -59,4 +59,27 @@ export class DBWorkspaceCluster implements WorkspaceCluster { @Column() govern: boolean; + + @Column({ + type: "simple-json", + transformer: (() => { + const defaultValue: AdmissionConstraint[] = []; + const jsonifiedDefault = JSON.stringify(defaultValue); + return { + to(value: any): any { + if (!value) { + return jsonifiedDefault; + } + return JSON.stringify(value); + }, + from(value: any): any { + if (value === jsonifiedDefault) { + return undefined; + } + return JSON.parse(value); + } + }; + })() + }) + admissionConstraints?: AdmissionConstraint[]; } \ No newline at end of file diff --git a/components/gitpod-db/src/typeorm/migration/1620209434733-AdmissionConstraints.ts b/components/gitpod-db/src/typeorm/migration/1620209434733-AdmissionConstraints.ts new file mode 100644 index 00000000000000..342bbe2ebbce00 --- /dev/null +++ b/components/gitpod-db/src/typeorm/migration/1620209434733-AdmissionConstraints.ts @@ -0,0 +1,23 @@ +/** + * Copyright (c) 2021 Gitpod GmbH. All rights reserved. + * Licensed under the GNU Affero General Public License (AGPL). + * See License-AGPL.txt in the project root for license information. + */ + +import {MigrationInterface, QueryRunner} from "typeorm"; +import { columnExists, tableExists } from "./helper/helper"; + +export class AdmissionConstraints1620209434733 implements MigrationInterface { + + public async up(queryRunner: QueryRunner): Promise { + if (await tableExists(queryRunner, "d_b_workspace_cluster")) { + if (!(await columnExists(queryRunner, "d_b_workspace_cluster", "admissionConstraints"))) { + await queryRunner.query("ALTER TABLE d_b_workspace_cluster ADD COLUMN admissionConstraints TEXT NOT NULL"); + } + } + } + + public async down(queryRunner: QueryRunner): Promise { + } + +} diff --git a/components/gitpod-db/src/typeorm/workspace-cluster-db-impl.ts b/components/gitpod-db/src/typeorm/workspace-cluster-db-impl.ts index d0a1e65437b65c..620229c0721329 100644 --- a/components/gitpod-db/src/typeorm/workspace-cluster-db-impl.ts +++ b/components/gitpod-db/src/typeorm/workspace-cluster-db-impl.ts @@ -9,7 +9,7 @@ import { TypeORM } from "./typeorm"; import { WorkspaceClusterDB } from "../workspace-cluster-db"; import { DBWorkspaceCluster } from "./entity/db-workspace-cluster"; -import { WorkspaceCluster, WorkspaceClusterFilter, WorkspaceClusterWoTls } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; +import { WorkspaceCluster, WorkspaceClusterFilter, WorkspaceClusterWoTLS } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; @injectable() export class WorkspaceClusterDBImpl implements WorkspaceClusterDB { @@ -40,14 +40,15 @@ import { WorkspaceCluster, WorkspaceClusterFilter, WorkspaceClusterWoTls } from } - async findFiltered(predicate: DeepPartial): Promise { - const prototype: WorkspaceClusterWoTls = { + async findFiltered(predicate: DeepPartial): Promise { + const prototype: WorkspaceClusterWoTLS = { name: "", url: "", score: 0, maxScore: 0, state: "available", govern: false, + admissionConstraints: [], }; const repo = await this.getRepo(); diff --git a/components/gitpod-protocol/src/permission.ts b/components/gitpod-protocol/src/permission.ts index 3f6eb68c5c6200..13c7e92596a381 100644 --- a/components/gitpod-protocol/src/permission.ts +++ b/components/gitpod-protocol/src/permission.ts @@ -14,7 +14,8 @@ export const Permissions = { "admin-users": undefined, "admin-workspaces": undefined, "admin-api": undefined, - "ide-settings": undefined + "ide-settings": undefined, + "new-workspace-cluster": undefined, }; export type PermissionName = keyof (typeof Permissions); export const Roles = {"devops": undefined, "viewer": undefined, "admin": undefined }; diff --git a/components/gitpod-protocol/src/workspace-cluster.ts b/components/gitpod-protocol/src/workspace-cluster.ts index 8dbcc22904ee24..2a430fb5b530c4 100644 --- a/components/gitpod-protocol/src/workspace-cluster.ts +++ b/components/gitpod-protocol/src/workspace-cluster.ts @@ -8,6 +8,7 @@ import * as fs from 'fs'; import { filePathTelepresenceAware } from './env'; import { DeepPartial } from "./util/deep-partial"; import { Without } from './util/without'; +import { PermissionName } from './permission'; export interface WorkspaceCluster { // Name of the workspace cluster. @@ -32,7 +33,11 @@ export interface WorkspaceCluster { // True if this bridge should control this cluster govern: boolean; + + // An optional set of constraints that limit who can start workspaces on the cluster + admissionConstraints?: AdmissionConstraint[]; } + export type WorkspaceClusterState = "available" | "cordoned" | "draining"; export interface TLSConfig { // the CA shared between client and server (base64 encoded) @@ -45,9 +50,14 @@ export interface TLSConfig { export namespace TLSConfig { export const loadFromBase64File = (path: string): string => fs.readFileSync(filePathTelepresenceAware(path)).toString("base64"); } -export type WorkspaceClusterWoTls = Without; +export type WorkspaceClusterWoTLS = Without; export type WorkspaceManagerConnectionInfo = Pick; +export type AdmissionConstraint = AdmissionConstraintFeaturePreview | AdmissionConstraintHasRole; +export type AdmissionConstraintFeaturePreview = { type: "has-feature-preview" }; +export type AdmissionConstraintHasRole = { type: "has-permission", permission: PermissionName }; + + export const WorkspaceClusterDB = Symbol("WorkspaceClusterDB"); export interface WorkspaceClusterDB { /** @@ -73,7 +83,7 @@ export interface WorkspaceClusterDB { * Lists all WorkspaceClusterWoTls for which the given predicate is true (does not return TLS for size/speed concerns) * @param predicate */ - findFiltered(predicate: DeepPartial): Promise; + findFiltered(predicate: DeepPartial): Promise; } export interface WorkspaceClusterFilter extends Pick { minScore: number; diff --git a/components/server/src/workspace/workspace-starter.ts b/components/server/src/workspace/workspace-starter.ts index 466c9ce4ad4658..04d2fdec650e23 100644 --- a/components/server/src/workspace/workspace-starter.ts +++ b/components/server/src/workspace/workspace-starter.ts @@ -156,7 +156,7 @@ export class WorkspaceStarter { startRequest.setServicePrefix(workspace.id); // tell the world we're starting this instance - const { manager, installation } = await this.clientProvider.getStartManager(); + const { manager, installation } = await this.clientProvider.getStartManager(user, workspace, instance); instance.status.phase = "pending"; instance.region = installation; await this.workspaceDb.trace({ span }).storeInstance(instance); diff --git a/components/ws-manager-api/typescript/mocha.opts b/components/ws-manager-api/typescript/mocha.opts new file mode 100644 index 00000000000000..33dbfa810d1530 --- /dev/null +++ b/components/ws-manager-api/typescript/mocha.opts @@ -0,0 +1,6 @@ +--require ts-node/register +--require reflect-metadata/Reflect +--require source-map-support/register +--reporter spec +--watch-extensions ts +--exit \ No newline at end of file diff --git a/components/ws-manager-api/typescript/package.json b/components/ws-manager-api/typescript/package.json index 863073fa2ad748..1badb9317ea22b 100644 --- a/components/ws-manager-api/typescript/package.json +++ b/components/ws-manager-api/typescript/package.json @@ -9,7 +9,8 @@ ], "scripts": { "build": "tsc && cp -f src/*.js src/*d.ts lib", - "watch": "leeway exec --package .:lib --transitive-dependencies --filter-type yarn --components --parallel -- tsc -w --preserveWatchOutput" + "watch": "leeway exec --package .:lib --transitive-dependencies --filter-type yarn --components --parallel -- tsc -w --preserveWatchOutput", + "test": "mocha --opts mocha.opts 'src/**/*.spec.ts'" }, "dependencies": { "@gitpod/content-service": "0.1.5", @@ -24,6 +25,8 @@ "@types/node": "^10", "grpc-tools": "^1.11.1", "grpc_tools_node_protoc_ts": "^5.2.1", - "typescript-formatter": "^7.2.2" + "typescript-formatter": "^7.2.2", + "@testdeck/mocha": "0.1.2", + "@types/chai": "^4.1.2" } } diff --git a/components/ws-manager-api/typescript/src/client-provider-source.ts b/components/ws-manager-api/typescript/src/client-provider-source.ts index 260f5769afa58c..416bf85c4d4096 100644 --- a/components/ws-manager-api/typescript/src/client-provider-source.ts +++ b/components/ws-manager-api/typescript/src/client-provider-source.ts @@ -4,14 +4,14 @@ * See License-AGPL.txt in the project root for license information. */ import { injectable, inject, multiInject } from 'inversify'; -import { TLSConfig, WorkspaceCluster, WorkspaceClusterDB, WorkspaceClusterWoTls } from '@gitpod/gitpod-protocol/lib/workspace-cluster'; +import { TLSConfig, WorkspaceCluster, WorkspaceClusterDB, WorkspaceClusterWoTLS } from '@gitpod/gitpod-protocol/lib/workspace-cluster'; import { log } from '@gitpod/gitpod-protocol/lib/util/logging'; export const WorkspaceManagerClientProviderSource = Symbol("WorkspaceManagerClientProviderSource"); export interface WorkspaceManagerClientProviderSource { getWorkspaceCluster(name: string): Promise; - getAllWorkspaceClusters(): Promise; + getAllWorkspaceClusters(): Promise; } @@ -23,7 +23,7 @@ export class WorkspaceManagerClientProviderEnvSource implements WorkspaceManager return this.clusters.find(m => m.name === name); } - public async getAllWorkspaceClusters(): Promise { + public async getAllWorkspaceClusters(): Promise { return this.clusters; } @@ -68,7 +68,7 @@ export class WorkspaceManagerClientProviderDBSource implements WorkspaceManagerC return await this.db.findByName(name); } - public async getAllWorkspaceClusters(): Promise { + public async getAllWorkspaceClusters(): Promise { return await this.db.findFiltered({}); } } @@ -88,8 +88,8 @@ export class WorkspaceManagerClientProviderCompositeSource implements WorkspaceM return undefined; } - async getAllWorkspaceClusters(): Promise { - const allClusters: Map = new Map(); + async getAllWorkspaceClusters(): Promise { + const allClusters: Map = new Map(); for (const source of this.sources) { const clusters = await source.getAllWorkspaceClusters(); for (const cluster of clusters) { @@ -99,7 +99,7 @@ export class WorkspaceManagerClientProviderCompositeSource implements WorkspaceM allClusters.set(cluster.name, cluster); } } - const result: WorkspaceClusterWoTls[] = []; + const result: WorkspaceClusterWoTLS[] = []; for (const [_, cluster] of allClusters) { result.push(cluster); } diff --git a/components/ws-manager-api/typescript/src/client-provider.spec.ts b/components/ws-manager-api/typescript/src/client-provider.spec.ts new file mode 100644 index 00000000000000..0e8c08112d5afe --- /dev/null +++ b/components/ws-manager-api/typescript/src/client-provider.spec.ts @@ -0,0 +1,72 @@ +/** + * Copyright (c) 2021 Gitpod GmbH. All rights reserved. + * Licensed under the GNU Affero General Public License (AGPL). + * See License-AGPL.txt in the project root for license information. + */ + +import "reflect-metadata"; + +import { Container } from 'inversify'; +import { suite, test } from "@testdeck/mocha"; +import * as chai from 'chai'; +import { WorkspaceManagerClientProvider } from "./client-provider"; +import { WorkspaceManagerClientProviderCompositeSource, WorkspaceManagerClientProviderSource } from "./client-provider-source"; +import { WorkspaceCluster, WorkspaceClusterWoTLS } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; +import { User, Workspace, WorkspaceInstance } from "@gitpod/gitpod-protocol"; +const expect = chai.expect; + +@suite +class TestClientProvider { + protected provider: WorkspaceManagerClientProvider; + + public before() { + const c = new Container(); + c.bind(WorkspaceManagerClientProvider).toSelf().inSingletonScope(); + c.bind(WorkspaceManagerClientProviderCompositeSource).toSelf().inSingletonScope(); + c.bind(WorkspaceManagerClientProviderSource).toDynamicValue((): WorkspaceManagerClientProviderSource => { + const cluster: WorkspaceCluster[] = [ + { name: "c1", govern: true, maxScore: 100, score: 0, state: "cordoned", url: "", admissionConstraints: [] }, + { name: "c2", govern: true, maxScore: 100, score: 50, state: "cordoned", url: "", admissionConstraints: [] }, + { name: "c3", govern: false, maxScore: 100, score: 50, state: "cordoned", url: "", admissionConstraints: [] }, + { name: "a1", govern: true, maxScore: 100, score: 0, state: "available", url: "", admissionConstraints: [] }, + { name: "a2", govern: true, maxScore: 100, score: 50, state: "available", url: "", admissionConstraints: [] }, + { name: "a3", govern: false, maxScore: 100, score: 50, state: "available", url: "", admissionConstraints: [] }, + { + name: "con1", govern: true, maxScore: 100, score: 0, state: "available", url: "", admissionConstraints: [ + { type: "has-feature-preview" }, + ] + }, + { + name: "con2", govern: true, maxScore: 100, score: 50, state: "available", url: "", admissionConstraints: [ + { type: "has-permission", permission: "new-workspace-cluster" }, + ] + }, + ]; + return { + getAllWorkspaceClusters: async () => { return cluster as WorkspaceClusterWoTLS[] }, + getWorkspaceCluster: async (name: string) => { + return cluster.find(c => c.name === name); + } + }; + }).inSingletonScope(); + this.provider = c.get(WorkspaceManagerClientProvider); + } + + @test + public async testGetStarterWorkspaceCluster() { + this.expectInstallations(["a1", "a2", "a3"], await this.provider.getAvailableStartCluster({} as User, {} as Workspace, {} as WorkspaceInstance)); + this.expectInstallations(["a1", "a2", "a3", "con1"], await this.provider.getAvailableStartCluster({ + additionalData: {featurePreview: true} + } as User, {} as Workspace, {} as WorkspaceInstance)); + this.expectInstallations(["a1", "a2", "a3", "con2"], await this.provider.getAvailableStartCluster({ + rolesOrPermissions: ["admin"] + } as User, {} as Workspace, {} as WorkspaceInstance)); + } + + private expectInstallations(expected: string[], actual: WorkspaceClusterWoTLS[]) { + expect(actual.map(e => e.name).sort()).to.be.eql(expected); + } + +} + +module.exports = new TestClientProvider() diff --git a/components/ws-manager-api/typescript/src/client-provider.ts b/components/ws-manager-api/typescript/src/client-provider.ts index fa7748ad8b3a6e..26c14206fee354 100644 --- a/components/ws-manager-api/typescript/src/client-provider.ts +++ b/components/ws-manager-api/typescript/src/client-provider.ts @@ -8,8 +8,8 @@ import * as grpc from "@grpc/grpc-js"; import { injectable, inject } from 'inversify'; import { WorkspaceManagerClient } from './core_grpc_pb'; import { PromisifiedWorkspaceManagerClient, linearBackoffStrategy } from "./promisified-client"; -import { Disposable } from "@gitpod/gitpod-protocol"; -import { WorkspaceClusterWoTls, WorkspaceManagerConnectionInfo } from '@gitpod/gitpod-protocol/lib/workspace-cluster'; +import { Disposable, User, Workspace, WorkspaceInstance } from "@gitpod/gitpod-protocol"; +import { WorkspaceClusterWoTLS, WorkspaceManagerConnectionInfo } from '@gitpod/gitpod-protocol/lib/workspace-cluster'; import { WorkspaceManagerClientProviderCompositeSource, WorkspaceManagerClientProviderSource } from "./client-provider-source"; import { log } from '@gitpod/gitpod-protocol/lib/util/logging'; @@ -28,10 +28,9 @@ export class WorkspaceManagerClientProvider implements Disposable { * * @returns The WorkspaceManagerClient that was chosen to start the next workspace with. */ - public async getStartManager(): Promise<{ manager: PromisifiedWorkspaceManagerClient, installation: string}> { - const allClusters = await this.source.getAllWorkspaceClusters(); - const availableClusters = allClusters.filter((c) => c.score >= 0 && c.govern && c.state === "available"); - const chosenCluster = chooseCluster(availableClusters); + public async getStartManager(user: User, workspace: Workspace, instance: WorkspaceInstance): Promise<{ manager: PromisifiedWorkspaceManagerClient, installation: string}> { + const availableCluster = await this.getAvailableStartCluster(user, workspace, instance); + const chosenCluster = chooseCluster(availableCluster); const client = await this.get(chosenCluster.name); return { manager: client, @@ -39,6 +38,12 @@ export class WorkspaceManagerClientProvider implements Disposable { }; } + public async getAvailableStartCluster(user: User, workspace: Workspace, instance: WorkspaceInstance): Promise { + const allClusters = await this.source.getAllWorkspaceClusters(); + const availableClusters = allClusters.filter(c => c.score >= 0 && c.state === "available").filter(admissionConstraintsFilter(user, workspace, instance)); + return availableClusters; + } + /** * @param name * @returns The WorkspaceManagerClient identified by the name. Throws an error if there is none. @@ -73,7 +78,7 @@ export class WorkspaceManagerClientProvider implements Disposable { /** * @returns All WorkspaceClusters (without TLS config) */ - public async getAllWorkspaceClusters(): Promise { + public async getAllWorkspaceClusters(): Promise { return this.source.getAllWorkspaceClusters(); } @@ -106,12 +111,12 @@ export class WorkspaceManagerClientProvider implements Disposable { * @param clusters * @returns The chosen cluster. Throws an error if there are 0 WorkspaceClusters to choose from. */ -function chooseCluster(availableCluster: WorkspaceClusterWoTls[]): WorkspaceClusterWoTls { +function chooseCluster(availableCluster: WorkspaceClusterWoTLS[]): WorkspaceClusterWoTLS { if (availableCluster.length === 0) { throw new Error("No cluster to choose from!"); } - const scoreFunc = (c: WorkspaceClusterWoTls): number => { + const scoreFunc = (c: WorkspaceClusterWoTLS): number => { let score = c.score; // here is the point where we may want to implement non-static approaches // clamp to maxScore @@ -134,4 +139,21 @@ function chooseCluster(availableCluster: WorkspaceClusterWoTls[]): WorkspaceClus } } return availableCluster[availableCluster.length - 1]; +} + +function admissionConstraintsFilter(user: User, workspace: Workspace, instance: WorkspaceInstance): (c: WorkspaceClusterWoTLS) => boolean { + return (c: WorkspaceClusterWoTLS) => { + if (!c.admissionConstraints) { + return true; + } + + return (c.admissionConstraints || []).every(con => { + switch (con.type) { + case "has-feature-preview": + return !!user.additionalData && !!user.additionalData.featurePreview; + case "has-permission": + return user.rolesOrPermissions?.includes(con.permission); + } + }); + }; } \ No newline at end of file diff --git a/components/ws-manager-bridge-api/cluster-service.proto b/components/ws-manager-bridge-api/cluster-service.proto index 2099d8aa71e85c..c3e07002d6f46b 100644 --- a/components/ws-manager-bridge-api/cluster-service.proto +++ b/components/ws-manager-bridge-api/cluster-service.proto @@ -20,6 +20,7 @@ message RegisterRequest { string url = 2; TlsConfig tls = 3; RegistrationHints hints = 4; + repeated AdmissionConstraint admission_constraints = 5; } message RegisterResponse {} @@ -36,6 +37,18 @@ message RegistrationHints { bool govern = 3; } +message AdmissionConstraint { + message FeaturePreview {} + message HasPermission { + string permission = 1; + } + + oneof constraint { + FeaturePreview has_feature_preview = 1; + HasPermission has_permission = 2; + } +} + enum Preferability { None = 0; Prefer = 1; @@ -49,6 +62,8 @@ message ClusterStatus { int32 score = 4; int32 max_score = 5; bool governed = 6; + repeated AdmissionConstraint admission_constraints = 7; + bool static = 8; } enum ClusterState { @@ -64,15 +79,25 @@ message UpdateRequest { int32 score = 2; int32 max_score = 3; bool cordoned = 4; + ModifyAdmissionConstraint admission_constraints = 5; } } +message ModifyAdmissionConstraint { + bool add = 1; + AdmissionConstraint constraint = 2; +} + message UpdateResponse {} -message DeregisterRequest { string name = 1; } +message DeregisterRequest { + string name = 1; +} message DeregisterResponse {} message ListRequest {} -message ListResponse { repeated ClusterStatus status = 1; } +message ListResponse { + repeated ClusterStatus status = 1; +} diff --git a/components/ws-manager-bridge-api/go/cluster-service.pb.go b/components/ws-manager-bridge-api/go/cluster-service.pb.go index 02c4b91e69cf22..10ade46db59ba5 100644 --- a/components/ws-manager-bridge-api/go/cluster-service.pb.go +++ b/components/ws-manager-bridge-api/go/cluster-service.pb.go @@ -130,10 +130,11 @@ type RegisterRequest struct { sizeCache protoimpl.SizeCache unknownFields protoimpl.UnknownFields - Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` - Url string `protobuf:"bytes,2,opt,name=url,proto3" json:"url,omitempty"` - Tls *TlsConfig `protobuf:"bytes,3,opt,name=tls,proto3" json:"tls,omitempty"` - Hints *RegistrationHints `protobuf:"bytes,4,opt,name=hints,proto3" json:"hints,omitempty"` + Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` + Url string `protobuf:"bytes,2,opt,name=url,proto3" json:"url,omitempty"` + Tls *TlsConfig `protobuf:"bytes,3,opt,name=tls,proto3" json:"tls,omitempty"` + Hints *RegistrationHints `protobuf:"bytes,4,opt,name=hints,proto3" json:"hints,omitempty"` + AdmissionConstraints []*AdmissionConstraint `protobuf:"bytes,5,rep,name=admission_constraints,json=admissionConstraints,proto3" json:"admission_constraints,omitempty"` } func (x *RegisterRequest) Reset() { @@ -196,6 +197,13 @@ func (x *RegisterRequest) GetHints() *RegistrationHints { return nil } +func (x *RegisterRequest) GetAdmissionConstraints() []*AdmissionConstraint { + if x != nil { + return x.AdmissionConstraints + } + return nil +} + type RegisterResponse struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache @@ -360,23 +368,105 @@ func (x *RegistrationHints) GetGovern() bool { return false } +type AdmissionConstraint struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + // Types that are assignable to Constraint: + // *AdmissionConstraint_HasFeaturePreview + // *AdmissionConstraint_HasPermission_ + Constraint isAdmissionConstraint_Constraint `protobuf_oneof:"constraint"` +} + +func (x *AdmissionConstraint) Reset() { + *x = AdmissionConstraint{} + if protoimpl.UnsafeEnabled { + mi := &file_cluster_service_proto_msgTypes[4] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *AdmissionConstraint) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*AdmissionConstraint) ProtoMessage() {} + +func (x *AdmissionConstraint) ProtoReflect() protoreflect.Message { + mi := &file_cluster_service_proto_msgTypes[4] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use AdmissionConstraint.ProtoReflect.Descriptor instead. +func (*AdmissionConstraint) Descriptor() ([]byte, []int) { + return file_cluster_service_proto_rawDescGZIP(), []int{4} +} + +func (m *AdmissionConstraint) GetConstraint() isAdmissionConstraint_Constraint { + if m != nil { + return m.Constraint + } + return nil +} + +func (x *AdmissionConstraint) GetHasFeaturePreview() *AdmissionConstraint_FeaturePreview { + if x, ok := x.GetConstraint().(*AdmissionConstraint_HasFeaturePreview); ok { + return x.HasFeaturePreview + } + return nil +} + +func (x *AdmissionConstraint) GetHasPermission() *AdmissionConstraint_HasPermission { + if x, ok := x.GetConstraint().(*AdmissionConstraint_HasPermission_); ok { + return x.HasPermission + } + return nil +} + +type isAdmissionConstraint_Constraint interface { + isAdmissionConstraint_Constraint() +} + +type AdmissionConstraint_HasFeaturePreview struct { + HasFeaturePreview *AdmissionConstraint_FeaturePreview `protobuf:"bytes,1,opt,name=has_feature_preview,json=hasFeaturePreview,proto3,oneof"` +} + +type AdmissionConstraint_HasPermission_ struct { + HasPermission *AdmissionConstraint_HasPermission `protobuf:"bytes,2,opt,name=has_permission,json=hasPermission,proto3,oneof"` +} + +func (*AdmissionConstraint_HasFeaturePreview) isAdmissionConstraint_Constraint() {} + +func (*AdmissionConstraint_HasPermission_) isAdmissionConstraint_Constraint() {} + type ClusterStatus struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache unknownFields protoimpl.UnknownFields - Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` - Url string `protobuf:"bytes,2,opt,name=url,proto3" json:"url,omitempty"` - State ClusterState `protobuf:"varint,3,opt,name=state,proto3,enum=workspacemanagerbridge.ClusterState" json:"state,omitempty"` - Score int32 `protobuf:"varint,4,opt,name=score,proto3" json:"score,omitempty"` - MaxScore int32 `protobuf:"varint,5,opt,name=max_score,json=maxScore,proto3" json:"max_score,omitempty"` - Governed bool `protobuf:"varint,6,opt,name=governed,proto3" json:"governed,omitempty"` + Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` + Url string `protobuf:"bytes,2,opt,name=url,proto3" json:"url,omitempty"` + State ClusterState `protobuf:"varint,3,opt,name=state,proto3,enum=workspacemanagerbridge.ClusterState" json:"state,omitempty"` + Score int32 `protobuf:"varint,4,opt,name=score,proto3" json:"score,omitempty"` + MaxScore int32 `protobuf:"varint,5,opt,name=max_score,json=maxScore,proto3" json:"max_score,omitempty"` + Governed bool `protobuf:"varint,6,opt,name=governed,proto3" json:"governed,omitempty"` + AdmissionConstraints []*AdmissionConstraint `protobuf:"bytes,7,rep,name=admission_constraints,json=admissionConstraints,proto3" json:"admission_constraints,omitempty"` + Static bool `protobuf:"varint,8,opt,name=static,proto3" json:"static,omitempty"` } func (x *ClusterStatus) Reset() { *x = ClusterStatus{} if protoimpl.UnsafeEnabled { - mi := &file_cluster_service_proto_msgTypes[4] + mi := &file_cluster_service_proto_msgTypes[5] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -389,7 +479,7 @@ func (x *ClusterStatus) String() string { func (*ClusterStatus) ProtoMessage() {} func (x *ClusterStatus) ProtoReflect() protoreflect.Message { - mi := &file_cluster_service_proto_msgTypes[4] + mi := &file_cluster_service_proto_msgTypes[5] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -402,7 +492,7 @@ func (x *ClusterStatus) ProtoReflect() protoreflect.Message { // Deprecated: Use ClusterStatus.ProtoReflect.Descriptor instead. func (*ClusterStatus) Descriptor() ([]byte, []int) { - return file_cluster_service_proto_rawDescGZIP(), []int{4} + return file_cluster_service_proto_rawDescGZIP(), []int{5} } func (x *ClusterStatus) GetName() string { @@ -447,6 +537,20 @@ func (x *ClusterStatus) GetGoverned() bool { return false } +func (x *ClusterStatus) GetAdmissionConstraints() []*AdmissionConstraint { + if x != nil { + return x.AdmissionConstraints + } + return nil +} + +func (x *ClusterStatus) GetStatic() bool { + if x != nil { + return x.Static + } + return false +} + type UpdateRequest struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache @@ -457,13 +561,14 @@ type UpdateRequest struct { // *UpdateRequest_Score // *UpdateRequest_MaxScore // *UpdateRequest_Cordoned + // *UpdateRequest_AdmissionConstraints Property isUpdateRequest_Property `protobuf_oneof:"property"` } func (x *UpdateRequest) Reset() { *x = UpdateRequest{} if protoimpl.UnsafeEnabled { - mi := &file_cluster_service_proto_msgTypes[5] + mi := &file_cluster_service_proto_msgTypes[6] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -476,7 +581,7 @@ func (x *UpdateRequest) String() string { func (*UpdateRequest) ProtoMessage() {} func (x *UpdateRequest) ProtoReflect() protoreflect.Message { - mi := &file_cluster_service_proto_msgTypes[5] + mi := &file_cluster_service_proto_msgTypes[6] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -489,7 +594,7 @@ func (x *UpdateRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use UpdateRequest.ProtoReflect.Descriptor instead. func (*UpdateRequest) Descriptor() ([]byte, []int) { - return file_cluster_service_proto_rawDescGZIP(), []int{5} + return file_cluster_service_proto_rawDescGZIP(), []int{6} } func (x *UpdateRequest) GetName() string { @@ -527,6 +632,13 @@ func (x *UpdateRequest) GetCordoned() bool { return false } +func (x *UpdateRequest) GetAdmissionConstraints() *ModifyAdmissionConstraint { + if x, ok := x.GetProperty().(*UpdateRequest_AdmissionConstraints); ok { + return x.AdmissionConstraints + } + return nil +} + type isUpdateRequest_Property interface { isUpdateRequest_Property() } @@ -543,12 +655,73 @@ type UpdateRequest_Cordoned struct { Cordoned bool `protobuf:"varint,4,opt,name=cordoned,proto3,oneof"` } +type UpdateRequest_AdmissionConstraints struct { + AdmissionConstraints *ModifyAdmissionConstraint `protobuf:"bytes,5,opt,name=admission_constraints,json=admissionConstraints,proto3,oneof"` +} + func (*UpdateRequest_Score) isUpdateRequest_Property() {} func (*UpdateRequest_MaxScore) isUpdateRequest_Property() {} func (*UpdateRequest_Cordoned) isUpdateRequest_Property() {} +func (*UpdateRequest_AdmissionConstraints) isUpdateRequest_Property() {} + +type ModifyAdmissionConstraint struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Add bool `protobuf:"varint,1,opt,name=add,proto3" json:"add,omitempty"` + Constraint *AdmissionConstraint `protobuf:"bytes,2,opt,name=constraint,proto3" json:"constraint,omitempty"` +} + +func (x *ModifyAdmissionConstraint) Reset() { + *x = ModifyAdmissionConstraint{} + if protoimpl.UnsafeEnabled { + mi := &file_cluster_service_proto_msgTypes[7] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *ModifyAdmissionConstraint) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*ModifyAdmissionConstraint) ProtoMessage() {} + +func (x *ModifyAdmissionConstraint) ProtoReflect() protoreflect.Message { + mi := &file_cluster_service_proto_msgTypes[7] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use ModifyAdmissionConstraint.ProtoReflect.Descriptor instead. +func (*ModifyAdmissionConstraint) Descriptor() ([]byte, []int) { + return file_cluster_service_proto_rawDescGZIP(), []int{7} +} + +func (x *ModifyAdmissionConstraint) GetAdd() bool { + if x != nil { + return x.Add + } + return false +} + +func (x *ModifyAdmissionConstraint) GetConstraint() *AdmissionConstraint { + if x != nil { + return x.Constraint + } + return nil +} + type UpdateResponse struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache @@ -558,7 +731,7 @@ type UpdateResponse struct { func (x *UpdateResponse) Reset() { *x = UpdateResponse{} if protoimpl.UnsafeEnabled { - mi := &file_cluster_service_proto_msgTypes[6] + mi := &file_cluster_service_proto_msgTypes[8] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -571,7 +744,7 @@ func (x *UpdateResponse) String() string { func (*UpdateResponse) ProtoMessage() {} func (x *UpdateResponse) ProtoReflect() protoreflect.Message { - mi := &file_cluster_service_proto_msgTypes[6] + mi := &file_cluster_service_proto_msgTypes[8] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -584,7 +757,7 @@ func (x *UpdateResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use UpdateResponse.ProtoReflect.Descriptor instead. func (*UpdateResponse) Descriptor() ([]byte, []int) { - return file_cluster_service_proto_rawDescGZIP(), []int{6} + return file_cluster_service_proto_rawDescGZIP(), []int{8} } type DeregisterRequest struct { @@ -598,7 +771,7 @@ type DeregisterRequest struct { func (x *DeregisterRequest) Reset() { *x = DeregisterRequest{} if protoimpl.UnsafeEnabled { - mi := &file_cluster_service_proto_msgTypes[7] + mi := &file_cluster_service_proto_msgTypes[9] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -611,7 +784,7 @@ func (x *DeregisterRequest) String() string { func (*DeregisterRequest) ProtoMessage() {} func (x *DeregisterRequest) ProtoReflect() protoreflect.Message { - mi := &file_cluster_service_proto_msgTypes[7] + mi := &file_cluster_service_proto_msgTypes[9] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -624,7 +797,7 @@ func (x *DeregisterRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use DeregisterRequest.ProtoReflect.Descriptor instead. func (*DeregisterRequest) Descriptor() ([]byte, []int) { - return file_cluster_service_proto_rawDescGZIP(), []int{7} + return file_cluster_service_proto_rawDescGZIP(), []int{9} } func (x *DeregisterRequest) GetName() string { @@ -643,7 +816,7 @@ type DeregisterResponse struct { func (x *DeregisterResponse) Reset() { *x = DeregisterResponse{} if protoimpl.UnsafeEnabled { - mi := &file_cluster_service_proto_msgTypes[8] + mi := &file_cluster_service_proto_msgTypes[10] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -656,7 +829,7 @@ func (x *DeregisterResponse) String() string { func (*DeregisterResponse) ProtoMessage() {} func (x *DeregisterResponse) ProtoReflect() protoreflect.Message { - mi := &file_cluster_service_proto_msgTypes[8] + mi := &file_cluster_service_proto_msgTypes[10] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -669,7 +842,7 @@ func (x *DeregisterResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use DeregisterResponse.ProtoReflect.Descriptor instead. func (*DeregisterResponse) Descriptor() ([]byte, []int) { - return file_cluster_service_proto_rawDescGZIP(), []int{8} + return file_cluster_service_proto_rawDescGZIP(), []int{10} } type ListRequest struct { @@ -681,7 +854,7 @@ type ListRequest struct { func (x *ListRequest) Reset() { *x = ListRequest{} if protoimpl.UnsafeEnabled { - mi := &file_cluster_service_proto_msgTypes[9] + mi := &file_cluster_service_proto_msgTypes[11] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -694,7 +867,7 @@ func (x *ListRequest) String() string { func (*ListRequest) ProtoMessage() {} func (x *ListRequest) ProtoReflect() protoreflect.Message { - mi := &file_cluster_service_proto_msgTypes[9] + mi := &file_cluster_service_proto_msgTypes[11] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -707,7 +880,7 @@ func (x *ListRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ListRequest.ProtoReflect.Descriptor instead. func (*ListRequest) Descriptor() ([]byte, []int) { - return file_cluster_service_proto_rawDescGZIP(), []int{9} + return file_cluster_service_proto_rawDescGZIP(), []int{11} } type ListResponse struct { @@ -721,7 +894,7 @@ type ListResponse struct { func (x *ListResponse) Reset() { *x = ListResponse{} if protoimpl.UnsafeEnabled { - mi := &file_cluster_service_proto_msgTypes[10] + mi := &file_cluster_service_proto_msgTypes[12] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -734,7 +907,7 @@ func (x *ListResponse) String() string { func (*ListResponse) ProtoMessage() {} func (x *ListResponse) ProtoReflect() protoreflect.Message { - mi := &file_cluster_service_proto_msgTypes[10] + mi := &file_cluster_service_proto_msgTypes[12] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -747,7 +920,7 @@ func (x *ListResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ListResponse.ProtoReflect.Descriptor instead. func (*ListResponse) Descriptor() ([]byte, []int) { - return file_cluster_service_proto_rawDescGZIP(), []int{10} + return file_cluster_service_proto_rawDescGZIP(), []int{12} } func (x *ListResponse) GetStatus() []*ClusterStatus { @@ -757,13 +930,98 @@ func (x *ListResponse) GetStatus() []*ClusterStatus { return nil } +type AdmissionConstraint_FeaturePreview struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields +} + +func (x *AdmissionConstraint_FeaturePreview) Reset() { + *x = AdmissionConstraint_FeaturePreview{} + if protoimpl.UnsafeEnabled { + mi := &file_cluster_service_proto_msgTypes[13] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *AdmissionConstraint_FeaturePreview) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*AdmissionConstraint_FeaturePreview) ProtoMessage() {} + +func (x *AdmissionConstraint_FeaturePreview) ProtoReflect() protoreflect.Message { + mi := &file_cluster_service_proto_msgTypes[13] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use AdmissionConstraint_FeaturePreview.ProtoReflect.Descriptor instead. +func (*AdmissionConstraint_FeaturePreview) Descriptor() ([]byte, []int) { + return file_cluster_service_proto_rawDescGZIP(), []int{4, 0} +} + +type AdmissionConstraint_HasPermission struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Permission string `protobuf:"bytes,1,opt,name=permission,proto3" json:"permission,omitempty"` +} + +func (x *AdmissionConstraint_HasPermission) Reset() { + *x = AdmissionConstraint_HasPermission{} + if protoimpl.UnsafeEnabled { + mi := &file_cluster_service_proto_msgTypes[14] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *AdmissionConstraint_HasPermission) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*AdmissionConstraint_HasPermission) ProtoMessage() {} + +func (x *AdmissionConstraint_HasPermission) ProtoReflect() protoreflect.Message { + mi := &file_cluster_service_proto_msgTypes[14] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use AdmissionConstraint_HasPermission.ProtoReflect.Descriptor instead. +func (*AdmissionConstraint_HasPermission) Descriptor() ([]byte, []int) { + return file_cluster_service_proto_rawDescGZIP(), []int{4, 1} +} + +func (x *AdmissionConstraint_HasPermission) GetPermission() string { + if x != nil { + return x.Permission + } + return "" +} + var File_cluster_service_proto protoreflect.FileDescriptor var file_cluster_service_proto_rawDesc = []byte{ 0x0a, 0x15, 0x63, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x2d, 0x73, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x16, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x22, - 0xad, 0x01, 0x0a, 0x0f, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, + 0x8f, 0x02, 0x0a, 0x0f, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x10, 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x12, 0x33, 0x0a, 0x03, 0x74, 0x6c, 0x73, @@ -773,91 +1031,139 @@ var file_cluster_service_proto_rawDesc = []byte{ 0x0a, 0x05, 0x68, 0x69, 0x6e, 0x74, 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x72, 0x61, 0x74, - 0x69, 0x6f, 0x6e, 0x48, 0x69, 0x6e, 0x74, 0x73, 0x52, 0x05, 0x68, 0x69, 0x6e, 0x74, 0x73, 0x22, - 0x12, 0x0a, 0x10, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x73, 0x70, 0x6f, - 0x6e, 0x73, 0x65, 0x22, 0x3f, 0x0a, 0x09, 0x54, 0x6c, 0x73, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, - 0x12, 0x0e, 0x0a, 0x02, 0x63, 0x61, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x02, 0x63, 0x61, - 0x12, 0x10, 0x0a, 0x03, 0x63, 0x72, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x63, - 0x72, 0x74, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, - 0x03, 0x6b, 0x65, 0x79, 0x22, 0x96, 0x01, 0x0a, 0x11, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x72, - 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x48, 0x69, 0x6e, 0x74, 0x73, 0x12, 0x4d, 0x0a, 0x0e, 0x70, 0x65, - 0x72, 0x66, 0x65, 0x72, 0x65, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x18, 0x01, 0x20, 0x01, - 0x28, 0x0e, 0x32, 0x25, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, - 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x50, 0x72, 0x65, 0x66, - 0x65, 0x72, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x52, 0x0e, 0x70, 0x65, 0x72, 0x66, 0x65, - 0x72, 0x65, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x12, 0x1a, 0x0a, 0x08, 0x63, 0x6f, 0x72, - 0x64, 0x6f, 0x6e, 0x65, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x08, 0x52, 0x08, 0x63, 0x6f, 0x72, - 0x64, 0x6f, 0x6e, 0x65, 0x64, 0x12, 0x16, 0x0a, 0x06, 0x67, 0x6f, 0x76, 0x65, 0x72, 0x6e, 0x18, - 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x06, 0x67, 0x6f, 0x76, 0x65, 0x72, 0x6e, 0x22, 0xc0, 0x01, - 0x0a, 0x0d, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, - 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, - 0x61, 0x6d, 0x65, 0x12, 0x10, 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, - 0x52, 0x03, 0x75, 0x72, 0x6c, 0x12, 0x3a, 0x0a, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x03, - 0x20, 0x01, 0x28, 0x0e, 0x32, 0x24, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, + 0x69, 0x6f, 0x6e, 0x48, 0x69, 0x6e, 0x74, 0x73, 0x52, 0x05, 0x68, 0x69, 0x6e, 0x74, 0x73, 0x12, + 0x60, 0x0a, 0x15, 0x61, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x5f, 0x63, 0x6f, 0x6e, + 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x2b, + 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, + 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x41, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, + 0x6e, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x52, 0x14, 0x61, 0x64, 0x6d, + 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, + 0x73, 0x22, 0x12, 0x0a, 0x10, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x73, + 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x3f, 0x0a, 0x09, 0x54, 0x6c, 0x73, 0x43, 0x6f, 0x6e, 0x66, + 0x69, 0x67, 0x12, 0x0e, 0x0a, 0x02, 0x63, 0x61, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x02, + 0x63, 0x61, 0x12, 0x10, 0x0a, 0x03, 0x63, 0x72, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, + 0x03, 0x63, 0x72, 0x74, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, + 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x22, 0x96, 0x01, 0x0a, 0x11, 0x52, 0x65, 0x67, 0x69, 0x73, + 0x74, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x48, 0x69, 0x6e, 0x74, 0x73, 0x12, 0x4d, 0x0a, 0x0e, + 0x70, 0x65, 0x72, 0x66, 0x65, 0x72, 0x65, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x18, 0x01, + 0x20, 0x01, 0x28, 0x0e, 0x32, 0x25, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, + 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x50, 0x72, + 0x65, 0x66, 0x65, 0x72, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x52, 0x0e, 0x70, 0x65, 0x72, + 0x66, 0x65, 0x72, 0x65, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x12, 0x1a, 0x0a, 0x08, 0x63, + 0x6f, 0x72, 0x64, 0x6f, 0x6e, 0x65, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x08, 0x52, 0x08, 0x63, + 0x6f, 0x72, 0x64, 0x6f, 0x6e, 0x65, 0x64, 0x12, 0x16, 0x0a, 0x06, 0x67, 0x6f, 0x76, 0x65, 0x72, + 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x06, 0x67, 0x6f, 0x76, 0x65, 0x72, 0x6e, 0x22, + 0xb8, 0x02, 0x0a, 0x13, 0x41, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x43, 0x6f, 0x6e, + 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x12, 0x6c, 0x0a, 0x13, 0x68, 0x61, 0x73, 0x5f, 0x66, + 0x65, 0x61, 0x74, 0x75, 0x72, 0x65, 0x5f, 0x70, 0x72, 0x65, 0x76, 0x69, 0x65, 0x77, 0x18, 0x01, + 0x20, 0x01, 0x28, 0x0b, 0x32, 0x3a, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, + 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x41, 0x64, + 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, + 0x74, 0x2e, 0x46, 0x65, 0x61, 0x74, 0x75, 0x72, 0x65, 0x50, 0x72, 0x65, 0x76, 0x69, 0x65, 0x77, + 0x48, 0x00, 0x52, 0x11, 0x68, 0x61, 0x73, 0x46, 0x65, 0x61, 0x74, 0x75, 0x72, 0x65, 0x50, 0x72, + 0x65, 0x76, 0x69, 0x65, 0x77, 0x12, 0x62, 0x0a, 0x0e, 0x68, 0x61, 0x73, 0x5f, 0x70, 0x65, 0x72, + 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x39, 0x2e, + 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, + 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x41, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, + 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x2e, 0x48, 0x61, 0x73, 0x50, 0x65, + 0x72, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x48, 0x00, 0x52, 0x0d, 0x68, 0x61, 0x73, 0x50, + 0x65, 0x72, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x1a, 0x10, 0x0a, 0x0e, 0x46, 0x65, 0x61, + 0x74, 0x75, 0x72, 0x65, 0x50, 0x72, 0x65, 0x76, 0x69, 0x65, 0x77, 0x1a, 0x2f, 0x0a, 0x0d, 0x48, + 0x61, 0x73, 0x50, 0x65, 0x72, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x1e, 0x0a, 0x0a, + 0x70, 0x65, 0x72, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, + 0x52, 0x0a, 0x70, 0x65, 0x72, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x42, 0x0c, 0x0a, 0x0a, + 0x63, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x22, 0xba, 0x02, 0x0a, 0x0d, 0x43, + 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x12, 0x0a, 0x04, + 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, + 0x12, 0x10, 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, + 0x72, 0x6c, 0x12, 0x3a, 0x0a, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, + 0x0e, 0x32, 0x24, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, + 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x43, 0x6c, 0x75, 0x73, 0x74, + 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x12, 0x14, + 0x0a, 0x05, 0x73, 0x63, 0x6f, 0x72, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x52, 0x05, 0x73, + 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1b, 0x0a, 0x09, 0x6d, 0x61, 0x78, 0x5f, 0x73, 0x63, 0x6f, 0x72, + 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x6d, 0x61, 0x78, 0x53, 0x63, 0x6f, 0x72, + 0x65, 0x12, 0x1a, 0x0a, 0x08, 0x67, 0x6f, 0x76, 0x65, 0x72, 0x6e, 0x65, 0x64, 0x18, 0x06, 0x20, + 0x01, 0x28, 0x08, 0x52, 0x08, 0x67, 0x6f, 0x76, 0x65, 0x72, 0x6e, 0x65, 0x64, 0x12, 0x60, 0x0a, + 0x15, 0x61, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x5f, 0x63, 0x6f, 0x6e, 0x73, 0x74, + 0x72, 0x61, 0x69, 0x6e, 0x74, 0x73, 0x18, 0x07, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x77, + 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, + 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x41, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x43, + 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x52, 0x14, 0x61, 0x64, 0x6d, 0x69, 0x73, + 0x73, 0x69, 0x6f, 0x6e, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x73, 0x12, + 0x16, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x18, 0x08, 0x20, 0x01, 0x28, 0x08, 0x52, + 0x06, 0x73, 0x74, 0x61, 0x74, 0x69, 0x63, 0x22, 0xee, 0x01, 0x0a, 0x0d, 0x55, 0x70, 0x64, 0x61, + 0x74, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, + 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x16, 0x0a, + 0x05, 0x73, 0x63, 0x6f, 0x72, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x48, 0x00, 0x52, 0x05, + 0x73, 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1d, 0x0a, 0x09, 0x6d, 0x61, 0x78, 0x5f, 0x73, 0x63, 0x6f, + 0x72, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x05, 0x48, 0x00, 0x52, 0x08, 0x6d, 0x61, 0x78, 0x53, + 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1c, 0x0a, 0x08, 0x63, 0x6f, 0x72, 0x64, 0x6f, 0x6e, 0x65, 0x64, + 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x48, 0x00, 0x52, 0x08, 0x63, 0x6f, 0x72, 0x64, 0x6f, 0x6e, + 0x65, 0x64, 0x12, 0x68, 0x0a, 0x15, 0x61, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x5f, + 0x63, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x73, 0x18, 0x05, 0x20, 0x01, 0x28, + 0x0b, 0x32, 0x31, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, + 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x4d, 0x6f, 0x64, 0x69, 0x66, + 0x79, 0x41, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x72, + 0x61, 0x69, 0x6e, 0x74, 0x48, 0x00, 0x52, 0x14, 0x61, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, + 0x6e, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x73, 0x42, 0x0a, 0x0a, 0x08, + 0x70, 0x72, 0x6f, 0x70, 0x65, 0x72, 0x74, 0x79, 0x22, 0x7a, 0x0a, 0x19, 0x4d, 0x6f, 0x64, 0x69, + 0x66, 0x79, 0x41, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x43, 0x6f, 0x6e, 0x73, 0x74, + 0x72, 0x61, 0x69, 0x6e, 0x74, 0x12, 0x10, 0x0a, 0x03, 0x61, 0x64, 0x64, 0x18, 0x01, 0x20, 0x01, + 0x28, 0x08, 0x52, 0x03, 0x61, 0x64, 0x64, 0x12, 0x4b, 0x0a, 0x0a, 0x63, 0x6f, 0x6e, 0x73, 0x74, + 0x72, 0x61, 0x69, 0x6e, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x77, 0x6f, + 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, + 0x69, 0x64, 0x67, 0x65, 0x2e, 0x41, 0x64, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x43, 0x6f, + 0x6e, 0x73, 0x74, 0x72, 0x61, 0x69, 0x6e, 0x74, 0x52, 0x0a, 0x63, 0x6f, 0x6e, 0x73, 0x74, 0x72, + 0x61, 0x69, 0x6e, 0x74, 0x22, 0x10, 0x0a, 0x0e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, + 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x27, 0x0a, 0x11, 0x44, 0x65, 0x72, 0x65, 0x67, 0x69, + 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x12, 0x0a, 0x04, 0x6e, + 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x22, + 0x14, 0x0a, 0x12, 0x44, 0x65, 0x72, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x73, + 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x0d, 0x0a, 0x0b, 0x4c, 0x69, 0x73, 0x74, 0x52, 0x65, 0x71, + 0x75, 0x65, 0x73, 0x74, 0x22, 0x4d, 0x0a, 0x0c, 0x4c, 0x69, 0x73, 0x74, 0x52, 0x65, 0x73, 0x70, + 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x3d, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x01, + 0x20, 0x03, 0x28, 0x0b, 0x32, 0x25, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x43, 0x6c, - 0x75, 0x73, 0x74, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x05, 0x73, 0x74, 0x61, 0x74, - 0x65, 0x12, 0x14, 0x0a, 0x05, 0x73, 0x63, 0x6f, 0x72, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, - 0x52, 0x05, 0x73, 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1b, 0x0a, 0x09, 0x6d, 0x61, 0x78, 0x5f, 0x73, - 0x63, 0x6f, 0x72, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x6d, 0x61, 0x78, 0x53, - 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1a, 0x0a, 0x08, 0x67, 0x6f, 0x76, 0x65, 0x72, 0x6e, 0x65, 0x64, - 0x18, 0x06, 0x20, 0x01, 0x28, 0x08, 0x52, 0x08, 0x67, 0x6f, 0x76, 0x65, 0x72, 0x6e, 0x65, 0x64, - 0x22, 0x84, 0x01, 0x0a, 0x0d, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65, - 0x73, 0x74, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, - 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x16, 0x0a, 0x05, 0x73, 0x63, 0x6f, 0x72, 0x65, 0x18, - 0x02, 0x20, 0x01, 0x28, 0x05, 0x48, 0x00, 0x52, 0x05, 0x73, 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1d, - 0x0a, 0x09, 0x6d, 0x61, 0x78, 0x5f, 0x73, 0x63, 0x6f, 0x72, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, - 0x05, 0x48, 0x00, 0x52, 0x08, 0x6d, 0x61, 0x78, 0x53, 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1c, 0x0a, - 0x08, 0x63, 0x6f, 0x72, 0x64, 0x6f, 0x6e, 0x65, 0x64, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x48, - 0x00, 0x52, 0x08, 0x63, 0x6f, 0x72, 0x64, 0x6f, 0x6e, 0x65, 0x64, 0x42, 0x0a, 0x0a, 0x08, 0x70, - 0x72, 0x6f, 0x70, 0x65, 0x72, 0x74, 0x79, 0x22, 0x10, 0x0a, 0x0e, 0x55, 0x70, 0x64, 0x61, 0x74, - 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x27, 0x0a, 0x11, 0x44, 0x65, 0x72, - 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x12, - 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, - 0x6d, 0x65, 0x22, 0x14, 0x0a, 0x12, 0x44, 0x65, 0x72, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, - 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x0d, 0x0a, 0x0b, 0x4c, 0x69, 0x73, 0x74, - 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x4d, 0x0a, 0x0c, 0x4c, 0x69, 0x73, 0x74, 0x52, - 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x3d, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, - 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x25, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, - 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, - 0x2e, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x06, - 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x2a, 0x37, 0x0a, 0x0d, 0x50, 0x72, 0x65, 0x66, 0x65, 0x72, - 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x12, 0x08, 0x0a, 0x04, 0x4e, 0x6f, 0x6e, 0x65, 0x10, - 0x00, 0x12, 0x0a, 0x0a, 0x06, 0x50, 0x72, 0x65, 0x66, 0x65, 0x72, 0x10, 0x01, 0x12, 0x10, 0x0a, - 0x0c, 0x44, 0x6f, 0x6e, 0x74, 0x53, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x10, 0x02, 0x2a, - 0x46, 0x0a, 0x0c, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, - 0x0b, 0x0a, 0x07, 0x55, 0x4e, 0x4b, 0x4e, 0x4f, 0x57, 0x4e, 0x10, 0x00, 0x12, 0x0d, 0x0a, 0x09, - 0x41, 0x56, 0x41, 0x49, 0x4c, 0x41, 0x42, 0x4c, 0x45, 0x10, 0x01, 0x12, 0x0c, 0x0a, 0x08, 0x43, - 0x4f, 0x52, 0x44, 0x4f, 0x4e, 0x45, 0x44, 0x10, 0x02, 0x12, 0x0c, 0x0a, 0x08, 0x44, 0x52, 0x41, - 0x49, 0x4e, 0x49, 0x4e, 0x47, 0x10, 0x03, 0x32, 0x88, 0x03, 0x0a, 0x0e, 0x43, 0x6c, 0x75, 0x73, - 0x74, 0x65, 0x72, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x12, 0x5f, 0x0a, 0x08, 0x52, 0x65, - 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x12, 0x27, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, - 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, - 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, - 0x28, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, - 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, - 0x72, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x59, 0x0a, 0x06, 0x55, - 0x70, 0x64, 0x61, 0x74, 0x65, 0x12, 0x25, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, - 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x55, - 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x26, 0x2e, 0x77, + 0x75, 0x73, 0x74, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x06, 0x73, 0x74, 0x61, + 0x74, 0x75, 0x73, 0x2a, 0x37, 0x0a, 0x0d, 0x50, 0x72, 0x65, 0x66, 0x65, 0x72, 0x61, 0x62, 0x69, + 0x6c, 0x69, 0x74, 0x79, 0x12, 0x08, 0x0a, 0x04, 0x4e, 0x6f, 0x6e, 0x65, 0x10, 0x00, 0x12, 0x0a, + 0x0a, 0x06, 0x50, 0x72, 0x65, 0x66, 0x65, 0x72, 0x10, 0x01, 0x12, 0x10, 0x0a, 0x0c, 0x44, 0x6f, + 0x6e, 0x74, 0x53, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x10, 0x02, 0x2a, 0x46, 0x0a, 0x0c, + 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x0b, 0x0a, 0x07, + 0x55, 0x4e, 0x4b, 0x4e, 0x4f, 0x57, 0x4e, 0x10, 0x00, 0x12, 0x0d, 0x0a, 0x09, 0x41, 0x56, 0x41, + 0x49, 0x4c, 0x41, 0x42, 0x4c, 0x45, 0x10, 0x01, 0x12, 0x0c, 0x0a, 0x08, 0x43, 0x4f, 0x52, 0x44, + 0x4f, 0x4e, 0x45, 0x44, 0x10, 0x02, 0x12, 0x0c, 0x0a, 0x08, 0x44, 0x52, 0x41, 0x49, 0x4e, 0x49, + 0x4e, 0x47, 0x10, 0x03, 0x32, 0x88, 0x03, 0x0a, 0x0e, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, + 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x12, 0x5f, 0x0a, 0x08, 0x52, 0x65, 0x67, 0x69, 0x73, + 0x74, 0x65, 0x72, 0x12, 0x27, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, + 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x52, 0x65, 0x67, + 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x28, 0x2e, 0x77, + 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, + 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, + 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x59, 0x0a, 0x06, 0x55, 0x70, 0x64, 0x61, + 0x74, 0x65, 0x12, 0x25, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, + 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x55, 0x70, 0x64, 0x61, + 0x74, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x26, 0x2e, 0x77, 0x6f, 0x72, 0x6b, + 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, + 0x67, 0x65, 0x2e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, + 0x65, 0x22, 0x00, 0x12, 0x65, 0x0a, 0x0a, 0x44, 0x65, 0x72, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, + 0x72, 0x12, 0x29, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, + 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x44, 0x65, 0x72, 0x65, 0x67, + 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x2a, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, - 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x70, - 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x65, 0x0a, 0x0a, 0x44, 0x65, 0x72, 0x65, 0x67, 0x69, - 0x73, 0x74, 0x65, 0x72, 0x12, 0x29, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, - 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x44, 0x65, - 0x72, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, - 0x2a, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, - 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x44, 0x65, 0x72, 0x65, 0x67, 0x69, 0x73, - 0x74, 0x65, 0x72, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x53, 0x0a, - 0x04, 0x4c, 0x69, 0x73, 0x74, 0x12, 0x23, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, - 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x4c, - 0x69, 0x73, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x24, 0x2e, 0x77, 0x6f, 0x72, - 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, - 0x64, 0x67, 0x65, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, - 0x22, 0x00, 0x42, 0x3a, 0x5a, 0x38, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, - 0x2f, 0x67, 0x69, 0x74, 0x70, 0x6f, 0x64, 0x2d, 0x69, 0x6f, 0x2f, 0x67, 0x69, 0x74, 0x70, 0x6f, - 0x64, 0x2f, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x2d, 0x6d, 0x61, 0x6e, 0x61, - 0x67, 0x65, 0x72, 0x2d, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x62, 0x06, - 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x44, 0x65, 0x72, 0x65, 0x67, 0x69, 0x73, 0x74, 0x65, 0x72, + 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x53, 0x0a, 0x04, 0x4c, 0x69, + 0x73, 0x74, 0x12, 0x23, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x6d, 0x61, + 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2e, 0x4c, 0x69, 0x73, 0x74, + 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x24, 0x2e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, + 0x61, 0x63, 0x65, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, + 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x42, + 0x3a, 0x5a, 0x38, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x67, 0x69, + 0x74, 0x70, 0x6f, 0x64, 0x2d, 0x69, 0x6f, 0x2f, 0x67, 0x69, 0x74, 0x70, 0x6f, 0x64, 0x2f, 0x77, + 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x2d, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, + 0x2d, 0x62, 0x72, 0x69, 0x64, 0x67, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x62, 0x06, 0x70, 0x72, 0x6f, + 0x74, 0x6f, 0x33, } var ( @@ -873,41 +1179,51 @@ func file_cluster_service_proto_rawDescGZIP() []byte { } var file_cluster_service_proto_enumTypes = make([]protoimpl.EnumInfo, 2) -var file_cluster_service_proto_msgTypes = make([]protoimpl.MessageInfo, 11) +var file_cluster_service_proto_msgTypes = make([]protoimpl.MessageInfo, 15) var file_cluster_service_proto_goTypes = []interface{}{ - (Preferability)(0), // 0: workspacemanagerbridge.Preferability - (ClusterState)(0), // 1: workspacemanagerbridge.ClusterState - (*RegisterRequest)(nil), // 2: workspacemanagerbridge.RegisterRequest - (*RegisterResponse)(nil), // 3: workspacemanagerbridge.RegisterResponse - (*TlsConfig)(nil), // 4: workspacemanagerbridge.TlsConfig - (*RegistrationHints)(nil), // 5: workspacemanagerbridge.RegistrationHints - (*ClusterStatus)(nil), // 6: workspacemanagerbridge.ClusterStatus - (*UpdateRequest)(nil), // 7: workspacemanagerbridge.UpdateRequest - (*UpdateResponse)(nil), // 8: workspacemanagerbridge.UpdateResponse - (*DeregisterRequest)(nil), // 9: workspacemanagerbridge.DeregisterRequest - (*DeregisterResponse)(nil), // 10: workspacemanagerbridge.DeregisterResponse - (*ListRequest)(nil), // 11: workspacemanagerbridge.ListRequest - (*ListResponse)(nil), // 12: workspacemanagerbridge.ListResponse + (Preferability)(0), // 0: workspacemanagerbridge.Preferability + (ClusterState)(0), // 1: workspacemanagerbridge.ClusterState + (*RegisterRequest)(nil), // 2: workspacemanagerbridge.RegisterRequest + (*RegisterResponse)(nil), // 3: workspacemanagerbridge.RegisterResponse + (*TlsConfig)(nil), // 4: workspacemanagerbridge.TlsConfig + (*RegistrationHints)(nil), // 5: workspacemanagerbridge.RegistrationHints + (*AdmissionConstraint)(nil), // 6: workspacemanagerbridge.AdmissionConstraint + (*ClusterStatus)(nil), // 7: workspacemanagerbridge.ClusterStatus + (*UpdateRequest)(nil), // 8: workspacemanagerbridge.UpdateRequest + (*ModifyAdmissionConstraint)(nil), // 9: workspacemanagerbridge.ModifyAdmissionConstraint + (*UpdateResponse)(nil), // 10: workspacemanagerbridge.UpdateResponse + (*DeregisterRequest)(nil), // 11: workspacemanagerbridge.DeregisterRequest + (*DeregisterResponse)(nil), // 12: workspacemanagerbridge.DeregisterResponse + (*ListRequest)(nil), // 13: workspacemanagerbridge.ListRequest + (*ListResponse)(nil), // 14: workspacemanagerbridge.ListResponse + (*AdmissionConstraint_FeaturePreview)(nil), // 15: workspacemanagerbridge.AdmissionConstraint.FeaturePreview + (*AdmissionConstraint_HasPermission)(nil), // 16: workspacemanagerbridge.AdmissionConstraint.HasPermission } var file_cluster_service_proto_depIdxs = []int32{ 4, // 0: workspacemanagerbridge.RegisterRequest.tls:type_name -> workspacemanagerbridge.TlsConfig 5, // 1: workspacemanagerbridge.RegisterRequest.hints:type_name -> workspacemanagerbridge.RegistrationHints - 0, // 2: workspacemanagerbridge.RegistrationHints.perfereability:type_name -> workspacemanagerbridge.Preferability - 1, // 3: workspacemanagerbridge.ClusterStatus.state:type_name -> workspacemanagerbridge.ClusterState - 6, // 4: workspacemanagerbridge.ListResponse.status:type_name -> workspacemanagerbridge.ClusterStatus - 2, // 5: workspacemanagerbridge.ClusterService.Register:input_type -> workspacemanagerbridge.RegisterRequest - 7, // 6: workspacemanagerbridge.ClusterService.Update:input_type -> workspacemanagerbridge.UpdateRequest - 9, // 7: workspacemanagerbridge.ClusterService.Deregister:input_type -> workspacemanagerbridge.DeregisterRequest - 11, // 8: workspacemanagerbridge.ClusterService.List:input_type -> workspacemanagerbridge.ListRequest - 3, // 9: workspacemanagerbridge.ClusterService.Register:output_type -> workspacemanagerbridge.RegisterResponse - 8, // 10: workspacemanagerbridge.ClusterService.Update:output_type -> workspacemanagerbridge.UpdateResponse - 10, // 11: workspacemanagerbridge.ClusterService.Deregister:output_type -> workspacemanagerbridge.DeregisterResponse - 12, // 12: workspacemanagerbridge.ClusterService.List:output_type -> workspacemanagerbridge.ListResponse - 9, // [9:13] is the sub-list for method output_type - 5, // [5:9] is the sub-list for method input_type - 5, // [5:5] is the sub-list for extension type_name - 5, // [5:5] is the sub-list for extension extendee - 0, // [0:5] is the sub-list for field type_name + 6, // 2: workspacemanagerbridge.RegisterRequest.admission_constraints:type_name -> workspacemanagerbridge.AdmissionConstraint + 0, // 3: workspacemanagerbridge.RegistrationHints.perfereability:type_name -> workspacemanagerbridge.Preferability + 15, // 4: workspacemanagerbridge.AdmissionConstraint.has_feature_preview:type_name -> workspacemanagerbridge.AdmissionConstraint.FeaturePreview + 16, // 5: workspacemanagerbridge.AdmissionConstraint.has_permission:type_name -> workspacemanagerbridge.AdmissionConstraint.HasPermission + 1, // 6: workspacemanagerbridge.ClusterStatus.state:type_name -> workspacemanagerbridge.ClusterState + 6, // 7: workspacemanagerbridge.ClusterStatus.admission_constraints:type_name -> workspacemanagerbridge.AdmissionConstraint + 9, // 8: workspacemanagerbridge.UpdateRequest.admission_constraints:type_name -> workspacemanagerbridge.ModifyAdmissionConstraint + 6, // 9: workspacemanagerbridge.ModifyAdmissionConstraint.constraint:type_name -> workspacemanagerbridge.AdmissionConstraint + 7, // 10: workspacemanagerbridge.ListResponse.status:type_name -> workspacemanagerbridge.ClusterStatus + 2, // 11: workspacemanagerbridge.ClusterService.Register:input_type -> workspacemanagerbridge.RegisterRequest + 8, // 12: workspacemanagerbridge.ClusterService.Update:input_type -> workspacemanagerbridge.UpdateRequest + 11, // 13: workspacemanagerbridge.ClusterService.Deregister:input_type -> workspacemanagerbridge.DeregisterRequest + 13, // 14: workspacemanagerbridge.ClusterService.List:input_type -> workspacemanagerbridge.ListRequest + 3, // 15: workspacemanagerbridge.ClusterService.Register:output_type -> workspacemanagerbridge.RegisterResponse + 10, // 16: workspacemanagerbridge.ClusterService.Update:output_type -> workspacemanagerbridge.UpdateResponse + 12, // 17: workspacemanagerbridge.ClusterService.Deregister:output_type -> workspacemanagerbridge.DeregisterResponse + 14, // 18: workspacemanagerbridge.ClusterService.List:output_type -> workspacemanagerbridge.ListResponse + 15, // [15:19] is the sub-list for method output_type + 11, // [11:15] is the sub-list for method input_type + 11, // [11:11] is the sub-list for extension type_name + 11, // [11:11] is the sub-list for extension extendee + 0, // [0:11] is the sub-list for field type_name } func init() { file_cluster_service_proto_init() } @@ -965,7 +1281,7 @@ func file_cluster_service_proto_init() { } } file_cluster_service_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ClusterStatus); i { + switch v := v.(*AdmissionConstraint); i { case 0: return &v.state case 1: @@ -977,7 +1293,7 @@ func file_cluster_service_proto_init() { } } file_cluster_service_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*UpdateRequest); i { + switch v := v.(*ClusterStatus); i { case 0: return &v.state case 1: @@ -989,7 +1305,7 @@ func file_cluster_service_proto_init() { } } file_cluster_service_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*UpdateResponse); i { + switch v := v.(*UpdateRequest); i { case 0: return &v.state case 1: @@ -1001,7 +1317,7 @@ func file_cluster_service_proto_init() { } } file_cluster_service_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*DeregisterRequest); i { + switch v := v.(*ModifyAdmissionConstraint); i { case 0: return &v.state case 1: @@ -1013,7 +1329,7 @@ func file_cluster_service_proto_init() { } } file_cluster_service_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*DeregisterResponse); i { + switch v := v.(*UpdateResponse); i { case 0: return &v.state case 1: @@ -1025,7 +1341,7 @@ func file_cluster_service_proto_init() { } } file_cluster_service_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListRequest); i { + switch v := v.(*DeregisterRequest); i { case 0: return &v.state case 1: @@ -1037,6 +1353,30 @@ func file_cluster_service_proto_init() { } } file_cluster_service_proto_msgTypes[10].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*DeregisterResponse); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_cluster_service_proto_msgTypes[11].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*ListRequest); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_cluster_service_proto_msgTypes[12].Exporter = func(v interface{}, i int) interface{} { switch v := v.(*ListResponse); i { case 0: return &v.state @@ -1048,11 +1388,40 @@ func file_cluster_service_proto_init() { return nil } } + file_cluster_service_proto_msgTypes[13].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*AdmissionConstraint_FeaturePreview); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_cluster_service_proto_msgTypes[14].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*AdmissionConstraint_HasPermission); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + } + file_cluster_service_proto_msgTypes[4].OneofWrappers = []interface{}{ + (*AdmissionConstraint_HasFeaturePreview)(nil), + (*AdmissionConstraint_HasPermission_)(nil), } - file_cluster_service_proto_msgTypes[5].OneofWrappers = []interface{}{ + file_cluster_service_proto_msgTypes[6].OneofWrappers = []interface{}{ (*UpdateRequest_Score)(nil), (*UpdateRequest_MaxScore)(nil), (*UpdateRequest_Cordoned)(nil), + (*UpdateRequest_AdmissionConstraints)(nil), } type x struct{} out := protoimpl.TypeBuilder{ @@ -1060,7 +1429,7 @@ func file_cluster_service_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: file_cluster_service_proto_rawDesc, NumEnums: 2, - NumMessages: 11, + NumMessages: 15, NumExtensions: 0, NumServices: 1, }, diff --git a/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.d.ts b/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.d.ts index 2e8d048a73cef0..8c2ad69bae5d9e 100644 --- a/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.d.ts +++ b/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.d.ts @@ -27,6 +27,10 @@ export class RegisterRequest extends jspb.Message { clearHints(): void; getHints(): RegistrationHints | undefined; setHints(value?: RegistrationHints): RegisterRequest; + clearAdmissionConstraintsList(): void; + getAdmissionConstraintsList(): Array; + setAdmissionConstraintsList(value: Array): RegisterRequest; + addAdmissionConstraints(value?: AdmissionConstraint, index?: number): AdmissionConstraint; serializeBinary(): Uint8Array; toObject(includeInstance?: boolean): RegisterRequest.AsObject; @@ -44,6 +48,7 @@ export namespace RegisterRequest { url: string, tls?: TlsConfig.AsObject, hints?: RegistrationHints.AsObject, + admissionConstraintsList: Array, } } @@ -116,6 +121,83 @@ export namespace RegistrationHints { } } +export class AdmissionConstraint extends jspb.Message { + + hasHasFeaturePreview(): boolean; + clearHasFeaturePreview(): void; + getHasFeaturePreview(): AdmissionConstraint.FeaturePreview | undefined; + setHasFeaturePreview(value?: AdmissionConstraint.FeaturePreview): AdmissionConstraint; + + hasHasPermission(): boolean; + clearHasPermission(): void; + getHasPermission(): AdmissionConstraint.HasPermission | undefined; + setHasPermission(value?: AdmissionConstraint.HasPermission): AdmissionConstraint; + + getConstraintCase(): AdmissionConstraint.ConstraintCase; + + serializeBinary(): Uint8Array; + toObject(includeInstance?: boolean): AdmissionConstraint.AsObject; + static toObject(includeInstance: boolean, msg: AdmissionConstraint): AdmissionConstraint.AsObject; + static extensions: {[key: number]: jspb.ExtensionFieldInfo}; + static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo}; + static serializeBinaryToWriter(message: AdmissionConstraint, writer: jspb.BinaryWriter): void; + static deserializeBinary(bytes: Uint8Array): AdmissionConstraint; + static deserializeBinaryFromReader(message: AdmissionConstraint, reader: jspb.BinaryReader): AdmissionConstraint; +} + +export namespace AdmissionConstraint { + export type AsObject = { + hasFeaturePreview?: AdmissionConstraint.FeaturePreview.AsObject, + hasPermission?: AdmissionConstraint.HasPermission.AsObject, + } + + + export class FeaturePreview extends jspb.Message { + + serializeBinary(): Uint8Array; + toObject(includeInstance?: boolean): FeaturePreview.AsObject; + static toObject(includeInstance: boolean, msg: FeaturePreview): FeaturePreview.AsObject; + static extensions: {[key: number]: jspb.ExtensionFieldInfo}; + static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo}; + static serializeBinaryToWriter(message: FeaturePreview, writer: jspb.BinaryWriter): void; + static deserializeBinary(bytes: Uint8Array): FeaturePreview; + static deserializeBinaryFromReader(message: FeaturePreview, reader: jspb.BinaryReader): FeaturePreview; + } + + export namespace FeaturePreview { + export type AsObject = { + } + } + + export class HasPermission extends jspb.Message { + getPermission(): string; + setPermission(value: string): HasPermission; + + serializeBinary(): Uint8Array; + toObject(includeInstance?: boolean): HasPermission.AsObject; + static toObject(includeInstance: boolean, msg: HasPermission): HasPermission.AsObject; + static extensions: {[key: number]: jspb.ExtensionFieldInfo}; + static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo}; + static serializeBinaryToWriter(message: HasPermission, writer: jspb.BinaryWriter): void; + static deserializeBinary(bytes: Uint8Array): HasPermission; + static deserializeBinaryFromReader(message: HasPermission, reader: jspb.BinaryReader): HasPermission; + } + + export namespace HasPermission { + export type AsObject = { + permission: string, + } + } + + + export enum ConstraintCase { + CONSTRAINT_NOT_SET = 0, + HAS_FEATURE_PREVIEW = 1, + HAS_PERMISSION = 2, + } + +} + export class ClusterStatus extends jspb.Message { getName(): string; setName(value: string): ClusterStatus; @@ -129,6 +211,12 @@ export class ClusterStatus extends jspb.Message { setMaxScore(value: number): ClusterStatus; getGoverned(): boolean; setGoverned(value: boolean): ClusterStatus; + clearAdmissionConstraintsList(): void; + getAdmissionConstraintsList(): Array; + setAdmissionConstraintsList(value: Array): ClusterStatus; + addAdmissionConstraints(value?: AdmissionConstraint, index?: number): AdmissionConstraint; + getStatic(): boolean; + setStatic(value: boolean): ClusterStatus; serializeBinary(): Uint8Array; toObject(includeInstance?: boolean): ClusterStatus.AsObject; @@ -148,6 +236,8 @@ export namespace ClusterStatus { score: number, maxScore: number, governed: boolean, + admissionConstraintsList: Array, + pb_static: boolean, } } @@ -170,6 +260,11 @@ export class UpdateRequest extends jspb.Message { getCordoned(): boolean; setCordoned(value: boolean): UpdateRequest; + hasAdmissionConstraints(): boolean; + clearAdmissionConstraints(): void; + getAdmissionConstraints(): ModifyAdmissionConstraint | undefined; + setAdmissionConstraints(value?: ModifyAdmissionConstraint): UpdateRequest; + getPropertyCase(): UpdateRequest.PropertyCase; serializeBinary(): Uint8Array; @@ -188,6 +283,7 @@ export namespace UpdateRequest { score: number, maxScore: number, cordoned: boolean, + admissionConstraints?: ModifyAdmissionConstraint.AsObject, } export enum PropertyCase { @@ -195,10 +291,37 @@ export namespace UpdateRequest { SCORE = 2, MAX_SCORE = 3, CORDONED = 4, + ADMISSION_CONSTRAINTS = 5, } } +export class ModifyAdmissionConstraint extends jspb.Message { + getAdd(): boolean; + setAdd(value: boolean): ModifyAdmissionConstraint; + + hasConstraint(): boolean; + clearConstraint(): void; + getConstraint(): AdmissionConstraint | undefined; + setConstraint(value?: AdmissionConstraint): ModifyAdmissionConstraint; + + serializeBinary(): Uint8Array; + toObject(includeInstance?: boolean): ModifyAdmissionConstraint.AsObject; + static toObject(includeInstance: boolean, msg: ModifyAdmissionConstraint): ModifyAdmissionConstraint.AsObject; + static extensions: {[key: number]: jspb.ExtensionFieldInfo}; + static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo}; + static serializeBinaryToWriter(message: ModifyAdmissionConstraint, writer: jspb.BinaryWriter): void; + static deserializeBinary(bytes: Uint8Array): ModifyAdmissionConstraint; + static deserializeBinaryFromReader(message: ModifyAdmissionConstraint, reader: jspb.BinaryReader): ModifyAdmissionConstraint; +} + +export namespace ModifyAdmissionConstraint { + export type AsObject = { + add: boolean, + constraint?: AdmissionConstraint.AsObject, + } +} + export class UpdateResponse extends jspb.Message { serializeBinary(): Uint8Array; diff --git a/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.js b/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.js index b3f7889b747f2f..9aa7b33b076259 100644 --- a/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.js +++ b/components/ws-manager-bridge-api/typescript/src/cluster-service_pb.js @@ -21,12 +21,17 @@ var jspb = require('google-protobuf'); var goog = jspb; var global = Function('return this')(); +goog.exportSymbol('proto.workspacemanagerbridge.AdmissionConstraint', null, global); +goog.exportSymbol('proto.workspacemanagerbridge.AdmissionConstraint.ConstraintCase', null, global); +goog.exportSymbol('proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview', null, global); +goog.exportSymbol('proto.workspacemanagerbridge.AdmissionConstraint.HasPermission', null, global); goog.exportSymbol('proto.workspacemanagerbridge.ClusterState', null, global); goog.exportSymbol('proto.workspacemanagerbridge.ClusterStatus', null, global); goog.exportSymbol('proto.workspacemanagerbridge.DeregisterRequest', null, global); goog.exportSymbol('proto.workspacemanagerbridge.DeregisterResponse', null, global); goog.exportSymbol('proto.workspacemanagerbridge.ListRequest', null, global); goog.exportSymbol('proto.workspacemanagerbridge.ListResponse', null, global); +goog.exportSymbol('proto.workspacemanagerbridge.ModifyAdmissionConstraint', null, global); goog.exportSymbol('proto.workspacemanagerbridge.Preferability', null, global); goog.exportSymbol('proto.workspacemanagerbridge.RegisterRequest', null, global); goog.exportSymbol('proto.workspacemanagerbridge.RegisterResponse', null, global); @@ -46,7 +51,7 @@ goog.exportSymbol('proto.workspacemanagerbridge.UpdateResponse', null, global); * @constructor */ proto.workspacemanagerbridge.RegisterRequest = function(opt_data) { - jspb.Message.initialize(this, opt_data, 0, -1, null, null); + jspb.Message.initialize(this, opt_data, 0, -1, proto.workspacemanagerbridge.RegisterRequest.repeatedFields_, null); }; goog.inherits(proto.workspacemanagerbridge.RegisterRequest, jspb.Message); if (goog.DEBUG && !COMPILED) { @@ -129,9 +134,72 @@ if (goog.DEBUG && !COMPILED) { * @extends {jspb.Message} * @constructor */ -proto.workspacemanagerbridge.ClusterStatus = function(opt_data) { +proto.workspacemanagerbridge.AdmissionConstraint = function(opt_data) { + jspb.Message.initialize(this, opt_data, 0, -1, null, proto.workspacemanagerbridge.AdmissionConstraint.oneofGroups_); +}; +goog.inherits(proto.workspacemanagerbridge.AdmissionConstraint, jspb.Message); +if (goog.DEBUG && !COMPILED) { + /** + * @public + * @override + */ + proto.workspacemanagerbridge.AdmissionConstraint.displayName = 'proto.workspacemanagerbridge.AdmissionConstraint'; +} +/** + * Generated by JsPbCodeGenerator. + * @param {Array=} opt_data Optional initial data array, typically from a + * server response, or constructed directly in Javascript. The array is used + * in place and becomes part of the constructed object. It is not cloned. + * If no data is provided, the constructed object will be empty, but still + * valid. + * @extends {jspb.Message} + * @constructor + */ +proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview = function(opt_data) { + jspb.Message.initialize(this, opt_data, 0, -1, null, null); +}; +goog.inherits(proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview, jspb.Message); +if (goog.DEBUG && !COMPILED) { + /** + * @public + * @override + */ + proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.displayName = 'proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview'; +} +/** + * Generated by JsPbCodeGenerator. + * @param {Array=} opt_data Optional initial data array, typically from a + * server response, or constructed directly in Javascript. The array is used + * in place and becomes part of the constructed object. It is not cloned. + * If no data is provided, the constructed object will be empty, but still + * valid. + * @extends {jspb.Message} + * @constructor + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission = function(opt_data) { jspb.Message.initialize(this, opt_data, 0, -1, null, null); }; +goog.inherits(proto.workspacemanagerbridge.AdmissionConstraint.HasPermission, jspb.Message); +if (goog.DEBUG && !COMPILED) { + /** + * @public + * @override + */ + proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.displayName = 'proto.workspacemanagerbridge.AdmissionConstraint.HasPermission'; +} +/** + * Generated by JsPbCodeGenerator. + * @param {Array=} opt_data Optional initial data array, typically from a + * server response, or constructed directly in Javascript. The array is used + * in place and becomes part of the constructed object. It is not cloned. + * If no data is provided, the constructed object will be empty, but still + * valid. + * @extends {jspb.Message} + * @constructor + */ +proto.workspacemanagerbridge.ClusterStatus = function(opt_data) { + jspb.Message.initialize(this, opt_data, 0, -1, proto.workspacemanagerbridge.ClusterStatus.repeatedFields_, null); +}; goog.inherits(proto.workspacemanagerbridge.ClusterStatus, jspb.Message); if (goog.DEBUG && !COMPILED) { /** @@ -161,6 +229,27 @@ if (goog.DEBUG && !COMPILED) { */ proto.workspacemanagerbridge.UpdateRequest.displayName = 'proto.workspacemanagerbridge.UpdateRequest'; } +/** + * Generated by JsPbCodeGenerator. + * @param {Array=} opt_data Optional initial data array, typically from a + * server response, or constructed directly in Javascript. The array is used + * in place and becomes part of the constructed object. It is not cloned. + * If no data is provided, the constructed object will be empty, but still + * valid. + * @extends {jspb.Message} + * @constructor + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint = function(opt_data) { + jspb.Message.initialize(this, opt_data, 0, -1, null, null); +}; +goog.inherits(proto.workspacemanagerbridge.ModifyAdmissionConstraint, jspb.Message); +if (goog.DEBUG && !COMPILED) { + /** + * @public + * @override + */ + proto.workspacemanagerbridge.ModifyAdmissionConstraint.displayName = 'proto.workspacemanagerbridge.ModifyAdmissionConstraint'; +} /** * Generated by JsPbCodeGenerator. * @param {Array=} opt_data Optional initial data array, typically from a @@ -267,6 +356,13 @@ if (goog.DEBUG && !COMPILED) { proto.workspacemanagerbridge.ListResponse.displayName = 'proto.workspacemanagerbridge.ListResponse'; } +/** + * List of repeated fields within this message type. + * @private {!Array} + * @const + */ +proto.workspacemanagerbridge.RegisterRequest.repeatedFields_ = [5]; + if (jspb.Message.GENERATE_TO_OBJECT) { @@ -301,7 +397,9 @@ proto.workspacemanagerbridge.RegisterRequest.toObject = function(includeInstance name: jspb.Message.getFieldWithDefault(msg, 1, ""), url: jspb.Message.getFieldWithDefault(msg, 2, ""), tls: (f = msg.getTls()) && proto.workspacemanagerbridge.TlsConfig.toObject(includeInstance, f), - hints: (f = msg.getHints()) && proto.workspacemanagerbridge.RegistrationHints.toObject(includeInstance, f) + hints: (f = msg.getHints()) && proto.workspacemanagerbridge.RegistrationHints.toObject(includeInstance, f), + admissionConstraintsList: jspb.Message.toObjectList(msg.getAdmissionConstraintsList(), + proto.workspacemanagerbridge.AdmissionConstraint.toObject, includeInstance) }; if (includeInstance) { @@ -356,6 +454,11 @@ proto.workspacemanagerbridge.RegisterRequest.deserializeBinaryFromReader = funct reader.readMessage(value,proto.workspacemanagerbridge.RegistrationHints.deserializeBinaryFromReader); msg.setHints(value); break; + case 5: + var value = new proto.workspacemanagerbridge.AdmissionConstraint; + reader.readMessage(value,proto.workspacemanagerbridge.AdmissionConstraint.deserializeBinaryFromReader); + msg.addAdmissionConstraints(value); + break; default: reader.skipField(); break; @@ -415,6 +518,14 @@ proto.workspacemanagerbridge.RegisterRequest.serializeBinaryToWriter = function( proto.workspacemanagerbridge.RegistrationHints.serializeBinaryToWriter ); } + f = message.getAdmissionConstraintsList(); + if (f.length > 0) { + writer.writeRepeatedMessage( + 5, + f, + proto.workspacemanagerbridge.AdmissionConstraint.serializeBinaryToWriter + ); + } }; @@ -528,6 +639,44 @@ proto.workspacemanagerbridge.RegisterRequest.prototype.hasHints = function() { }; +/** + * repeated AdmissionConstraint admission_constraints = 5; + * @return {!Array} + */ +proto.workspacemanagerbridge.RegisterRequest.prototype.getAdmissionConstraintsList = function() { + return /** @type{!Array} */ ( + jspb.Message.getRepeatedWrapperField(this, proto.workspacemanagerbridge.AdmissionConstraint, 5)); +}; + + +/** + * @param {!Array} value + * @return {!proto.workspacemanagerbridge.RegisterRequest} returns this +*/ +proto.workspacemanagerbridge.RegisterRequest.prototype.setAdmissionConstraintsList = function(value) { + return jspb.Message.setRepeatedWrapperField(this, 5, value); +}; + + +/** + * @param {!proto.workspacemanagerbridge.AdmissionConstraint=} opt_value + * @param {number=} opt_index + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} + */ +proto.workspacemanagerbridge.RegisterRequest.prototype.addAdmissionConstraints = function(opt_value, opt_index) { + return jspb.Message.addToRepeatedWrapperField(this, 5, opt_value, proto.workspacemanagerbridge.AdmissionConstraint, opt_index); +}; + + +/** + * Clears the list making it empty but non-null. + * @return {!proto.workspacemanagerbridge.RegisterRequest} returns this + */ +proto.workspacemanagerbridge.RegisterRequest.prototype.clearAdmissionConstraintsList = function() { + return this.setAdmissionConstraintsList([]); +}; + + @@ -1010,6 +1159,32 @@ proto.workspacemanagerbridge.RegistrationHints.prototype.setGovern = function(va +/** + * Oneof group definitions for this message. Each group defines the field + * numbers belonging to that group. When of these fields' value is set, all + * other fields in the group are cleared. During deserialization, if multiple + * fields are encountered for a group, only the last value seen will be kept. + * @private {!Array>} + * @const + */ +proto.workspacemanagerbridge.AdmissionConstraint.oneofGroups_ = [[1,2]]; + +/** + * @enum {number} + */ +proto.workspacemanagerbridge.AdmissionConstraint.ConstraintCase = { + CONSTRAINT_NOT_SET: 0, + HAS_FEATURE_PREVIEW: 1, + HAS_PERMISSION: 2 +}; + +/** + * @return {proto.workspacemanagerbridge.AdmissionConstraint.ConstraintCase} + */ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.getConstraintCase = function() { + return /** @type {proto.workspacemanagerbridge.AdmissionConstraint.ConstraintCase} */(jspb.Message.computeOneofCase(this, proto.workspacemanagerbridge.AdmissionConstraint.oneofGroups_[0])); +}; + if (jspb.Message.GENERATE_TO_OBJECT) { @@ -1025,8 +1200,8 @@ if (jspb.Message.GENERATE_TO_OBJECT) { * http://goto/soy-param-migration * @return {!Object} */ -proto.workspacemanagerbridge.ClusterStatus.prototype.toObject = function(opt_includeInstance) { - return proto.workspacemanagerbridge.ClusterStatus.toObject(opt_includeInstance, this); +proto.workspacemanagerbridge.AdmissionConstraint.prototype.toObject = function(opt_includeInstance) { + return proto.workspacemanagerbridge.AdmissionConstraint.toObject(opt_includeInstance, this); }; @@ -1035,18 +1210,14 @@ proto.workspacemanagerbridge.ClusterStatus.prototype.toObject = function(opt_inc * @param {boolean|undefined} includeInstance Deprecated. Whether to include * the JSPB instance for transitional soy proto support: * http://goto/soy-param-migration - * @param {!proto.workspacemanagerbridge.ClusterStatus} msg The msg instance to transform. + * @param {!proto.workspacemanagerbridge.AdmissionConstraint} msg The msg instance to transform. * @return {!Object} * @suppress {unusedLocalVariables} f is only used for nested messages */ -proto.workspacemanagerbridge.ClusterStatus.toObject = function(includeInstance, msg) { +proto.workspacemanagerbridge.AdmissionConstraint.toObject = function(includeInstance, msg) { var f, obj = { - name: jspb.Message.getFieldWithDefault(msg, 1, ""), - url: jspb.Message.getFieldWithDefault(msg, 2, ""), - state: jspb.Message.getFieldWithDefault(msg, 3, 0), - score: jspb.Message.getFieldWithDefault(msg, 4, 0), - maxScore: jspb.Message.getFieldWithDefault(msg, 5, 0), - governed: jspb.Message.getBooleanFieldWithDefault(msg, 6, false) + hasFeaturePreview: (f = msg.getHasFeaturePreview()) && proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.toObject(includeInstance, f), + hasPermission: (f = msg.getHasPermission()) && proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.toObject(includeInstance, f) }; if (includeInstance) { @@ -1060,23 +1231,23 @@ proto.workspacemanagerbridge.ClusterStatus.toObject = function(includeInstance, /** * Deserializes binary data (in protobuf wire format). * @param {jspb.ByteSource} bytes The bytes to deserialize. - * @return {!proto.workspacemanagerbridge.ClusterStatus} + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} */ -proto.workspacemanagerbridge.ClusterStatus.deserializeBinary = function(bytes) { +proto.workspacemanagerbridge.AdmissionConstraint.deserializeBinary = function(bytes) { var reader = new jspb.BinaryReader(bytes); - var msg = new proto.workspacemanagerbridge.ClusterStatus; - return proto.workspacemanagerbridge.ClusterStatus.deserializeBinaryFromReader(msg, reader); + var msg = new proto.workspacemanagerbridge.AdmissionConstraint; + return proto.workspacemanagerbridge.AdmissionConstraint.deserializeBinaryFromReader(msg, reader); }; /** * Deserializes binary data (in protobuf wire format) from the * given reader into the given message object. - * @param {!proto.workspacemanagerbridge.ClusterStatus} msg The message object to deserialize into. + * @param {!proto.workspacemanagerbridge.AdmissionConstraint} msg The message object to deserialize into. * @param {!jspb.BinaryReader} reader The BinaryReader to use. - * @return {!proto.workspacemanagerbridge.ClusterStatus} + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} */ -proto.workspacemanagerbridge.ClusterStatus.deserializeBinaryFromReader = function(msg, reader) { +proto.workspacemanagerbridge.AdmissionConstraint.deserializeBinaryFromReader = function(msg, reader) { while (reader.nextField()) { if (reader.isEndGroup()) { break; @@ -1084,28 +1255,14 @@ proto.workspacemanagerbridge.ClusterStatus.deserializeBinaryFromReader = functio var field = reader.getFieldNumber(); switch (field) { case 1: - var value = /** @type {string} */ (reader.readString()); - msg.setName(value); + var value = new proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview; + reader.readMessage(value,proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.deserializeBinaryFromReader); + msg.setHasFeaturePreview(value); break; case 2: - var value = /** @type {string} */ (reader.readString()); - msg.setUrl(value); - break; - case 3: - var value = /** @type {!proto.workspacemanagerbridge.ClusterState} */ (reader.readEnum()); - msg.setState(value); - break; - case 4: - var value = /** @type {number} */ (reader.readInt32()); - msg.setScore(value); - break; - case 5: - var value = /** @type {number} */ (reader.readInt32()); - msg.setMaxScore(value); - break; - case 6: - var value = /** @type {boolean} */ (reader.readBool()); - msg.setGoverned(value); + var value = new proto.workspacemanagerbridge.AdmissionConstraint.HasPermission; + reader.readMessage(value,proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.deserializeBinaryFromReader); + msg.setHasPermission(value); break; default: reader.skipField(); @@ -1120,9 +1277,9 @@ proto.workspacemanagerbridge.ClusterStatus.deserializeBinaryFromReader = functio * Serializes the message to binary data (in protobuf wire format). * @return {!Uint8Array} */ -proto.workspacemanagerbridge.ClusterStatus.prototype.serializeBinary = function() { +proto.workspacemanagerbridge.AdmissionConstraint.prototype.serializeBinary = function() { var writer = new jspb.BinaryWriter(); - proto.workspacemanagerbridge.ClusterStatus.serializeBinaryToWriter(this, writer); + proto.workspacemanagerbridge.AdmissionConstraint.serializeBinaryToWriter(this, writer); return writer.getResultBuffer(); }; @@ -1130,86 +1287,571 @@ proto.workspacemanagerbridge.ClusterStatus.prototype.serializeBinary = function( /** * Serializes the given message to binary data (in protobuf wire * format), writing to the given BinaryWriter. - * @param {!proto.workspacemanagerbridge.ClusterStatus} message + * @param {!proto.workspacemanagerbridge.AdmissionConstraint} message * @param {!jspb.BinaryWriter} writer * @suppress {unusedLocalVariables} f is only used for nested messages */ -proto.workspacemanagerbridge.ClusterStatus.serializeBinaryToWriter = function(message, writer) { +proto.workspacemanagerbridge.AdmissionConstraint.serializeBinaryToWriter = function(message, writer) { var f = undefined; - f = message.getName(); - if (f.length > 0) { - writer.writeString( + f = message.getHasFeaturePreview(); + if (f != null) { + writer.writeMessage( 1, - f + f, + proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.serializeBinaryToWriter ); } - f = message.getUrl(); - if (f.length > 0) { - writer.writeString( + f = message.getHasPermission(); + if (f != null) { + writer.writeMessage( 2, - f - ); - } - f = message.getState(); - if (f !== 0.0) { - writer.writeEnum( - 3, - f - ); - } - f = message.getScore(); - if (f !== 0) { - writer.writeInt32( - 4, - f - ); - } - f = message.getMaxScore(); - if (f !== 0) { - writer.writeInt32( - 5, - f - ); - } - f = message.getGoverned(); - if (f) { - writer.writeBool( - 6, - f + f, + proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.serializeBinaryToWriter ); } }; + + + +if (jspb.Message.GENERATE_TO_OBJECT) { /** - * optional string name = 1; - * @return {string} + * Creates an object representation of this proto. + * Field names that are reserved in JavaScript and will be renamed to pb_name. + * Optional fields that are not set will be set to undefined. + * To access a reserved field use, foo.pb_, eg, foo.pb_default. + * For the list of reserved names please see: + * net/proto2/compiler/js/internal/generator.cc#kKeyword. + * @param {boolean=} opt_includeInstance Deprecated. whether to include the + * JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @return {!Object} */ -proto.workspacemanagerbridge.ClusterStatus.prototype.getName = function() { - return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 1, "")); +proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.prototype.toObject = function(opt_includeInstance) { + return proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.toObject(opt_includeInstance, this); }; /** - * @param {string} value - * @return {!proto.workspacemanagerbridge.ClusterStatus} returns this + * Static version of the {@see toObject} method. + * @param {boolean|undefined} includeInstance Deprecated. Whether to include + * the JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @param {!proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview} msg The msg instance to transform. + * @return {!Object} + * @suppress {unusedLocalVariables} f is only used for nested messages */ -proto.workspacemanagerbridge.ClusterStatus.prototype.setName = function(value) { - return jspb.Message.setProto3StringField(this, 1, value); +proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.toObject = function(includeInstance, msg) { + var f, obj = { + + }; + + if (includeInstance) { + obj.$jspbMessageInstance = msg; + } + return obj; }; +} /** - * optional string url = 2; - * @return {string} + * Deserializes binary data (in protobuf wire format). + * @param {jspb.ByteSource} bytes The bytes to deserialize. + * @return {!proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview} */ -proto.workspacemanagerbridge.ClusterStatus.prototype.getUrl = function() { - return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 2, "")); +proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.deserializeBinary = function(bytes) { + var reader = new jspb.BinaryReader(bytes); + var msg = new proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview; + return proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.deserializeBinaryFromReader(msg, reader); }; /** - * @param {string} value + * Deserializes binary data (in protobuf wire format) from the + * given reader into the given message object. + * @param {!proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview} msg The message object to deserialize into. + * @param {!jspb.BinaryReader} reader The BinaryReader to use. + * @return {!proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview} + */ +proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.deserializeBinaryFromReader = function(msg, reader) { + while (reader.nextField()) { + if (reader.isEndGroup()) { + break; + } + var field = reader.getFieldNumber(); + switch (field) { + default: + reader.skipField(); + break; + } + } + return msg; +}; + + +/** + * Serializes the message to binary data (in protobuf wire format). + * @return {!Uint8Array} + */ +proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.prototype.serializeBinary = function() { + var writer = new jspb.BinaryWriter(); + proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.serializeBinaryToWriter(this, writer); + return writer.getResultBuffer(); +}; + + +/** + * Serializes the given message to binary data (in protobuf wire + * format), writing to the given BinaryWriter. + * @param {!proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview} message + * @param {!jspb.BinaryWriter} writer + * @suppress {unusedLocalVariables} f is only used for nested messages + */ +proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview.serializeBinaryToWriter = function(message, writer) { + var f = undefined; +}; + + + + + +if (jspb.Message.GENERATE_TO_OBJECT) { +/** + * Creates an object representation of this proto. + * Field names that are reserved in JavaScript and will be renamed to pb_name. + * Optional fields that are not set will be set to undefined. + * To access a reserved field use, foo.pb_, eg, foo.pb_default. + * For the list of reserved names please see: + * net/proto2/compiler/js/internal/generator.cc#kKeyword. + * @param {boolean=} opt_includeInstance Deprecated. whether to include the + * JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @return {!Object} + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.prototype.toObject = function(opt_includeInstance) { + return proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.toObject(opt_includeInstance, this); +}; + + +/** + * Static version of the {@see toObject} method. + * @param {boolean|undefined} includeInstance Deprecated. Whether to include + * the JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @param {!proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} msg The msg instance to transform. + * @return {!Object} + * @suppress {unusedLocalVariables} f is only used for nested messages + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.toObject = function(includeInstance, msg) { + var f, obj = { + permission: jspb.Message.getFieldWithDefault(msg, 1, "") + }; + + if (includeInstance) { + obj.$jspbMessageInstance = msg; + } + return obj; +}; +} + + +/** + * Deserializes binary data (in protobuf wire format). + * @param {jspb.ByteSource} bytes The bytes to deserialize. + * @return {!proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.deserializeBinary = function(bytes) { + var reader = new jspb.BinaryReader(bytes); + var msg = new proto.workspacemanagerbridge.AdmissionConstraint.HasPermission; + return proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.deserializeBinaryFromReader(msg, reader); +}; + + +/** + * Deserializes binary data (in protobuf wire format) from the + * given reader into the given message object. + * @param {!proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} msg The message object to deserialize into. + * @param {!jspb.BinaryReader} reader The BinaryReader to use. + * @return {!proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.deserializeBinaryFromReader = function(msg, reader) { + while (reader.nextField()) { + if (reader.isEndGroup()) { + break; + } + var field = reader.getFieldNumber(); + switch (field) { + case 1: + var value = /** @type {string} */ (reader.readString()); + msg.setPermission(value); + break; + default: + reader.skipField(); + break; + } + } + return msg; +}; + + +/** + * Serializes the message to binary data (in protobuf wire format). + * @return {!Uint8Array} + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.prototype.serializeBinary = function() { + var writer = new jspb.BinaryWriter(); + proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.serializeBinaryToWriter(this, writer); + return writer.getResultBuffer(); +}; + + +/** + * Serializes the given message to binary data (in protobuf wire + * format), writing to the given BinaryWriter. + * @param {!proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} message + * @param {!jspb.BinaryWriter} writer + * @suppress {unusedLocalVariables} f is only used for nested messages + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.serializeBinaryToWriter = function(message, writer) { + var f = undefined; + f = message.getPermission(); + if (f.length > 0) { + writer.writeString( + 1, + f + ); + } +}; + + +/** + * optional string permission = 1; + * @return {string} + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.prototype.getPermission = function() { + return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 1, "")); +}; + + +/** + * @param {string} value + * @return {!proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} returns this + */ +proto.workspacemanagerbridge.AdmissionConstraint.HasPermission.prototype.setPermission = function(value) { + return jspb.Message.setProto3StringField(this, 1, value); +}; + + +/** + * optional FeaturePreview has_feature_preview = 1; + * @return {?proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview} + */ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.getHasFeaturePreview = function() { + return /** @type{?proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview} */ ( + jspb.Message.getWrapperField(this, proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview, 1)); +}; + + +/** + * @param {?proto.workspacemanagerbridge.AdmissionConstraint.FeaturePreview|undefined} value + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} returns this +*/ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.setHasFeaturePreview = function(value) { + return jspb.Message.setOneofWrapperField(this, 1, proto.workspacemanagerbridge.AdmissionConstraint.oneofGroups_[0], value); +}; + + +/** + * Clears the message field making it undefined. + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} returns this + */ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.clearHasFeaturePreview = function() { + return this.setHasFeaturePreview(undefined); +}; + + +/** + * Returns whether this field is set. + * @return {boolean} + */ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.hasHasFeaturePreview = function() { + return jspb.Message.getField(this, 1) != null; +}; + + +/** + * optional HasPermission has_permission = 2; + * @return {?proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} + */ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.getHasPermission = function() { + return /** @type{?proto.workspacemanagerbridge.AdmissionConstraint.HasPermission} */ ( + jspb.Message.getWrapperField(this, proto.workspacemanagerbridge.AdmissionConstraint.HasPermission, 2)); +}; + + +/** + * @param {?proto.workspacemanagerbridge.AdmissionConstraint.HasPermission|undefined} value + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} returns this +*/ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.setHasPermission = function(value) { + return jspb.Message.setOneofWrapperField(this, 2, proto.workspacemanagerbridge.AdmissionConstraint.oneofGroups_[0], value); +}; + + +/** + * Clears the message field making it undefined. + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} returns this + */ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.clearHasPermission = function() { + return this.setHasPermission(undefined); +}; + + +/** + * Returns whether this field is set. + * @return {boolean} + */ +proto.workspacemanagerbridge.AdmissionConstraint.prototype.hasHasPermission = function() { + return jspb.Message.getField(this, 2) != null; +}; + + + +/** + * List of repeated fields within this message type. + * @private {!Array} + * @const + */ +proto.workspacemanagerbridge.ClusterStatus.repeatedFields_ = [7]; + + + +if (jspb.Message.GENERATE_TO_OBJECT) { +/** + * Creates an object representation of this proto. + * Field names that are reserved in JavaScript and will be renamed to pb_name. + * Optional fields that are not set will be set to undefined. + * To access a reserved field use, foo.pb_, eg, foo.pb_default. + * For the list of reserved names please see: + * net/proto2/compiler/js/internal/generator.cc#kKeyword. + * @param {boolean=} opt_includeInstance Deprecated. whether to include the + * JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @return {!Object} + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.toObject = function(opt_includeInstance) { + return proto.workspacemanagerbridge.ClusterStatus.toObject(opt_includeInstance, this); +}; + + +/** + * Static version of the {@see toObject} method. + * @param {boolean|undefined} includeInstance Deprecated. Whether to include + * the JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @param {!proto.workspacemanagerbridge.ClusterStatus} msg The msg instance to transform. + * @return {!Object} + * @suppress {unusedLocalVariables} f is only used for nested messages + */ +proto.workspacemanagerbridge.ClusterStatus.toObject = function(includeInstance, msg) { + var f, obj = { + name: jspb.Message.getFieldWithDefault(msg, 1, ""), + url: jspb.Message.getFieldWithDefault(msg, 2, ""), + state: jspb.Message.getFieldWithDefault(msg, 3, 0), + score: jspb.Message.getFieldWithDefault(msg, 4, 0), + maxScore: jspb.Message.getFieldWithDefault(msg, 5, 0), + governed: jspb.Message.getBooleanFieldWithDefault(msg, 6, false), + admissionConstraintsList: jspb.Message.toObjectList(msg.getAdmissionConstraintsList(), + proto.workspacemanagerbridge.AdmissionConstraint.toObject, includeInstance), + pb_static: jspb.Message.getBooleanFieldWithDefault(msg, 8, false) + }; + + if (includeInstance) { + obj.$jspbMessageInstance = msg; + } + return obj; +}; +} + + +/** + * Deserializes binary data (in protobuf wire format). + * @param {jspb.ByteSource} bytes The bytes to deserialize. + * @return {!proto.workspacemanagerbridge.ClusterStatus} + */ +proto.workspacemanagerbridge.ClusterStatus.deserializeBinary = function(bytes) { + var reader = new jspb.BinaryReader(bytes); + var msg = new proto.workspacemanagerbridge.ClusterStatus; + return proto.workspacemanagerbridge.ClusterStatus.deserializeBinaryFromReader(msg, reader); +}; + + +/** + * Deserializes binary data (in protobuf wire format) from the + * given reader into the given message object. + * @param {!proto.workspacemanagerbridge.ClusterStatus} msg The message object to deserialize into. + * @param {!jspb.BinaryReader} reader The BinaryReader to use. + * @return {!proto.workspacemanagerbridge.ClusterStatus} + */ +proto.workspacemanagerbridge.ClusterStatus.deserializeBinaryFromReader = function(msg, reader) { + while (reader.nextField()) { + if (reader.isEndGroup()) { + break; + } + var field = reader.getFieldNumber(); + switch (field) { + case 1: + var value = /** @type {string} */ (reader.readString()); + msg.setName(value); + break; + case 2: + var value = /** @type {string} */ (reader.readString()); + msg.setUrl(value); + break; + case 3: + var value = /** @type {!proto.workspacemanagerbridge.ClusterState} */ (reader.readEnum()); + msg.setState(value); + break; + case 4: + var value = /** @type {number} */ (reader.readInt32()); + msg.setScore(value); + break; + case 5: + var value = /** @type {number} */ (reader.readInt32()); + msg.setMaxScore(value); + break; + case 6: + var value = /** @type {boolean} */ (reader.readBool()); + msg.setGoverned(value); + break; + case 7: + var value = new proto.workspacemanagerbridge.AdmissionConstraint; + reader.readMessage(value,proto.workspacemanagerbridge.AdmissionConstraint.deserializeBinaryFromReader); + msg.addAdmissionConstraints(value); + break; + case 8: + var value = /** @type {boolean} */ (reader.readBool()); + msg.setStatic(value); + break; + default: + reader.skipField(); + break; + } + } + return msg; +}; + + +/** + * Serializes the message to binary data (in protobuf wire format). + * @return {!Uint8Array} + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.serializeBinary = function() { + var writer = new jspb.BinaryWriter(); + proto.workspacemanagerbridge.ClusterStatus.serializeBinaryToWriter(this, writer); + return writer.getResultBuffer(); +}; + + +/** + * Serializes the given message to binary data (in protobuf wire + * format), writing to the given BinaryWriter. + * @param {!proto.workspacemanagerbridge.ClusterStatus} message + * @param {!jspb.BinaryWriter} writer + * @suppress {unusedLocalVariables} f is only used for nested messages + */ +proto.workspacemanagerbridge.ClusterStatus.serializeBinaryToWriter = function(message, writer) { + var f = undefined; + f = message.getName(); + if (f.length > 0) { + writer.writeString( + 1, + f + ); + } + f = message.getUrl(); + if (f.length > 0) { + writer.writeString( + 2, + f + ); + } + f = message.getState(); + if (f !== 0.0) { + writer.writeEnum( + 3, + f + ); + } + f = message.getScore(); + if (f !== 0) { + writer.writeInt32( + 4, + f + ); + } + f = message.getMaxScore(); + if (f !== 0) { + writer.writeInt32( + 5, + f + ); + } + f = message.getGoverned(); + if (f) { + writer.writeBool( + 6, + f + ); + } + f = message.getAdmissionConstraintsList(); + if (f.length > 0) { + writer.writeRepeatedMessage( + 7, + f, + proto.workspacemanagerbridge.AdmissionConstraint.serializeBinaryToWriter + ); + } + f = message.getStatic(); + if (f) { + writer.writeBool( + 8, + f + ); + } +}; + + +/** + * optional string name = 1; + * @return {string} + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.getName = function() { + return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 1, "")); +}; + + +/** + * @param {string} value + * @return {!proto.workspacemanagerbridge.ClusterStatus} returns this + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.setName = function(value) { + return jspb.Message.setProto3StringField(this, 1, value); +}; + + +/** + * optional string url = 2; + * @return {string} + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.getUrl = function() { + return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 2, "")); +}; + + +/** + * @param {string} value * @return {!proto.workspacemanagerbridge.ClusterStatus} returns this */ proto.workspacemanagerbridge.ClusterStatus.prototype.setUrl = function(value) { @@ -1289,6 +1931,62 @@ proto.workspacemanagerbridge.ClusterStatus.prototype.setGoverned = function(valu }; +/** + * repeated AdmissionConstraint admission_constraints = 7; + * @return {!Array} + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.getAdmissionConstraintsList = function() { + return /** @type{!Array} */ ( + jspb.Message.getRepeatedWrapperField(this, proto.workspacemanagerbridge.AdmissionConstraint, 7)); +}; + + +/** + * @param {!Array} value + * @return {!proto.workspacemanagerbridge.ClusterStatus} returns this +*/ +proto.workspacemanagerbridge.ClusterStatus.prototype.setAdmissionConstraintsList = function(value) { + return jspb.Message.setRepeatedWrapperField(this, 7, value); +}; + + +/** + * @param {!proto.workspacemanagerbridge.AdmissionConstraint=} opt_value + * @param {number=} opt_index + * @return {!proto.workspacemanagerbridge.AdmissionConstraint} + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.addAdmissionConstraints = function(opt_value, opt_index) { + return jspb.Message.addToRepeatedWrapperField(this, 7, opt_value, proto.workspacemanagerbridge.AdmissionConstraint, opt_index); +}; + + +/** + * Clears the list making it empty but non-null. + * @return {!proto.workspacemanagerbridge.ClusterStatus} returns this + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.clearAdmissionConstraintsList = function() { + return this.setAdmissionConstraintsList([]); +}; + + +/** + * optional bool static = 8; + * @return {boolean} + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.getStatic = function() { + return /** @type {boolean} */ (jspb.Message.getBooleanFieldWithDefault(this, 8, false)); +}; + + +/** + * @param {boolean} value + * @return {!proto.workspacemanagerbridge.ClusterStatus} returns this + */ +proto.workspacemanagerbridge.ClusterStatus.prototype.setStatic = function(value) { + return jspb.Message.setProto3BooleanField(this, 8, value); +}; + + /** * Oneof group definitions for this message. Each group defines the field @@ -1298,7 +1996,7 @@ proto.workspacemanagerbridge.ClusterStatus.prototype.setGoverned = function(valu * @private {!Array>} * @const */ -proto.workspacemanagerbridge.UpdateRequest.oneofGroups_ = [[2,3,4]]; +proto.workspacemanagerbridge.UpdateRequest.oneofGroups_ = [[2,3,4,5]]; /** * @enum {number} @@ -1307,7 +2005,8 @@ proto.workspacemanagerbridge.UpdateRequest.PropertyCase = { PROPERTY_NOT_SET: 0, SCORE: 2, MAX_SCORE: 3, - CORDONED: 4 + CORDONED: 4, + ADMISSION_CONSTRAINTS: 5 }; /** @@ -1351,7 +2050,8 @@ proto.workspacemanagerbridge.UpdateRequest.toObject = function(includeInstance, name: jspb.Message.getFieldWithDefault(msg, 1, ""), score: jspb.Message.getFieldWithDefault(msg, 2, 0), maxScore: jspb.Message.getFieldWithDefault(msg, 3, 0), - cordoned: jspb.Message.getBooleanFieldWithDefault(msg, 4, false) + cordoned: jspb.Message.getBooleanFieldWithDefault(msg, 4, false), + admissionConstraints: (f = msg.getAdmissionConstraints()) && proto.workspacemanagerbridge.ModifyAdmissionConstraint.toObject(includeInstance, f) }; if (includeInstance) { @@ -1404,6 +2104,11 @@ proto.workspacemanagerbridge.UpdateRequest.deserializeBinaryFromReader = functio var value = /** @type {boolean} */ (reader.readBool()); msg.setCordoned(value); break; + case 5: + var value = new proto.workspacemanagerbridge.ModifyAdmissionConstraint; + reader.readMessage(value,proto.workspacemanagerbridge.ModifyAdmissionConstraint.deserializeBinaryFromReader); + msg.setAdmissionConstraints(value); + break; default: reader.skipField(); break; @@ -1461,6 +2166,14 @@ proto.workspacemanagerbridge.UpdateRequest.serializeBinaryToWriter = function(me f ); } + f = message.getAdmissionConstraints(); + if (f != null) { + writer.writeMessage( + 5, + f, + proto.workspacemanagerbridge.ModifyAdmissionConstraint.serializeBinaryToWriter + ); + } }; @@ -1590,6 +2303,224 @@ proto.workspacemanagerbridge.UpdateRequest.prototype.hasCordoned = function() { }; +/** + * optional ModifyAdmissionConstraint admission_constraints = 5; + * @return {?proto.workspacemanagerbridge.ModifyAdmissionConstraint} + */ +proto.workspacemanagerbridge.UpdateRequest.prototype.getAdmissionConstraints = function() { + return /** @type{?proto.workspacemanagerbridge.ModifyAdmissionConstraint} */ ( + jspb.Message.getWrapperField(this, proto.workspacemanagerbridge.ModifyAdmissionConstraint, 5)); +}; + + +/** + * @param {?proto.workspacemanagerbridge.ModifyAdmissionConstraint|undefined} value + * @return {!proto.workspacemanagerbridge.UpdateRequest} returns this +*/ +proto.workspacemanagerbridge.UpdateRequest.prototype.setAdmissionConstraints = function(value) { + return jspb.Message.setOneofWrapperField(this, 5, proto.workspacemanagerbridge.UpdateRequest.oneofGroups_[0], value); +}; + + +/** + * Clears the message field making it undefined. + * @return {!proto.workspacemanagerbridge.UpdateRequest} returns this + */ +proto.workspacemanagerbridge.UpdateRequest.prototype.clearAdmissionConstraints = function() { + return this.setAdmissionConstraints(undefined); +}; + + +/** + * Returns whether this field is set. + * @return {boolean} + */ +proto.workspacemanagerbridge.UpdateRequest.prototype.hasAdmissionConstraints = function() { + return jspb.Message.getField(this, 5) != null; +}; + + + + + +if (jspb.Message.GENERATE_TO_OBJECT) { +/** + * Creates an object representation of this proto. + * Field names that are reserved in JavaScript and will be renamed to pb_name. + * Optional fields that are not set will be set to undefined. + * To access a reserved field use, foo.pb_, eg, foo.pb_default. + * For the list of reserved names please see: + * net/proto2/compiler/js/internal/generator.cc#kKeyword. + * @param {boolean=} opt_includeInstance Deprecated. whether to include the + * JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @return {!Object} + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.toObject = function(opt_includeInstance) { + return proto.workspacemanagerbridge.ModifyAdmissionConstraint.toObject(opt_includeInstance, this); +}; + + +/** + * Static version of the {@see toObject} method. + * @param {boolean|undefined} includeInstance Deprecated. Whether to include + * the JSPB instance for transitional soy proto support: + * http://goto/soy-param-migration + * @param {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} msg The msg instance to transform. + * @return {!Object} + * @suppress {unusedLocalVariables} f is only used for nested messages + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.toObject = function(includeInstance, msg) { + var f, obj = { + add: jspb.Message.getBooleanFieldWithDefault(msg, 1, false), + constraint: (f = msg.getConstraint()) && proto.workspacemanagerbridge.AdmissionConstraint.toObject(includeInstance, f) + }; + + if (includeInstance) { + obj.$jspbMessageInstance = msg; + } + return obj; +}; +} + + +/** + * Deserializes binary data (in protobuf wire format). + * @param {jspb.ByteSource} bytes The bytes to deserialize. + * @return {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.deserializeBinary = function(bytes) { + var reader = new jspb.BinaryReader(bytes); + var msg = new proto.workspacemanagerbridge.ModifyAdmissionConstraint; + return proto.workspacemanagerbridge.ModifyAdmissionConstraint.deserializeBinaryFromReader(msg, reader); +}; + + +/** + * Deserializes binary data (in protobuf wire format) from the + * given reader into the given message object. + * @param {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} msg The message object to deserialize into. + * @param {!jspb.BinaryReader} reader The BinaryReader to use. + * @return {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.deserializeBinaryFromReader = function(msg, reader) { + while (reader.nextField()) { + if (reader.isEndGroup()) { + break; + } + var field = reader.getFieldNumber(); + switch (field) { + case 1: + var value = /** @type {boolean} */ (reader.readBool()); + msg.setAdd(value); + break; + case 2: + var value = new proto.workspacemanagerbridge.AdmissionConstraint; + reader.readMessage(value,proto.workspacemanagerbridge.AdmissionConstraint.deserializeBinaryFromReader); + msg.setConstraint(value); + break; + default: + reader.skipField(); + break; + } + } + return msg; +}; + + +/** + * Serializes the message to binary data (in protobuf wire format). + * @return {!Uint8Array} + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.serializeBinary = function() { + var writer = new jspb.BinaryWriter(); + proto.workspacemanagerbridge.ModifyAdmissionConstraint.serializeBinaryToWriter(this, writer); + return writer.getResultBuffer(); +}; + + +/** + * Serializes the given message to binary data (in protobuf wire + * format), writing to the given BinaryWriter. + * @param {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} message + * @param {!jspb.BinaryWriter} writer + * @suppress {unusedLocalVariables} f is only used for nested messages + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.serializeBinaryToWriter = function(message, writer) { + var f = undefined; + f = message.getAdd(); + if (f) { + writer.writeBool( + 1, + f + ); + } + f = message.getConstraint(); + if (f != null) { + writer.writeMessage( + 2, + f, + proto.workspacemanagerbridge.AdmissionConstraint.serializeBinaryToWriter + ); + } +}; + + +/** + * optional bool add = 1; + * @return {boolean} + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.getAdd = function() { + return /** @type {boolean} */ (jspb.Message.getBooleanFieldWithDefault(this, 1, false)); +}; + + +/** + * @param {boolean} value + * @return {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} returns this + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.setAdd = function(value) { + return jspb.Message.setProto3BooleanField(this, 1, value); +}; + + +/** + * optional AdmissionConstraint constraint = 2; + * @return {?proto.workspacemanagerbridge.AdmissionConstraint} + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.getConstraint = function() { + return /** @type{?proto.workspacemanagerbridge.AdmissionConstraint} */ ( + jspb.Message.getWrapperField(this, proto.workspacemanagerbridge.AdmissionConstraint, 2)); +}; + + +/** + * @param {?proto.workspacemanagerbridge.AdmissionConstraint|undefined} value + * @return {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} returns this +*/ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.setConstraint = function(value) { + return jspb.Message.setWrapperField(this, 2, value); +}; + + +/** + * Clears the message field making it undefined. + * @return {!proto.workspacemanagerbridge.ModifyAdmissionConstraint} returns this + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.clearConstraint = function() { + return this.setConstraint(undefined); +}; + + +/** + * Returns whether this field is set. + * @return {boolean} + */ +proto.workspacemanagerbridge.ModifyAdmissionConstraint.prototype.hasConstraint = function() { + return jspb.Message.getField(this, 2) != null; +}; + + diff --git a/components/ws-manager-bridge/src/bridge-controller.ts b/components/ws-manager-bridge/src/bridge-controller.ts index 99bf663d3f9d74..9132a72c16f6aa 100644 --- a/components/ws-manager-bridge/src/bridge-controller.ts +++ b/components/ws-manager-bridge/src/bridge-controller.ts @@ -10,7 +10,7 @@ import { Configuration } from "./config"; import { WorkspaceManagerClientProvider } from '@gitpod/ws-manager/lib/client-provider'; import { WorkspaceManagerClientProviderSource } from '@gitpod/ws-manager/lib/client-provider-source'; import { log } from '@gitpod/gitpod-protocol/lib/util/logging'; -import { TLSConfig, WorkspaceClusterDB, WorkspaceClusterWoTls } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; +import { TLSConfig, WorkspaceClusterDB, WorkspaceClusterWoTLS } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; import { WorkspaceCluster } from "@gitpod/gitpod-protocol/lib/workspace-cluster"; import { Queue } from "@gitpod/gitpod-protocol"; @@ -98,9 +98,9 @@ export class BridgeController { return bridge; } - protected async getAllWorkspaceClusters(): Promise> { + protected async getAllWorkspaceClusters(): Promise> { const allInfos = await this.clientProvider.getAllWorkspaceClusters(); - const result: Map = new Map(); + const result: Map = new Map(); for (const cluster of allInfos) { result.set(cluster.name, cluster); } @@ -131,7 +131,7 @@ export class WorkspaceManagerClientProviderConfigSource implements WorkspaceMana return this.clusters.find(m => m.name === name); } - public async getAllWorkspaceClusters(): Promise { + public async getAllWorkspaceClusters(): Promise { return this.clusters; } diff --git a/components/ws-manager-bridge/src/cluster-service-server.ts b/components/ws-manager-bridge/src/cluster-service-server.ts index 409e96f59755c8..634ec378f9ba9f 100644 --- a/components/ws-manager-bridge/src/cluster-service-server.ts +++ b/components/ws-manager-bridge/src/cluster-service-server.ts @@ -6,7 +6,7 @@ import { Queue } from '@gitpod/gitpod-protocol'; import { log } from '@gitpod/gitpod-protocol/lib/util/logging'; -import { WorkspaceCluster, WorkspaceClusterDB, WorkspaceClusterState, TLSConfig } from '@gitpod/gitpod-protocol/lib/workspace-cluster'; +import { WorkspaceCluster, WorkspaceClusterDB, WorkspaceClusterState, TLSConfig, AdmissionConstraint, AdmissionConstraintHasRole, WorkspaceClusterWoTLS } from '@gitpod/gitpod-protocol/lib/workspace-cluster'; import { ClusterServiceService, ClusterState, @@ -20,10 +20,12 @@ import { RegisterRequest, RegisterResponse, UpdateRequest, - UpdateResponse + UpdateResponse, + AdmissionConstraint as GRPCAdmissionConstraint, } from '@gitpod/ws-manager-bridge-api/lib'; import { GetWorkspacesRequest } from '@gitpod/ws-manager/lib'; import { WorkspaceManagerClientProvider } from '@gitpod/ws-manager/lib/client-provider'; +import { WorkspaceManagerClientProviderCompositeSource, WorkspaceManagerClientProviderSource } from '@gitpod/ws-manager/lib/client-provider-source'; import * as grpc from "@grpc/grpc-js"; import { ServiceError as grpcServiceError } from '@grpc/grpc-js'; import { inject, injectable } from 'inversify'; @@ -52,6 +54,9 @@ export class ClusterService implements IClusterServiceServer { @inject(WorkspaceManagerClientProvider) protected readonly clientProvider: WorkspaceManagerClientProvider; + @inject(WorkspaceManagerClientProviderCompositeSource) + protected readonly allClientProvider: WorkspaceManagerClientProviderSource; + // using a queue to make sure we do concurrency right protected readonly queue: Queue = new Queue(); @@ -101,6 +106,8 @@ export class ClusterService implements IClusterServiceServer { key: req.tls.key }; + const admissionConstraints = call.request.getAdmissionConstraintsList().map(mapAdmissionConstraint).filter(c => !!c) as AdmissionConstraint[]; + const newCluster: WorkspaceCluster = { name: req.name, url: req.url, @@ -109,6 +116,7 @@ export class ClusterService implements IClusterServiceServer { maxScore: 100, govern, tls, + admissionConstraints }; // try to connect to validate the config. Throws an exception if it fails. @@ -152,6 +160,25 @@ export class ClusterService implements IClusterServiceServer { if (call.request.hasCordoned()) { cluster.state = mapCordoned(req.cordoned); } + if (call.request.hasAdmissionConstraints()) { + const mod = call.request.getAdmissionConstraints()!; + const c = mapAdmissionConstraint(mod.getConstraint()); + if (!!c) { + if (mod.getAdd()) { + cluster.admissionConstraints = (cluster.admissionConstraints || []).concat([c]); + } else { + cluster.admissionConstraints = cluster.admissionConstraints?.filter(v => { + if (v.type !== c.type) { + return true; + } + if (v.type === "has-permission" && v.permission === (c as AdmissionConstraintHasRole).permission) { + return true; + } + return false; + }) + } + } + } await this.db.save(cluster); this.triggerReconcile("update", req.name); @@ -181,17 +208,24 @@ export class ClusterService implements IClusterServiceServer { public list(call: grpc.ServerUnaryCall, callback: grpc.sendUnaryData) { this.queue.enqueue(async () => { try { - const allClusters = await this.db.findFiltered({}) - const response = new ListResponse(); - for (const cluster of allClusters) { - const clusterStatus = new ClusterStatus(); - clusterStatus.setName(cluster.name); - clusterStatus.setUrl(cluster.url); - clusterStatus.setState(mapClusterState(cluster.state)); - clusterStatus.setScore(cluster.score); - clusterStatus.setMaxScore(cluster.maxScore); - clusterStatus.setGoverned(cluster.govern); + + const dbClusterIdx = new Map(); + const allDBClusters = await this.db.findFiltered({}); + for (const cluster of allDBClusters) { + const clusterStatus = convertToGRPC(cluster); + response.addStatus(clusterStatus); + dbClusterIdx.set(cluster.name, true); + } + + const allCluster = await this.allClientProvider.getAllWorkspaceClusters(); + for (const cluster of allCluster) { + if (dbClusterIdx.get(cluster.name)) { + continue; + } + + const clusterStatus = convertToGRPC(cluster); + clusterStatus.setStatic(true); response.addStatus(clusterStatus); } @@ -210,6 +244,52 @@ export class ClusterService implements IClusterServiceServer { } } +function convertToGRPC(ws: WorkspaceClusterWoTLS): ClusterStatus { + const clusterStatus = new ClusterStatus(); + clusterStatus.setName(ws.name); + clusterStatus.setUrl(ws.url); + clusterStatus.setState(mapClusterState(ws.state)); + clusterStatus.setScore(ws.score); + clusterStatus.setMaxScore(ws.maxScore); + clusterStatus.setGoverned(ws.govern); + ws.admissionConstraints?.forEach(c => { + const constraint = new GRPCAdmissionConstraint(); + switch (c.type) { + case "has-feature-preview": + constraint.setHasFeaturePreview(new GRPCAdmissionConstraint.FeaturePreview()); + break; + case "has-permission": + const perm = new GRPCAdmissionConstraint.HasPermission(); + perm.setPermission(c.permission); + constraint.setHasPermission(perm); + break; + default: + return; + } + clusterStatus.addAdmissionConstraints(constraint); + }); + return clusterStatus; +} + +function mapAdmissionConstraint(c: GRPCAdmissionConstraint | undefined): AdmissionConstraint | undefined { + if (!c) { + return; + } + + if (c.hasHasFeaturePreview()) { + return {type: "has-feature-preview"}; + } + if (c.hasHasPermission()) { + const permission = c.getHasPermission()?.getPermission(); + if (!permission) { + return; + } + + return {type: "has-permission", permission}; + } + return; +} + function mapPreferabilityToScore(p: Preferability): number | undefined { switch (p) { case Preferability.PREFER: return 100; diff --git a/dev/gpctl/cmd/clusters-cordon.go b/dev/gpctl/cmd/clusters-cordon.go index 677e720390c6ae..84c11431d6c376 100644 --- a/dev/gpctl/cmd/clusters-cordon.go +++ b/dev/gpctl/cmd/clusters-cordon.go @@ -17,9 +17,8 @@ import ( // clustersCordonCmd represents the clustersCordonCmd command var clustersCordonCmd = &cobra.Command{ - Use: "cordon [cluster name]", + Use: "cordon --name [cluster name]", Short: "Cordon a cluster", - Args: cobra.ExactArgs(1), Run: func(cmd *cobra.Command, args []string) { ctx, cancel := context.WithCancel(context.Background()) defer cancel() @@ -30,7 +29,7 @@ var clustersCordonCmd = &cobra.Command{ } defer conn.Close() - name := args[0] + name := getClusterName() request := &api.UpdateRequest{Name: name, Property: &api.UpdateRequest_Cordoned{Cordoned: true}} _, err = client.Update(ctx, request) if err != nil && err != io.EOF { diff --git a/dev/gpctl/cmd/clusters-deregister.go b/dev/gpctl/cmd/clusters-deregister.go index 15bf2dcf402ec3..b4e37b80577cfc 100644 --- a/dev/gpctl/cmd/clusters-deregister.go +++ b/dev/gpctl/cmd/clusters-deregister.go @@ -17,10 +17,9 @@ import ( // clustersDeregisterCmd represents the clustersDeregisterCmd command var clustersDeregisterCmd = &cobra.Command{ - Use: "deregister [cluster name]", + Use: "deregister --name [cluster name]", Short: "Deregister a cluster", Long: "Deregisters the cluster [cluster name].", - Args: cobra.ExactArgs(1), Run: func(cmd *cobra.Command, args []string) { ctx, cancel := context.WithCancel(context.Background()) defer cancel() @@ -31,8 +30,7 @@ var clustersDeregisterCmd = &cobra.Command{ } defer conn.Close() - name := args[0] - + name := getClusterName() _, err = client.Deregister(ctx, &api.DeregisterRequest{Name: name}) if err != nil && err != io.EOF { log.Fatal(err) diff --git a/dev/gpctl/cmd/clusters-list.go b/dev/gpctl/cmd/clusters-list.go index 5ccfed9ae9c525..ebeb54e62332d2 100644 --- a/dev/gpctl/cmd/clusters-list.go +++ b/dev/gpctl/cmd/clusters-list.go @@ -33,9 +33,9 @@ var clustersListCmd = &cobra.Command{ log.Fatal(err) } - tpl := `NAME URL STATE SCORE MAX_SCORE GOVERNED + tpl := `NAME URL STATIC STATE SCORE GOVERNED ADMISSION CONSTRAINTS {{- range .Status }} -{{ .Name }} {{ .Url }} {{ .State }} {{ .Score }} {{ .MaxScore }} {{ .Governed -}} +{{ .Name }} {{ .Url }} {{ .Static }} {{ .State }} {{ .Score }} {{ .Governed }} {{ .AdmissionConstraints -}} {{ end }} ` getOutputFormat(tpl, "{..name}").Print(resp) diff --git a/dev/gpctl/cmd/clusters-swap.go b/dev/gpctl/cmd/clusters-swap.go new file mode 100644 index 00000000000000..55960cfec89148 --- /dev/null +++ b/dev/gpctl/cmd/clusters-swap.go @@ -0,0 +1,88 @@ +// Copyright (c) 2021 Gitpod GmbH. All rights reserved. +// Licensed under the GNU Affero General Public License (AGPL). +// See License-AGPL.txt in the project root for license information. + +package cmd + +import ( + "context" + "fmt" + "io" + + "github.com/spf13/cobra" + + "github.com/gitpod-io/gitpod/common-go/log" + "github.com/gitpod-io/gitpod/ws-manager-bridge/api" +) + +// clustersSwapCmd represents the clustersSwapCmd command +var clustersSwapCmd = &cobra.Command{ + Use: "swap [source cluster] [target cluster]", + Short: "Swaps the status and score of two clusters", + Long: "Swaps the status and score of two clusters. Beware: this is not an atomic operation.", + Args: cobra.ExactArgs(2), + Run: func(cmd *cobra.Command, args []string) { + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() + + conn, client, err := getClustersClient(ctx) + if err != nil { + log.WithError(err).Fatal("cannot connect") + } + defer conn.Close() + + resp, err := client.List(ctx, &api.ListRequest{}) + if err != nil { + log.Fatal(err) + } + var ( + src *api.ClusterStatus + dst *api.ClusterStatus + ) + for _, c := range resp.Status { + if c.Name == args[0] { + src = c + } + if c.Name == args[1] { + dst = c + } + } + if src == nil { + log.Fatal("source cluster \"%s\" not found", args[0]) + } + if dst == nil { + log.Fatal("destination cluster \"%s\" not found", args[1]) + } + if ignore, _ := cmd.Flags().GetBool("ignore-admission-constraints"); !ignore { + if len(src.AdmissionConstraints) > 0 || len(dst.AdmissionConstraints) > 0 { + log.Fatal("one of the clusters has admission constraints. Swapping their state/score is unlikely to have the desired effect. If you want to swap nonetheless, please remove the constraints or run with --ignore-admission-constraints") + } + } + if !src.Governed || !dst.Governed { + log.Fatal("can only swap goverened cluster") + } + if src.Static || dst.Static { + log.Fatal("can only swap non-static cluster") + } + + reqs := []*api.UpdateRequest{ + {Name: dst.Name, Property: &api.UpdateRequest_Cordoned{Cordoned: src.State == api.ClusterState_CORDONED}}, + {Name: dst.Name, Property: &api.UpdateRequest_Score{Score: src.Score}}, + {Name: src.Name, Property: &api.UpdateRequest_Cordoned{Cordoned: dst.State == api.ClusterState_CORDONED}}, + {Name: src.Name, Property: &api.UpdateRequest_Score{Score: dst.Score}}, + } + for _, r := range reqs { + _, err = client.Update(ctx, r) + if err != nil && err != io.EOF { + log.Fatal(err) + } + } + + fmt.Printf("updated '%s' to score=%d,cordoned=%v and %s to score=%d,cordoned=%v \n", src.Name, dst.Score, dst.State == api.ClusterState_CORDONED, dst.Name, src.Score, src.State == api.ClusterState_CORDONED) + }, +} + +func init() { + clustersCmd.AddCommand(clustersSwapCmd) + clustersSwapCmd.Flags().Bool("ignore-admission-constraints", false, "swap despite existing admission constraints") +} diff --git a/dev/gpctl/cmd/clusters-uncordon.go b/dev/gpctl/cmd/clusters-uncordon.go index 8b61bd78444793..650408cdec3977 100644 --- a/dev/gpctl/cmd/clusters-uncordon.go +++ b/dev/gpctl/cmd/clusters-uncordon.go @@ -17,9 +17,8 @@ import ( // clustersUncordonCmd represents the clustersUncordonCmd command var clustersUncordonCmd = &cobra.Command{ - Use: "uncordon [cluster name]", + Use: "uncordon --name [cluster name]", Short: "Un-cordon a cluster", - Args: cobra.ExactArgs(1), Run: func(cmd *cobra.Command, args []string) { ctx, cancel := context.WithCancel(context.Background()) defer cancel() @@ -30,7 +29,7 @@ var clustersUncordonCmd = &cobra.Command{ } defer conn.Close() - name := args[0] + name := getClusterName() request := &api.UpdateRequest{Name: name, Property: &api.UpdateRequest_Cordoned{Cordoned: false}} _, err = client.Update(ctx, request) if err != nil && err != io.EOF { diff --git a/dev/gpctl/cmd/clusters-update.go b/dev/gpctl/cmd/clusters-update.go index 07d46534df4878..3b6d45dc13b00a 100644 --- a/dev/gpctl/cmd/clusters-update.go +++ b/dev/gpctl/cmd/clusters-update.go @@ -9,6 +9,7 @@ import ( "fmt" "io" "strconv" + "strings" "github.com/spf13/cobra" @@ -18,11 +19,18 @@ import ( // clustersUpdateCmd represents the clustersUpdateCmd command var clustersUpdateCmd = &cobra.Command{ - Use: "update [cluster name] [property] [value]", + Use: "update --name [cluster name]", Short: "Update a cluster", - Long: "Updates the [property] (score, max_score, or crodoned) of the cluster [cluster name] with the new value [value].", - Args: cobra.ExactArgs(3), + Args: cobra.ExactArgs(1), +} + +var clustersUpdateScoreCmd = &cobra.Command{ + Use: "score ", + Short: "Update a cluster's score", + Args: cobra.ExactArgs(1), Run: func(cmd *cobra.Command, args []string) { + name := getClusterName() + ctx, cancel := context.WithCancel(context.Background()) defer cancel() @@ -32,39 +40,117 @@ var clustersUpdateCmd = &cobra.Command{ } defer conn.Close() - name := args[0] + value, err := strconv.Atoi(args[0]) + if err != nil { + log.Fatal(err) + } + request := &api.UpdateRequest{Name: name, Property: &api.UpdateRequest_Score{Score: int32(value)}} - var request *api.UpdateRequest - switch args[1] { - case "score": - value, err := strconv.Atoi(args[2]) - if err != nil { - log.Fatal(err) - } - request = &api.UpdateRequest{Name: name, Property: &api.UpdateRequest_Score{Score: int32(value)}} - case "max_score": - value, err := strconv.Atoi(args[2]) - if err != nil { - log.Fatal(err) + _, err = client.Update(ctx, request) + if err != nil && err != io.EOF { + log.Fatal(err) + } + + fmt.Printf("cluster '%s' updated with score=%s\n", name, args[0]) + }, +} + +var clustersUpdateMaxScoreCmd = &cobra.Command{ + Use: "max-score ", + Short: "Update a cluster's max score", + Args: cobra.ExactArgs(1), + Run: func(cmd *cobra.Command, args []string) { + name := getClusterName() + + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() + + conn, client, err := getClustersClient(ctx) + if err != nil { + log.WithError(err).Fatal("cannot connect") + } + defer conn.Close() + + value, err := strconv.Atoi(args[0]) + if err != nil { + log.Fatal(err) + } + request := &api.UpdateRequest{Name: name, Property: &api.UpdateRequest_MaxScore{MaxScore: int32(value)}} + + _, err = client.Update(ctx, request) + if err != nil && err != io.EOF { + log.Fatal(err) + } + + fmt.Printf("cluster '%s' updated with max_score=%s\n", name, args[0]) + }, +} + +var clustersUpdateAdmissionConstraintCmd = &cobra.Command{ + Use: "admission-constraint add|remove has-feature-preview|has-permission=", + Short: "Updates a cluster's admission constraints", + Args: cobra.ExactArgs(2), + Run: func(cmd *cobra.Command, args []string) { + name := getClusterName() + + var add bool + switch args[0] { + case "add": + add = true + case "remove": + add = false + default: + log.Fatalf("must be add or remove instead of \"%s\"", args[0]) + } + + request := &api.UpdateRequest{Name: name} + if args[1] == "has-feature-preview" { + request.Property = &api.UpdateRequest_AdmissionConstraints{ + AdmissionConstraints: &api.ModifyAdmissionConstraint{ + Add: add, + Constraint: &api.AdmissionConstraint{ + Constraint: &api.AdmissionConstraint_HasFeaturePreview{}, + }, + }, } - request = &api.UpdateRequest{Name: name, Property: &api.UpdateRequest_MaxScore{MaxScore: int32(value)}} - case "cordoned": - value, err := strconv.ParseBool(args[2]) - if err != nil { - log.Fatal(err) + } else if strings.HasPrefix(args[1], "has-permission=") { + request.Property = &api.UpdateRequest_AdmissionConstraints{ + AdmissionConstraints: &api.ModifyAdmissionConstraint{ + Add: add, + Constraint: &api.AdmissionConstraint{ + Constraint: &api.AdmissionConstraint_HasPermission_{ + HasPermission: &api.AdmissionConstraint_HasPermission{ + Permission: strings.TrimPrefix(args[1], "has-permission="), + }, + }, + }, + }, } - request = &api.UpdateRequest{Name: name, Property: &api.UpdateRequest_Cordoned{Cordoned: value}} + } else { + log.Fatalf("unknown constraint: %s", args[1]) + } + + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() + + conn, client, err := getClustersClient(ctx) + if err != nil { + log.WithError(err).Fatal("cannot connect") } + defer conn.Close() _, err = client.Update(ctx, request) if err != nil && err != io.EOF { log.Fatal(err) } - fmt.Printf("cluster '%s' updated with %s=%s\n", name, args[1], args[2]) + fmt.Printf("cluster '%s' updated with admission constraint %s\n", name, request.GetAdmissionConstraints()) }, } func init() { clustersCmd.AddCommand(clustersUpdateCmd) + clustersUpdateCmd.AddCommand(clustersUpdateScoreCmd) + clustersUpdateCmd.AddCommand(clustersUpdateMaxScoreCmd) + clustersUpdateCmd.AddCommand(clustersUpdateAdmissionConstraintCmd) } diff --git a/dev/gpctl/cmd/clusters.go b/dev/gpctl/cmd/clusters.go index 56f7a1dc55e4ef..f345e5962face5 100644 --- a/dev/gpctl/cmd/clusters.go +++ b/dev/gpctl/cmd/clusters.go @@ -14,6 +14,7 @@ import ( "google.golang.org/grpc/credentials" "k8s.io/client-go/kubernetes" + "github.com/gitpod-io/gitpod/common-go/log" "github.com/gitpod-io/gitpod/gpctl/pkg/util" "github.com/gitpod-io/gitpod/ws-manager-bridge/api" ) @@ -21,17 +22,32 @@ import ( // clustersCmd represents the clusters command var clustersCmd = &cobra.Command{ Use: "clusters", - Short: "Controls and inspects clusters", + Short: "Controls and inspects cluster", Args: cobra.ExactArgs(1), } +var clustersCmdOpts struct { + TLS string + Port int + Name string +} + func init() { - clustersCmd.PersistentFlags().StringP("tls", "t", "", "TLS certificate when connecting to a secured gRPC endpoint") - clustersCmd.PersistentFlags().StringP("port", "p", "8080", "port of the gRPC endpoint") + clustersCmd.PersistentFlags().StringVarP(&clustersCmdOpts.TLS, "tls", "t", "", "TLS certificate when connecting to a secured gRPC endpoint") + clustersCmd.PersistentFlags().IntVarP(&clustersCmdOpts.Port, "port", "p", 8080, "port of the gRPC endpoint") + clustersCmd.PersistentFlags().StringVarP(&clustersCmdOpts.Name, "name", "n", "", "name of the cluster to affect") rootCmd.AddCommand(clustersCmd) } +func getClusterName() string { + name := clustersCmdOpts.Name + if name == "" { + log.Fatal("missing --name") + } + return name +} + func getClustersClient(ctx context.Context) (*grpc.ClientConn, api.ClusterServiceClient, error) { cfg, namespace, err := getKubeconfig() if err != nil { @@ -43,11 +59,11 @@ func getClustersClient(ctx context.Context) (*grpc.ClientConn, api.ClusterServic } localPort := "30303" - remotePort, _ := clustersCmd.Flags().GetString("port") - if remotePort == "" { - remotePort = "8099" + remotePort := clustersCmdOpts.Port + if remotePort == 0 { + remotePort = 8099 } - port := fmt.Sprintf("%s:%s", localPort, remotePort) + port := fmt.Sprintf("%s:%d", localPort, remotePort) podName, err := util.FindAnyPodForComponent(clientSet, namespace, "ws-manager-bridge") if err != nil { return nil, nil, err diff --git a/dev/gpctl/cmd/completion.go b/dev/gpctl/cmd/completion.go index 11b75581352809..5e65a1723770f2 100644 --- a/dev/gpctl/cmd/completion.go +++ b/dev/gpctl/cmd/completion.go @@ -4,79 +4,71 @@ package cmd -//go:generate sh -c "cd .. && echo \\# generated using go generate in components/gpctl > ../../devops/images/workspaces/gitpod-dev/gpctl_completion; go run main.go completion bash >> ../../devops/images/workspaces/gitpod-dev/gpctl_completion" - import ( "os" "github.com/spf13/cobra" ) -const ( - bashCompletionFunc = `__gpctl_parse_get_workspace_url() -{ - local gpctl_output out - if gpctl_output=$(gpctl workspaces list --output-template '{{ range .Status }}{{ .Id }} {{ .Spec.Url | trimPrefix "http://" | trimPrefix "https://" }} {{ end }}' | tr " " "\n" 2>/dev/null); then - out=($(echo "${gpctl_output}" | awk '{print $1}')) - COMPREPLY=( $( compgen -W "${out[*]}" -- "$cur" ) ) - fi -} -__gpctl_get_workspace_url() -{ - __gpctl_parse_get_workspace_url - if [[ $? -eq 0 ]]; then - return 0 - fi -} -__gpctl_parse_get_imagebuild_ref() -{ - local gpctl_output out - if gpctl_output=$(gpctl imagebuilds list -o jsonpath | tr " " "\n" 2>/dev/null); then - out=($(echo "${gpctl_output}" | awk '{print $1}')) - COMPREPLY=( $( compgen -W "${out[*]}" -- "$cur" ) ) - fi -} -__gpctl_get_imagebuild_ref() -{ - __gpctl_parse_get_imagebuild_ref - if [[ $? -eq 0 ]]; then - return 0 - fi -} -__gpctl_custom_func() { - case ${last_command} in - gpctl_workspaces_describe | gpctl_workspaces_stop | gpctl_workspaces_snapshot) - __gpctl_get_workspace_url - return - ;; - gpctl_imagebuilds_logs) - __gpctl_get_imagebuild_ref - return - ;; - *) - ;; - esac -} -` -) +var completionCmd = &cobra.Command{ + Use: "completion [bash|zsh|fish|powershell]", + Short: "Generate completion script", + Long: `To load completions: + +Bash: + + $ source <(gpctl completion bash) + + # To load completions for each session, execute once: + # Linux: + $ gpctl completion bash > /etc/bash_completion.d/gpctl + # macOS: + $ gpctl completion bash > /usr/local/etc/bash_completion.d/gpctl + +Zsh: + + # If shell completion is not already enabled in your environment, + # you will need to enable it. You can execute the following once: + + $ echo "autoload -U compinit; compinit" >> ~/.zshrc + + # To load completions for each session, execute once: + $ gpctl completion zsh > "${fpath[1]}/_gpctl" + + # You will need to start a new shell for this setup to take effect. + +fish: + + $ gpctl completion fish | source + + # To load completions for each session, execute once: + $ gpctl completion fish > ~/.config/fish/completions/gpctl.fish + +PowerShell: + + PS> gpctl completion powershell | Out-String | Invoke-Expression -// bashCompletionCmd represents the bashCompletion command -var bashCompletionCmd = &cobra.Command{ - Use: "completion bash|zsh", - Short: "Provides shell completion for gpctl. Use with `. <(gpctl completion)`", - Hidden: true, - Args: cobra.ExactValidArgs(1), - ValidArgs: []string{"bash", "zsh"}, + # To load completions for every new session, run: + PS> gpctl completion powershell > gpctl.ps1 + # and source this file from your PowerShell profile. +`, + DisableFlagsInUseLine: true, + ValidArgs: []string{"bash", "zsh", "fish", "powershell"}, + Args: cobra.ExactValidArgs(1), Run: func(cmd *cobra.Command, args []string) { switch args[0] { case "bash": - rootCmd.GenBashCompletion(os.Stdout) + cmd.Root().GenBashCompletion(os.Stdout) case "zsh": - rootCmd.GenZshCompletion(os.Stdout) + cmd.Root().GenZshCompletion(os.Stdout) + case "fish": + cmd.Root().GenFishCompletion(os.Stdout, true) + case "powershell": + cmd.Root().GenPowerShellCompletionWithDesc(os.Stdout) } }, } func init() { - rootCmd.AddCommand(bashCompletionCmd) + rootCmd.AddCommand(completionCmd) } diff --git a/dev/gpctl/cmd/root.go b/dev/gpctl/cmd/root.go index ff84cb19ca6103..b13fd11ad9d5d7 100644 --- a/dev/gpctl/cmd/root.go +++ b/dev/gpctl/cmd/root.go @@ -20,10 +20,9 @@ import ( // rootCmd represents the base command when called without any subcommands var rootCmd = &cobra.Command{ - Use: "gpctl", - Short: "Gpctl controls a Gitpod installation", - Args: cobra.MinimumNArgs(1), - BashCompletionFunction: bashCompletionFunc, + Use: "gpctl", + Short: "Gpctl controls a Gitpod installation", + Args: cobra.MinimumNArgs(1), } // Execute adds all child commands to the root command and sets flags appropriately. diff --git a/dev/gpctl/cmd/workspaces-start.go b/dev/gpctl/cmd/workspaces-start.go index 7ab3d086c8f8a6..b86286c8e16b87 100644 --- a/dev/gpctl/cmd/workspaces-start.go +++ b/dev/gpctl/cmd/workspaces-start.go @@ -93,7 +93,7 @@ func init() { } workspacesCmd.AddCommand(workspacesStartCmd) - workspacesStartCmd.Flags().StringVarP(&startWorkspaceReq.ServicePrefix, "service-prefix", "p", "", "use a service prefix different from the workspace ID") + workspacesStartCmd.Flags().StringVar(&startWorkspaceReq.ServicePrefix, "service-prefix", "", "use a service prefix different from the workspace ID") workspacesStartCmd.Flags().StringVar(&startWorkspaceReq.Metadata.Owner, "owner", "gpctl", "set the workspace owner") workspacesStartCmd.Flags().StringVar(&startWorkspaceReq.Metadata.MetaId, "workspace-id", wsid, "set the workspace ID") workspacesStartCmd.Flags().IntP("count", "n", 1, "start multiple workspaces with the same spec - useful for load tests") diff --git a/dev/gpctl/go.mod b/dev/gpctl/go.mod index 722bb5e5309677..2a1e8703c2df8d 100644 --- a/dev/gpctl/go.mod +++ b/dev/gpctl/go.mod @@ -16,7 +16,7 @@ require ( github.com/huandu/xstrings v1.2.0 // indirect github.com/mitchellh/copystructure v1.0.0 // indirect github.com/mitchellh/go-homedir v1.1.0 - github.com/spf13/cobra v0.0.5 + github.com/spf13/cobra v1.1.3 golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 google.golang.org/grpc v1.37.0 google.golang.org/protobuf v1.26.0 diff --git a/dev/gpctl/go.sum b/dev/gpctl/go.sum index faa366bab972a0..dd5f7f3878d4fd 100644 --- a/dev/gpctl/go.sum +++ b/dev/gpctl/go.sum @@ -15,6 +15,7 @@ cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNF cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc= cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE= cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk= +cloud.google.com/go/firestore v1.1.0/go.mod h1:ulACoGHTpvq5r8rxGJ4ddJZBZqakUQqClKRT5SZwBmk= cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I= cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw= cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA= @@ -40,6 +41,7 @@ github.com/Masterminds/semver v1.5.0/go.mod h1:MB6lktGJrhw8PrUyiEoblNEGEQ+RzHPF0 github.com/Masterminds/sprig v2.22.0+incompatible h1:z4yfnGrZ7netVz+0EDJ0Wi+5VZCSYp4Z0m2dk6cEM60= github.com/Masterminds/sprig v2.22.0+incompatible/go.mod h1:y6hNFY5UBTIWBxnzTeuNhlNS5hqE0NB0E6fgfo2Br3o= github.com/NYTimes/gziphandler v0.0.0-20170623195520-56545f4a5d46/go.mod h1:3wb06e3pkSAbeQ52E9H9iFoQsEEwGN64994WTCIhntQ= +github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU= github.com/PuerkitoBio/purell v1.1.1/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbtSwDGJws/X0= github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578/go.mod h1:uGdkoq3SwY9Y+13GIhn11/XLaGBb4BfwItxLd5jeuXE= github.com/Shopify/sarama v1.19.0/go.mod h1:FVkBWblsNy7DGZRfXLU0O9RCGt5g3g3yEuWXgklEdEo= @@ -57,7 +59,6 @@ github.com/alecthomas/units v0.0.0-20190924025748-f65c72e2690d/go.mod h1:rBZYJk5 github.com/apache/thrift v0.12.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb+bacwQ= github.com/apache/thrift v0.13.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb+bacwQ= github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o= -github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8= github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY= github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= github.com/aryann/difflib v0.0.0-20170710044230-e206f873d14a/go.mod h1:DAHtR1m6lCRdSC2Tm3DSWRPvIPr6xNKyeHdqDQSQT+A= @@ -69,9 +70,12 @@ github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24 github.com/beorn7/perks v1.0.0/go.mod h1:KWe93zE9D1o94FZ5RNwFwVgaQK1VOXiVxmqh+CedLV8= github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= github.com/bgentry/speakeasy v0.1.0/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs= +github.com/bketelsen/crypt v0.0.3-0.20200106085610-5cbc8cc4026c/go.mod h1:MKsuJmJgSg28kpZDP6UIiPt0e0Oz0kqKNGyRaWEPv84= +github.com/bmizerany/assert v0.0.0-20160611221934-b7ed37b82869/go.mod h1:Ekp36dRnpXw/yCqJaO+ZrUyxD+3VXMFFr56k5XYrpB4= github.com/casbin/casbin/v2 v2.1.2/go.mod h1:YcPU1XXisHhLzuxH9coDNf2FbKpjGlbCg3n9yuLkIJQ= github.com/cenkalti/backoff v2.2.1+incompatible/go.mod h1:90ReRw6GdpyfrHakVjL/QHaoyV4aDUVVkXQJJJ3NXXM= github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= +github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc= github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI= @@ -81,19 +85,23 @@ github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDk github.com/cncf/udpa/go v0.0.0-20201120205902-5459f2c99403/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= github.com/codahale/hdrhistogram v0.0.0-20161010025455-3a0bb77429bd/go.mod h1:sE/e/2PUdi/liOCUjSTXgM1o87ZssimdTWN964YiIeI= -github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= -github.com/coreos/go-etcd v2.0.0+incompatible/go.mod h1:Jez6KQU2B/sWsbdaef3ED8NzMklzPG4d5KIOhIy30Tk= +github.com/coreos/bbolt v1.3.2/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk= +github.com/coreos/etcd v3.3.13+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= +github.com/coreos/go-semver v0.3.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= github.com/coreos/go-systemd v0.0.0-20180511133405-39ca1b05acc7/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= +github.com/coreos/go-systemd v0.0.0-20190321100706-95778dfbb74e/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= github.com/coreos/pkg v0.0.0-20160727233714-3ac0863d7acf/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= -github.com/cpuguy83/go-md2man v1.0.10/go.mod h1:SmD6nW6nTyfqj6ABTjUi3V3JVMnlJmwcJI5acqYI6dE= +github.com/coreos/pkg v0.0.0-20180928190104-399ea9e2e55f/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= github.com/cpuguy83/go-md2man/v2 v2.0.0-20190314233015-f79a8a8ca69d/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= +github.com/cpuguy83/go-md2man/v2 v2.0.0/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= github.com/creack/pty v1.1.7/go.mod h1:lj5s0c3V2DBrqTV7llrYr5NG6My20zk30Fl46Y7DoTY= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ= +github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954/go.mod h1:vAd38F8PWV+bWy6jNmig1y/TA+kYO4g3RSRF0IAv0no= github.com/docopt/docopt-go v0.0.0-20180111231733-ee0de3bc6815/go.mod h1:WwZ+bS3ebgob9U8Nd0kOddGdZWjyMGR8Wziv+TBNwSE= github.com/dustin/go-humanize v0.0.0-20171111073723-bb3d318650d4/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/eapache/go-resiliency v1.1.0/go.mod h1:kFI+JgMyC7bLPUVY133qvEBtVayf5mFgVsvEsIPBvNs= @@ -149,6 +157,7 @@ github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69 github.com/golang/freetype v0.0.0-20170609003504-e2365dfdc4a0/go.mod h1:E/TSTwGwJL78qG/PmXZO1EjYhfJinVAhrmmHX6Z8B9k= github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q= github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20190129154638-5b532d6fd5ef/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20190702054246-869f871628b6/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20191227052852-215e87163ea7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= @@ -210,10 +219,14 @@ github.com/gorilla/mux v1.7.3/go.mod h1:1lud6UwP+6orDFRuTfBEV8e9/aOM/c4fVVCaMa2z github.com/gorilla/websocket v0.0.0-20170926233335-4201258b820c/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ= github.com/gorilla/websocket v1.4.2/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7/go.mod h1:FecbI9+v66THATjSRHfNgh1IVFe/9kFxbXtjV0ctIMA= +github.com/grpc-ecosystem/go-grpc-middleware v1.0.0/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs= github.com/grpc-ecosystem/go-grpc-middleware v1.0.1-0.20190118093823-f849b5445de4/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs= github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk= +github.com/grpc-ecosystem/grpc-gateway v1.9.0/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= github.com/grpc-ecosystem/grpc-gateway v1.9.5/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= +github.com/hashicorp/consul/api v1.1.0/go.mod h1:VmuI/Lkw1nC05EYQWNKwWGbkg+FbDBtguAZLlVdkD9Q= github.com/hashicorp/consul/api v1.3.0/go.mod h1:MmDNSzIMUjNpY/mQ398R4bk2FnqQLoPndWW5VkKPlCE= +github.com/hashicorp/consul/sdk v0.1.1/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8= github.com/hashicorp/consul/sdk v0.3.0/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8= github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= @@ -274,7 +287,7 @@ github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= github.com/lightstep/lightstep-tracer-common/golang/gogo v0.0.0-20190605223551-bc2310a04743/go.mod h1:qklhhLq1aX+mtWk9cPHPzaBjWImj5ULL6C7HFJtXQMM= github.com/lightstep/lightstep-tracer-go v0.18.1/go.mod h1:jlF1pusYV4pidLvZ+XD0UBX0ZE6WURAspgAczcDHrL4= github.com/lyft/protoc-gen-validate v0.0.13/go.mod h1:XbGvPuh87YZc5TdIa2/I4pLk0QoUACkjt2znoq26NVQ= -github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/magiconair/properties v1.8.1/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU= @@ -319,6 +332,7 @@ github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e h1:fD57ERR4JtEqsWb github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno= github.com/oklog/oklog v0.3.2/go.mod h1:FCV+B7mhrz4o+ueLpx+KqkyXRGMWOYEvfiXtdGtbWGs= github.com/oklog/run v1.0.0/go.mod h1:dlhp/R75TPv97u0XWUtDeV/lRKWPKSdTuV0TZvrmrQA= +github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U= github.com/olekukonko/tablewriter v0.0.0-20170122224234-a0225b3f23b5/go.mod h1:vsDQFd/mU46D+Z4whnwzcISnGGzXWMclvtLoiIKAKIo= github.com/onsi/ginkgo v0.0.0-20170829012221-11459a886d9c/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= @@ -358,6 +372,7 @@ github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZN github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI= github.com/prometheus/client_golang v0.9.1/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw= github.com/prometheus/client_golang v0.9.3-0.20190127221311-3c4408c8b829/go.mod h1:p2iRAGwDERtqlqzRXnrOVns+ignqQo//hLXqYxZYVNs= +github.com/prometheus/client_golang v0.9.3/go.mod h1:/TN21ttK/J9q6uSwhBd54HahCDft0ttaMvbicHlPoso= github.com/prometheus/client_golang v1.0.0/go.mod h1:db9x61etRT2tGnBNRi70OPL5FsnadC4Ky3P0J6CfImo= github.com/prometheus/client_golang v1.3.0/go.mod h1:hJaj2vgQTGQmVCsAACORcieXFeDPbaTKGT+JTgUa3og= github.com/prometheus/client_golang v1.7.1/go.mod h1:PY5Wy2awLA44sXw4AOSfFBetzPP4j5+D6mVACh+pe2M= @@ -368,26 +383,30 @@ github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1: github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.1.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.2.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= +github.com/prometheus/common v0.0.0-20181113130724-41aa239b4cce/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro= github.com/prometheus/common v0.2.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= +github.com/prometheus/common v0.4.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= github.com/prometheus/common v0.4.1/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= github.com/prometheus/common v0.7.0/go.mod h1:DjGbpBbp5NYNiECxcL/VnbXCCaQpKd3tt26CguLLsqA= github.com/prometheus/common v0.10.0/go.mod h1:Tlit/dnDKsSWFlCLTWaA1cyBgKHSMdTB80sz/V91rCo= github.com/prometheus/common v0.15.0/go.mod h1:U+gB1OBLb1lF3O42bTCL+FK18tX9Oar16Clt/msog/s= github.com/prometheus/procfs v0.0.0-20181005140218-185b4288413d/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= github.com/prometheus/procfs v0.0.0-20190117184657-bf6a532e95b1/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= +github.com/prometheus/procfs v0.0.0-20190507164030-5867b95ac084/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= github.com/prometheus/procfs v0.0.2/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= github.com/prometheus/procfs v0.0.8/go.mod h1:7Qr8sr6344vo1JqZ6HhLceV9o3AJ1Ff+GxbHq6oeK9A= github.com/prometheus/procfs v0.1.3/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= github.com/prometheus/procfs v0.2.0/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= +github.com/prometheus/tsdb v0.7.1/go.mod h1:qhTCs0VvXwvX/y3TZrWD7rabWM+ijKTux40TwIPHuXU= github.com/rcrowley/go-metrics v0.0.0-20181016184325-3113b8401b8a/go.mod h1:bCqnVzQkZxMG4s8nGwiZ5l3QUCyqpo9Y+/ZMZ9VjZe4= github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6SoW27p1b0cqNHllgS5HIMJraePCO15w5zCzIWYg= github.com/rogpeppe/go-charset v0.0.0-20180617210344-2471d30d28b4/go.mod h1:qgYeAmZ5ZIpBWTGllZSQnw97Dj+woV0toclVaRGI8pc= github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= -github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g= github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts= github.com/samuel/go-zookeeper v0.0.0-20190923202752-2cc03de413da/go.mod h1:gi+0XIa01GRL2eRQVjQkKGqKF3SF9vZR/HnPullcV2E= github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg65j358z/aeFdxmN0P9QXhEzd20vsDc= +github.com/segmentio/backo-go v0.0.0-20200129164019-23eae7c10bd3/go.mod h1:9/Rh6yILuLysoQnZ2oNooD2g7aBnvM7r/fNVxRNWfBc= github.com/shurcooL/sanitized_anchor_name v1.0.0/go.mod h1:1NzhyTcUVG4SuEtjjoZeVRXNmyL/1OwPU0+IJeTBvfc= github.com/sirupsen/logrus v1.2.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo= github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE= @@ -398,19 +417,20 @@ github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d/go.mod h1 github.com/smartystreets/goconvey v1.6.4/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA= github.com/soheilhy/cmux v0.1.4/go.mod h1:IM3LyeVVIOuxMH7sFAkER9+bJ4dT7Ms6E4xg4kGIyLM= github.com/sony/gobreaker v0.4.1/go.mod h1:ZKptC7FHNvhBz7dN2LGjPVBz2sZJmc0/PkyDJOjmxWY= +github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ= github.com/spf13/afero v1.2.2/go.mod h1:9ZxEEn6pIJ8Rxe320qSDBk6AsU0r9pR7Q4OcevTdifk= github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ= -github.com/spf13/cobra v0.0.5 h1:f0B+LkLX6DtmRH1isoNA9VTtNUK9K8xYd28JNNfOv/s= -github.com/spf13/cobra v0.0.5/go.mod h1:3K3wKZymM7VvHMDS9+Akkh4K60UwM26emMESw8tLCHU= +github.com/spf13/cobra v1.1.3 h1:xghbfqPkxzxP3C/f3n5DdpAbdKLj4ZE4BWQI362l53M= +github.com/spf13/cobra v1.1.3/go.mod h1:pGADOWyqRD/YMrPZigI/zbliZ2wVD/23d+is3pSWzOo= github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo= github.com/spf13/pflag v0.0.0-20170130214245-9ff6c6923cff/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= github.com/spf13/pflag v1.0.1/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA= github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= -github.com/spf13/viper v1.3.2/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DMA2s= +github.com/spf13/viper v1.7.0/go.mod h1:8WkrPz2fc9jxqZNCJI/76HCieCp4Q8HaLFoCha5qpdg= github.com/streadway/amqp v0.0.0-20190404075320-75d898a42a94/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= github.com/streadway/amqp v0.0.0-20190827072141-edfb9018d271/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= github.com/streadway/handy v0.0.0-20190108123426-d5acb3125c2a/go.mod h1:qNTQ5P5JnDBl6z3cMAg/SywNDC5ABu5ApDIw6lUbRmI= @@ -424,16 +444,18 @@ github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5 github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY= github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw= github.com/tmc/grpc-websocket-proxy v0.0.0-20170815181823-89b8d40f7ca8/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= +github.com/tmc/grpc-websocket-proxy v0.0.0-20190109142713-0ad062ec5ee5/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= github.com/uber/jaeger-client-go v2.28.0+incompatible/go.mod h1:WVhlPFC8FDjOFMMWRy2pZqQJSXxYSwNYOkTr/Z6d3Kk= github.com/uber/jaeger-lib v2.4.1+incompatible/go.mod h1:ComeNDZlWwrWnDv8aPp0Ba6+uUTzImX/AauajbLI56U= -github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljTbGfSG7qAOspJ7OScBnGdDN/yBr0sguwnwf0= github.com/urfave/cli v1.20.0/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA= github.com/urfave/cli v1.22.1/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2/go.mod h1:UETIi67q53MR2AWcXfiuqkDkRtnGDLqkBTpCHuJHxtU= -github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q= +github.com/xtgo/uuid v0.0.0-20140804021211-a0b114877d4c/go.mod h1:UrdRz5enIKZ63MEE3IF9l2/ebyx59GyGgPi+tICQdmM= github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= +go.etcd.io/bbolt v1.3.2/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= go.etcd.io/bbolt v1.3.3/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= go.etcd.io/etcd v0.0.0-20191023171146-3cf2f69b5738/go.mod h1:dnLIgRNXwCJa5e+c6mIZCrds/GIG4ncV9HhK5PX7jPg= go.opencensus.io v0.20.1/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk= @@ -443,6 +465,7 @@ go.opencensus.io v0.22.0/go.mod h1:+kGneAE2xo2IficOXnaByMWTGM9T73dGwxeWcUqIpI8= go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= go.opencensus.io v0.22.3/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= +go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= go.uber.org/atomic v1.5.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ= go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0= go.uber.org/multierr v1.3.0/go.mod h1:VgVr7evmIr6uPjLBxg28wmKNXyqE9akIJ5XnfpiKl+4= @@ -451,7 +474,6 @@ go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= go.uber.org/zap v1.13.0/go.mod h1:zwrFLgMcdUuIBviXEYEH1YKNaOBnKXsx2IPda5bBwHM= golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/crypto v0.0.0-20181029021203-45a5f77698d3/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= -golang.org/x/crypto v0.0.0-20181203042331-505ab145d0a9/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= @@ -548,7 +570,6 @@ golang.org/x/sys v0.0.0-20181026203630-95b1ffbd15a5/go.mod h1:STP8DvDyc/dI5b8T5h golang.org/x/sys v0.0.0-20181107165924-66b7b1311ac8/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20181116152217-5ac8a444bdc5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= -golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -621,6 +642,7 @@ golang.org/x/tools v0.0.0-20190911174233-4f2ddba30aff/go.mod h1:b+2E5dAYhXwXZwtn golang.org/x/tools v0.0.0-20191012152004-8de300cfc20a/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191029041327-9cc4af7d6b2c/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191029190741-b9c20aec41a5/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191112195655-aa38f8e97acc/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191113191852-77e3bb0ad9e7/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191115202509-3a792d9c32b2/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= @@ -726,7 +748,9 @@ gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMy gopkg.in/gcfg.v1 v1.2.3/go.mod h1:yesOnuUOFQAhST5vPY4nbZsb/huCgGGXlipJsBn0b3o= gopkg.in/inf.v0 v0.9.1 h1:73M5CoZyi3ZLMOyDlQh031Cx6N9NDJ2Vvfl76EDAgDc= gopkg.in/inf.v0 v0.9.1/go.mod h1:cWUDdTG/fYaXco+Dcufb5Vnc6Gp2YChqWtbxRZE0mXw= +gopkg.in/ini.v1 v1.51.0/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k= gopkg.in/resty.v1 v1.12.0/go.mod h1:mDo4pnntr5jdWRML875a/NmxYqAlA73dVijT2AXvQQo= +gopkg.in/segmentio/analytics-go.v3 v3.1.0/go.mod h1:4QqqlTlSSpVlWA9/9nDcPw+FkM2yv1NQoYjUbL9/JAw= gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw= gopkg.in/warnings.v0 v0.1.2/go.mod h1:jksf8JmL6Qr/oQM2OXTHunEvvTAsrWBLb6OOjuVWRNI= gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74=