From 521b2adc588f34e91eae4b74c2108b720d80691a Mon Sep 17 00:00:00 2001 From: Michal Fiedorowicz Date: Fri, 30 Aug 2024 10:14:14 +0100 Subject: [PATCH 1/2] feat: add virtualization Signed-off-by: Michal Fiedorowicz --- diode/ingester.go | 540 +++++++ diode/ingester_test.go | 534 +++++++ diode/v1/diodepb/ingester.pb.go | 1470 +++++++++++++++---- diode/v1/diodepb/ingester.pb.validate.go | 1691 ++++++++++++++++++++++ examples/main.go | 120 ++ internal/codegen/codegen.go | 19 +- 6 files changed, 4102 insertions(+), 272 deletions(-) diff --git a/diode/ingester.go b/diode/ingester.go index 51fe9ca..4a90ff2 100644 --- a/diode/ingester.go +++ b/diode/ingester.go @@ -14,6 +14,216 @@ type Entity interface { ConvertToProtoEntity() *diodepb.Entity } +// Cluster is based on diodepb.Cluster +type Cluster struct { + Name *string + Type *ClusterType + Group *ClusterGroup + Site *Site + Status *string + Description *string + Tags []*Tag +} + +// ConvertToProtoMessageCluster converts a Cluster to a diodepb.Cluster +func (e *Cluster) ConvertToProtoMessage() proto.Message { + return &diodepb.Cluster{ + Name: e.GetName(), + Type: e.GetType(), + Group: e.GetGroup(), + Site: e.GetSite(), + Status: e.GetStatus(), + Description: e.GetDescription(), + Tags: e.GetTags(), + } +} + +// GetName returns the Name field +func (e *Cluster) GetName() string { + if e != nil && e.Name != nil { + return *e.Name + } + return "" +} + +// GetType returns the Type field +func (e *Cluster) GetType() *diodepb.ClusterType { + if e != nil && e.Type != nil { + return e.Type.ConvertToProtoMessage().(*diodepb.ClusterType) + } + return nil +} + +// GetGroup returns the Group field +func (e *Cluster) GetGroup() *diodepb.ClusterGroup { + if e != nil && e.Group != nil { + return e.Group.ConvertToProtoMessage().(*diodepb.ClusterGroup) + } + return nil +} + +// GetSite returns the Site field +func (e *Cluster) GetSite() *diodepb.Site { + if e != nil && e.Site != nil { + return e.Site.ConvertToProtoMessage().(*diodepb.Site) + } + return nil +} + +// GetStatus returns the Status field +func (e *Cluster) GetStatus() string { + if e != nil && e.Status != nil { + return *e.Status + } + return "" +} + +// GetDescription returns the Description field +func (e *Cluster) GetDescription() *string { + if e != nil && e.Description != nil { + return e.Description + } + return nil +} + +// GetTags returns the Tags field +func (e *Cluster) GetTags() []*diodepb.Tag { + var tags []*diodepb.Tag + for _, el := range e.Tags { + tags = append(tags, el.ConvertToProtoMessage().(*diodepb.Tag)) + } + return tags +} + +// ConvertToProtoEntityCluster converts a Cluster to a diodepb.Entity +func (e *Cluster) ConvertToProtoEntity() *diodepb.Entity { + return &diodepb.Entity{ + Entity: &diodepb.Entity_Cluster{ + Cluster: e.ConvertToProtoMessage().(*diodepb.Cluster), + }, + } +} + +// ClusterGroup is based on diodepb.ClusterGroup +type ClusterGroup struct { + Name *string + Slug *string + Description *string + Tags []*Tag +} + +// ConvertToProtoMessageClusterGroup converts a ClusterGroup to a diodepb.ClusterGroup +func (e *ClusterGroup) ConvertToProtoMessage() proto.Message { + return &diodepb.ClusterGroup{ + Name: e.GetName(), + Slug: e.GetSlug(), + Description: e.GetDescription(), + Tags: e.GetTags(), + } +} + +// GetName returns the Name field +func (e *ClusterGroup) GetName() string { + if e != nil && e.Name != nil { + return *e.Name + } + return "" +} + +// GetSlug returns the Slug field +func (e *ClusterGroup) GetSlug() string { + if e != nil && e.Slug != nil { + return *e.Slug + } + return "" +} + +// GetDescription returns the Description field +func (e *ClusterGroup) GetDescription() *string { + if e != nil && e.Description != nil { + return e.Description + } + return nil +} + +// GetTags returns the Tags field +func (e *ClusterGroup) GetTags() []*diodepb.Tag { + var tags []*diodepb.Tag + for _, el := range e.Tags { + tags = append(tags, el.ConvertToProtoMessage().(*diodepb.Tag)) + } + return tags +} + +// ConvertToProtoEntityClusterGroup converts a ClusterGroup to a diodepb.Entity +func (e *ClusterGroup) ConvertToProtoEntity() *diodepb.Entity { + return &diodepb.Entity{ + Entity: &diodepb.Entity_ClusterGroup{ + ClusterGroup: e.ConvertToProtoMessage().(*diodepb.ClusterGroup), + }, + } +} + +// ClusterType is based on diodepb.ClusterType +type ClusterType struct { + Name *string + Slug *string + Description *string + Tags []*Tag +} + +// ConvertToProtoMessageClusterType converts a ClusterType to a diodepb.ClusterType +func (e *ClusterType) ConvertToProtoMessage() proto.Message { + return &diodepb.ClusterType{ + Name: e.GetName(), + Slug: e.GetSlug(), + Description: e.GetDescription(), + Tags: e.GetTags(), + } +} + +// GetName returns the Name field +func (e *ClusterType) GetName() string { + if e != nil && e.Name != nil { + return *e.Name + } + return "" +} + +// GetSlug returns the Slug field +func (e *ClusterType) GetSlug() string { + if e != nil && e.Slug != nil { + return *e.Slug + } + return "" +} + +// GetDescription returns the Description field +func (e *ClusterType) GetDescription() *string { + if e != nil && e.Description != nil { + return e.Description + } + return nil +} + +// GetTags returns the Tags field +func (e *ClusterType) GetTags() []*diodepb.Tag { + var tags []*diodepb.Tag + for _, el := range e.Tags { + tags = append(tags, el.ConvertToProtoMessage().(*diodepb.Tag)) + } + return tags +} + +// ConvertToProtoEntityClusterType converts a ClusterType to a diodepb.Entity +func (e *ClusterType) ConvertToProtoEntity() *diodepb.Entity { + return &diodepb.Entity{ + Entity: &diodepb.Entity_ClusterType{ + ClusterType: e.ConvertToProtoMessage().(*diodepb.ClusterType), + }, + } +} + // Device is based on diodepb.Device type Device struct { Name *string @@ -965,3 +1175,333 @@ func (e *Tag) GetColor() string { } return "" } + +// VMInterface is based on diodepb.VMInterface +type VMInterface struct { + VirtualMachine *VirtualMachine + Name *string + Enabled *bool + Mtu *int32 + MacAddress *string + Description *string + Tags []*Tag +} + +// ConvertToProtoMessageVMInterface converts a VMInterface to a diodepb.VMInterface +func (e *VMInterface) ConvertToProtoMessage() proto.Message { + return &diodepb.VMInterface{ + VirtualMachine: e.GetVirtualMachine(), + Name: e.GetName(), + Enabled: e.GetEnabled(), + Mtu: e.GetMtu(), + MacAddress: e.GetMacAddress(), + Description: e.GetDescription(), + Tags: e.GetTags(), + } +} + +// GetVirtualMachine returns the VirtualMachine field +func (e *VMInterface) GetVirtualMachine() *diodepb.VirtualMachine { + if e != nil && e.VirtualMachine != nil { + return e.VirtualMachine.ConvertToProtoMessage().(*diodepb.VirtualMachine) + } + return nil +} + +// GetName returns the Name field +func (e *VMInterface) GetName() string { + if e != nil && e.Name != nil { + return *e.Name + } + return "" +} + +// GetEnabled returns the Enabled field +func (e *VMInterface) GetEnabled() *bool { + if e != nil && e.Enabled != nil { + return e.Enabled + } + return nil +} + +// GetMtu returns the Mtu field +func (e *VMInterface) GetMtu() *int32 { + if e != nil && e.Mtu != nil { + return e.Mtu + } + return nil +} + +// GetMacAddress returns the MacAddress field +func (e *VMInterface) GetMacAddress() *string { + if e != nil && e.MacAddress != nil { + return e.MacAddress + } + return nil +} + +// GetDescription returns the Description field +func (e *VMInterface) GetDescription() *string { + if e != nil && e.Description != nil { + return e.Description + } + return nil +} + +// GetTags returns the Tags field +func (e *VMInterface) GetTags() []*diodepb.Tag { + var tags []*diodepb.Tag + for _, el := range e.Tags { + tags = append(tags, el.ConvertToProtoMessage().(*diodepb.Tag)) + } + return tags +} + +// ConvertToProtoEntityVMInterface converts a VMInterface to a diodepb.Entity +func (e *VMInterface) ConvertToProtoEntity() *diodepb.Entity { + return &diodepb.Entity{ + Entity: &diodepb.Entity_Vminterface{ + Vminterface: e.ConvertToProtoMessage().(*diodepb.VMInterface), + }, + } +} + +// VirtualDisk is based on diodepb.VirtualDisk +type VirtualDisk struct { + VirtualMachine *VirtualMachine + Name *string + Size *int32 + Description *string + Tags []*Tag +} + +// ConvertToProtoMessageVirtualDisk converts a VirtualDisk to a diodepb.VirtualDisk +func (e *VirtualDisk) ConvertToProtoMessage() proto.Message { + return &diodepb.VirtualDisk{ + VirtualMachine: e.GetVirtualMachine(), + Name: e.GetName(), + Size: e.GetSize(), + Description: e.GetDescription(), + Tags: e.GetTags(), + } +} + +// GetVirtualMachine returns the VirtualMachine field +func (e *VirtualDisk) GetVirtualMachine() *diodepb.VirtualMachine { + if e != nil && e.VirtualMachine != nil { + return e.VirtualMachine.ConvertToProtoMessage().(*diodepb.VirtualMachine) + } + return nil +} + +// GetName returns the Name field +func (e *VirtualDisk) GetName() string { + if e != nil && e.Name != nil { + return *e.Name + } + return "" +} + +// GetSize returns the Size field +func (e *VirtualDisk) GetSize() int32 { + if e != nil && e.Size != nil { + return *e.Size + } + return 0 +} + +// GetDescription returns the Description field +func (e *VirtualDisk) GetDescription() *string { + if e != nil && e.Description != nil { + return e.Description + } + return nil +} + +// GetTags returns the Tags field +func (e *VirtualDisk) GetTags() []*diodepb.Tag { + var tags []*diodepb.Tag + for _, el := range e.Tags { + tags = append(tags, el.ConvertToProtoMessage().(*diodepb.Tag)) + } + return tags +} + +// ConvertToProtoEntityVirtualDisk converts a VirtualDisk to a diodepb.Entity +func (e *VirtualDisk) ConvertToProtoEntity() *diodepb.Entity { + return &diodepb.Entity{ + Entity: &diodepb.Entity_VirtualDisk{ + VirtualDisk: e.ConvertToProtoMessage().(*diodepb.VirtualDisk), + }, + } +} + +// VirtualMachine is based on diodepb.VirtualMachine +type VirtualMachine struct { + Name *string + Status *string + Site *Site + Cluster *Cluster + Role *Role + Device *Device + Platform *Platform + PrimaryIp4 *IPAddress + PrimaryIp6 *IPAddress + Vcpus *int32 + Memory *int32 + Disk *int32 + Description *string + Comments *string + Tags []*Tag +} + +// ConvertToProtoMessageVirtualMachine converts a VirtualMachine to a diodepb.VirtualMachine +func (e *VirtualMachine) ConvertToProtoMessage() proto.Message { + return &diodepb.VirtualMachine{ + Name: e.GetName(), + Status: e.GetStatus(), + Site: e.GetSite(), + Cluster: e.GetCluster(), + Role: e.GetRole(), + Device: e.GetDevice(), + Platform: e.GetPlatform(), + PrimaryIp4: e.GetPrimaryIp4(), + PrimaryIp6: e.GetPrimaryIp6(), + Vcpus: e.GetVcpus(), + Memory: e.GetMemory(), + Disk: e.GetDisk(), + Description: e.GetDescription(), + Comments: e.GetComments(), + Tags: e.GetTags(), + } +} + +// GetName returns the Name field +func (e *VirtualMachine) GetName() string { + if e != nil && e.Name != nil { + return *e.Name + } + return "" +} + +// GetStatus returns the Status field +func (e *VirtualMachine) GetStatus() string { + if e != nil && e.Status != nil { + return *e.Status + } + return "" +} + +// GetSite returns the Site field +func (e *VirtualMachine) GetSite() *diodepb.Site { + if e != nil && e.Site != nil { + return e.Site.ConvertToProtoMessage().(*diodepb.Site) + } + return nil +} + +// GetCluster returns the Cluster field +func (e *VirtualMachine) GetCluster() *diodepb.Cluster { + if e != nil && e.Cluster != nil { + return e.Cluster.ConvertToProtoMessage().(*diodepb.Cluster) + } + return nil +} + +// GetRole returns the Role field +func (e *VirtualMachine) GetRole() *diodepb.Role { + if e != nil && e.Role != nil { + return e.Role.ConvertToProtoMessage().(*diodepb.Role) + } + return nil +} + +// GetDevice returns the Device field +func (e *VirtualMachine) GetDevice() *diodepb.Device { + if e != nil && e.Device != nil { + return e.Device.ConvertToProtoMessage().(*diodepb.Device) + } + return nil +} + +// GetPlatform returns the Platform field +func (e *VirtualMachine) GetPlatform() *diodepb.Platform { + if e != nil && e.Platform != nil { + return e.Platform.ConvertToProtoMessage().(*diodepb.Platform) + } + return nil +} + +// GetPrimaryIp4 returns the PrimaryIp4 field +func (e *VirtualMachine) GetPrimaryIp4() *diodepb.IPAddress { + if e != nil && e.PrimaryIp4 != nil { + return e.PrimaryIp4.ConvertToProtoMessage().(*diodepb.IPAddress) + } + return nil +} + +// GetPrimaryIp6 returns the PrimaryIp6 field +func (e *VirtualMachine) GetPrimaryIp6() *diodepb.IPAddress { + if e != nil && e.PrimaryIp6 != nil { + return e.PrimaryIp6.ConvertToProtoMessage().(*diodepb.IPAddress) + } + return nil +} + +// GetVcpus returns the Vcpus field +func (e *VirtualMachine) GetVcpus() *int32 { + if e != nil && e.Vcpus != nil { + return e.Vcpus + } + return nil +} + +// GetMemory returns the Memory field +func (e *VirtualMachine) GetMemory() *int32 { + if e != nil && e.Memory != nil { + return e.Memory + } + return nil +} + +// GetDisk returns the Disk field +func (e *VirtualMachine) GetDisk() *int32 { + if e != nil && e.Disk != nil { + return e.Disk + } + return nil +} + +// GetDescription returns the Description field +func (e *VirtualMachine) GetDescription() *string { + if e != nil && e.Description != nil { + return e.Description + } + return nil +} + +// GetComments returns the Comments field +func (e *VirtualMachine) GetComments() *string { + if e != nil && e.Comments != nil { + return e.Comments + } + return nil +} + +// GetTags returns the Tags field +func (e *VirtualMachine) GetTags() []*diodepb.Tag { + var tags []*diodepb.Tag + for _, el := range e.Tags { + tags = append(tags, el.ConvertToProtoMessage().(*diodepb.Tag)) + } + return tags +} + +// ConvertToProtoEntityVirtualMachine converts a VirtualMachine to a diodepb.Entity +func (e *VirtualMachine) ConvertToProtoEntity() *diodepb.Entity { + return &diodepb.Entity{ + Entity: &diodepb.Entity_VirtualMachine{ + VirtualMachine: e.ConvertToProtoMessage().(*diodepb.VirtualMachine), + }, + } +} diff --git a/diode/ingester_test.go b/diode/ingester_test.go index 7bd9deb..8e9620b 100644 --- a/diode/ingester_test.go +++ b/diode/ingester_test.go @@ -1019,3 +1019,537 @@ func TestTagMethods(t *testing.T) { }) } } + +func TestClusterMethods(t *testing.T) { + tests := []struct { + name string + cluster *Cluster + expected interface{} + method func(*Cluster) interface{} + }{ + { + name: "GetName", + cluster: &Cluster{Name: String("cluster-1")}, + expected: "cluster-1", + method: func(c *Cluster) interface{} { + return c.GetName() + }, + }, + { + name: "GetType", + cluster: &Cluster{Type: &ClusterType{}}, + expected: &diodepb.ClusterType{}, + method: func(c *Cluster) interface{} { + return c.GetType() + }, + }, + { + name: "GetGroup", + cluster: &Cluster{Group: &ClusterGroup{}}, + expected: &diodepb.ClusterGroup{}, + method: func(c *Cluster) interface{} { + return c.GetGroup() + }, + }, + { + name: "GetSite", + cluster: &Cluster{Site: &Site{}}, + expected: &diodepb.Site{}, + method: func(c *Cluster) interface{} { + return c.GetSite() + }, + }, + { + name: "GetStatus", + cluster: &Cluster{Status: String("active")}, + expected: "active", + method: func(c *Cluster) interface{} { + return c.GetStatus() + }, + }, + { + name: "GetDescription", + cluster: &Cluster{Description: String("Test description")}, + expected: String("Test description"), + method: func(c *Cluster) interface{} { + return c.GetDescription() + }, + }, + { + name: "GetTags", + cluster: &Cluster{Tags: []*Tag{{Name: String("tag-1")}}}, + expected: []*diodepb.Tag{{Name: "tag-1"}}, + method: func(c *Cluster) interface{} { + return c.GetTags() + }, + }, + { + name: "ConvertToProtoMessage", + cluster: &Cluster{Name: String("cluster-1")}, + expected: &diodepb.Cluster{Name: "cluster-1"}, + method: func(c *Cluster) interface{} { + return c.ConvertToProtoMessage() + }, + }, + { + name: "ConvertToProtoEntity", + cluster: &Cluster{Name: String("cluster-1")}, + expected: &diodepb.Entity{ + Entity: &diodepb.Entity_Cluster{ + Cluster: &diodepb.Cluster{Name: "cluster-1"}, + }, + }, + method: func(c *Cluster) interface{} { + return c.ConvertToProtoEntity() + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + require.Equal(t, tt.expected, tt.method(tt.cluster)) + }) + } +} + +func TestClusterGroupMethods(t *testing.T) { + tests := []struct { + name string + clusterGroup *ClusterGroup + expected interface{} + method func(*ClusterGroup) interface{} + }{ + { + name: "GetName", + clusterGroup: &ClusterGroup{Name: String("group-1")}, + expected: "group-1", + method: func(cg *ClusterGroup) interface{} { + return cg.GetName() + }, + }, + { + name: "GetSlug", + clusterGroup: &ClusterGroup{Slug: String("group-slug")}, + expected: "group-slug", + method: func(cg *ClusterGroup) interface{} { + return cg.GetSlug() + }, + }, + { + name: "GetDescription", + clusterGroup: &ClusterGroup{Description: String("Test description")}, + expected: String("Test description"), + method: func(cg *ClusterGroup) interface{} { + return cg.GetDescription() + }, + }, + { + name: "GetTags", + clusterGroup: &ClusterGroup{Tags: []*Tag{{Name: String("tag-1")}}}, + expected: []*diodepb.Tag{{Name: "tag-1"}}, + method: func(cg *ClusterGroup) interface{} { + return cg.GetTags() + }, + }, + { + name: "ConvertToProtoMessage", + clusterGroup: &ClusterGroup{Name: String("group-1")}, + expected: &diodepb.ClusterGroup{Name: "group-1"}, + method: func(cg *ClusterGroup) interface{} { + return cg.ConvertToProtoMessage() + }, + }, + { + name: "ConvertToProtoEntity", + clusterGroup: &ClusterGroup{Name: String("group-1")}, + expected: &diodepb.Entity{ + Entity: &diodepb.Entity_ClusterGroup{ + ClusterGroup: &diodepb.ClusterGroup{Name: "group-1"}, + }, + }, + method: func(cg *ClusterGroup) interface{} { + return cg.ConvertToProtoEntity() + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + require.Equal(t, tt.expected, tt.method(tt.clusterGroup)) + }) + } +} + +func TestClusterTypeMethods(t *testing.T) { + tests := []struct { + name string + clusterType *ClusterType + expected interface{} + method func(*ClusterType) interface{} + }{ + { + name: "GetName", + clusterType: &ClusterType{Name: String("type-1")}, + expected: "type-1", + method: func(ct *ClusterType) interface{} { + return ct.GetName() + }, + }, + { + name: "GetSlug", + clusterType: &ClusterType{Slug: String("type-slug")}, + expected: "type-slug", + method: func(ct *ClusterType) interface{} { + return ct.GetSlug() + }, + }, + { + name: "GetDescription", + clusterType: &ClusterType{Description: String("Test description")}, + expected: String("Test description"), + method: func(ct *ClusterType) interface{} { + return ct.GetDescription() + }, + }, + { + name: "GetTags", + clusterType: &ClusterType{Tags: []*Tag{{Name: String("tag-1")}}}, + expected: []*diodepb.Tag{{Name: "tag-1"}}, + method: func(ct *ClusterType) interface{} { + return ct.GetTags() + }, + }, + { + name: "ConvertToProtoMessage", + clusterType: &ClusterType{Name: String("type-1")}, + expected: &diodepb.ClusterType{Name: "type-1"}, + method: func(ct *ClusterType) interface{} { + return ct.ConvertToProtoMessage() + }, + }, + { + name: "ConvertToProtoEntity", + clusterType: &ClusterType{Name: String("type-1")}, + expected: &diodepb.Entity{ + Entity: &diodepb.Entity_ClusterType{ + ClusterType: &diodepb.ClusterType{Name: "type-1"}, + }, + }, + method: func(ct *ClusterType) interface{} { + return ct.ConvertToProtoEntity() + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + require.Equal(t, tt.expected, tt.method(tt.clusterType)) + }) + } +} + +func TestVirtualMachineMethods(t *testing.T) { + tests := []struct { + name string + virtualMachine *VirtualMachine + expected interface{} + method func(*VirtualMachine) interface{} + }{ + { + name: "GetName", + virtualMachine: &VirtualMachine{Name: String("vm-1")}, + expected: "vm-1", + method: func(vm *VirtualMachine) interface{} { + return vm.GetName() + }, + }, + { + name: "GetStatus", + virtualMachine: &VirtualMachine{Status: String("running")}, + expected: "running", + method: func(vm *VirtualMachine) interface{} { + return vm.GetStatus() + }, + }, + { + name: "GetSite", + virtualMachine: &VirtualMachine{Site: &Site{Name: String("site-1")}}, + expected: &diodepb.Site{Name: "site-1"}, + method: func(vm *VirtualMachine) interface{} { + return vm.GetSite() + }, + }, + { + name: "GetCluster", + virtualMachine: &VirtualMachine{Cluster: &Cluster{Name: String("cluster-1")}}, + expected: &diodepb.Cluster{Name: "cluster-1"}, + method: func(vm *VirtualMachine) interface{} { + return vm.GetCluster() + }, + }, + { + name: "GetRole", + virtualMachine: &VirtualMachine{Role: &Role{Name: String("role-1")}}, + expected: &diodepb.Role{Name: "role-1"}, + method: func(vm *VirtualMachine) interface{} { + return vm.GetRole() + }, + }, + { + name: "GetDevice", + virtualMachine: &VirtualMachine{Device: &Device{Name: String("device-1")}}, + expected: &diodepb.Device{Name: "device-1"}, + method: func(vm *VirtualMachine) interface{} { + return vm.GetDevice() + }, + }, + { + name: "GetPlatform", + virtualMachine: &VirtualMachine{Platform: &Platform{Name: String("platform-1")}}, + expected: &diodepb.Platform{Name: "platform-1"}, + method: func(vm *VirtualMachine) interface{} { + return vm.GetPlatform() + }, + }, + { + name: "GetPrimaryIp4", + virtualMachine: &VirtualMachine{PrimaryIp4: &IPAddress{Address: String("192.168.1.1")}}, + expected: &diodepb.IPAddress{ + Address: "192.168.1.1", + AssignedObject: (*diodepb.IPAddress_Interface)(nil), + }, + method: func(vm *VirtualMachine) interface{} { + return vm.GetPrimaryIp4() + }, + }, + { + name: "GetPrimaryIp6", + virtualMachine: &VirtualMachine{PrimaryIp6: &IPAddress{Address: String("::1")}}, + expected: &diodepb.IPAddress{ + Address: "::1", + AssignedObject: (*diodepb.IPAddress_Interface)(nil), + }, + method: func(vm *VirtualMachine) interface{} { + return vm.GetPrimaryIp6() + }, + }, + { + name: "GetVcpus", + virtualMachine: &VirtualMachine{Vcpus: Int32(4)}, + expected: Int32(4), + method: func(vm *VirtualMachine) interface{} { + return vm.GetVcpus() + }, + }, + { + name: "GetMemory", + virtualMachine: &VirtualMachine{Memory: Int32(8192)}, + expected: Int32(8192), + method: func(vm *VirtualMachine) interface{} { + return vm.GetMemory() + }, + }, + { + name: "GetDisk", + virtualMachine: &VirtualMachine{Disk: Int32(100)}, + expected: Int32(100), + method: func(vm *VirtualMachine) interface{} { + return vm.GetDisk() + }, + }, + { + name: "GetDescription", + virtualMachine: &VirtualMachine{Description: String("Test VM")}, + expected: String("Test VM"), + method: func(vm *VirtualMachine) interface{} { + return vm.GetDescription() + }, + }, + { + name: "GetComments", + virtualMachine: &VirtualMachine{Comments: String("No comments")}, + expected: String("No comments"), + method: func(vm *VirtualMachine) interface{} { + return vm.GetComments() + }, + }, + { + name: "GetTags", + virtualMachine: &VirtualMachine{Tags: []*Tag{{Name: String("tag-1")}}}, + expected: []*diodepb.Tag{{Name: "tag-1"}}, + method: func(vm *VirtualMachine) interface{} { + return vm.GetTags() + }, + }, + { + name: "ConvertToProtoMessage", + virtualMachine: &VirtualMachine{Name: String("vm-1")}, + expected: &diodepb.VirtualMachine{Name: "vm-1"}, + method: func(vm *VirtualMachine) interface{} { + return vm.ConvertToProtoMessage() + }, + }, + { + name: "ConvertToProtoEntity", + virtualMachine: &VirtualMachine{Name: String("vm-1")}, + expected: &diodepb.Entity{ + Entity: &diodepb.Entity_VirtualMachine{ + VirtualMachine: &diodepb.VirtualMachine{Name: "vm-1"}, + }, + }, + method: func(vm *VirtualMachine) interface{} { + return vm.ConvertToProtoEntity() + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + require.Equal(t, tt.expected, tt.method(tt.virtualMachine)) + }) + } +} + +func TestVMInterfaceMethods(t *testing.T) { + tests := []struct { + name string + vmInterface *VMInterface + expected interface{} + method func(*VMInterface) interface{} + }{ + { + name: "GetName", + vmInterface: &VMInterface{Name: String("vminterface-1")}, + expected: "vminterface-1", + method: func(vmi *VMInterface) interface{} { + return vmi.GetName() + }, + }, + { + name: "GetMacAddress", + vmInterface: &VMInterface{MacAddress: String("00:1A:2B:3C:4D:5E")}, + expected: String("00:1A:2B:3C:4D:5E"), + method: func(vmi *VMInterface) interface{} { + return vmi.GetMacAddress() + }, + }, + { + name: "GetDescription", + vmInterface: &VMInterface{Description: String("Test description")}, + expected: String("Test description"), + method: func(vmi *VMInterface) interface{} { + return vmi.GetDescription() + }, + }, + { + name: "GetTags", + vmInterface: &VMInterface{Tags: []*Tag{{Name: String("tag-1")}}}, + expected: []*diodepb.Tag{{Name: "tag-1"}}, + method: func(vmi *VMInterface) interface{} { + return vmi.GetTags() + }, + }, + { + name: "ConvertToProtoMessage", + vmInterface: &VMInterface{Name: String("vminterface-1")}, + expected: &diodepb.VMInterface{Name: "vminterface-1"}, + method: func(vmi *VMInterface) interface{} { + return vmi.ConvertToProtoMessage() + }, + }, + { + name: "ConvertToProtoEntity", + vmInterface: &VMInterface{Name: String("vminterface-1")}, + expected: &diodepb.Entity{ + Entity: &diodepb.Entity_Vminterface{ + Vminterface: &diodepb.VMInterface{Name: "vminterface-1"}, + }, + }, + method: func(vmi *VMInterface) interface{} { + return vmi.ConvertToProtoEntity() + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + require.Equal(t, tt.expected, tt.method(tt.vmInterface)) + }) + } +} + +func TestVirtualDiskMethods(t *testing.T) { + tests := []struct { + name string + virtualDisk *VirtualDisk + expected interface{} + method func(*VirtualDisk) interface{} + }{ + { + name: "GetVirtualMachine", + virtualDisk: &VirtualDisk{VirtualMachine: &VirtualMachine{Name: String("vm-1")}}, + expected: &diodepb.VirtualMachine{Name: "vm-1"}, + method: func(vd *VirtualDisk) interface{} { + return vd.GetVirtualMachine() + }, + }, + { + name: "GetName", + virtualDisk: &VirtualDisk{Name: String("disk-1")}, + expected: "disk-1", + method: func(vd *VirtualDisk) interface{} { + return vd.GetName() + }, + }, + { + name: "GetSize", + virtualDisk: &VirtualDisk{Size: Int32(1024)}, + expected: *Int32(1024), + method: func(vd *VirtualDisk) interface{} { + return vd.GetSize() + }, + }, + { + name: "GetDescription", + virtualDisk: &VirtualDisk{Description: String("Test disk")}, + expected: String("Test disk"), + method: func(vd *VirtualDisk) interface{} { + return vd.GetDescription() + }, + }, + { + name: "GetTags", + virtualDisk: &VirtualDisk{Tags: []*Tag{{Name: String("tag-1")}}}, + expected: []*diodepb.Tag{{Name: "tag-1"}}, + method: func(vd *VirtualDisk) interface{} { + return vd.GetTags() + }, + }, + { + name: "ConvertToProtoMessage", + virtualDisk: &VirtualDisk{Name: String("disk-1")}, + expected: &diodepb.VirtualDisk{Name: "disk-1"}, + method: func(vd *VirtualDisk) interface{} { + return vd.ConvertToProtoMessage() + }, + }, + { + name: "ConvertToProtoEntity", + virtualDisk: &VirtualDisk{Name: String("disk-1")}, + expected: &diodepb.Entity{ + Entity: &diodepb.Entity_VirtualDisk{ + VirtualDisk: &diodepb.VirtualDisk{Name: "disk-1"}, + }, + }, + method: func(vd *VirtualDisk) interface{} { + return vd.ConvertToProtoEntity() + }, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + require.Equal(t, tt.expected, tt.method(tt.virtualDisk)) + }) + } +} diff --git a/diode/v1/diodepb/ingester.pb.go b/diode/v1/diodepb/ingester.pb.go index 3bf215a..1db16b4 100644 --- a/diode/v1/diodepb/ingester.pb.go +++ b/diode/v1/diodepb/ingester.pb.go @@ -326,6 +326,582 @@ func (x *Interface) GetTags() []*Tag { return nil } +// A Cluster +type Cluster struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` + Type *ClusterType `protobuf:"bytes,2,opt,name=type,proto3" json:"type,omitempty"` + Group *ClusterGroup `protobuf:"bytes,3,opt,name=group,proto3" json:"group,omitempty"` + Site *Site `protobuf:"bytes,4,opt,name=site,proto3" json:"site,omitempty"` + Status string `protobuf:"bytes,5,opt,name=status,proto3" json:"status,omitempty"` + Description *string `protobuf:"bytes,6,opt,name=description,proto3,oneof" json:"description,omitempty"` + Tags []*Tag `protobuf:"bytes,7,rep,name=tags,proto3" json:"tags,omitempty"` +} + +func (x *Cluster) Reset() { + *x = Cluster{} + if protoimpl.UnsafeEnabled { + mi := &file_diode_v1_ingester_proto_msgTypes[2] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *Cluster) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*Cluster) ProtoMessage() {} + +func (x *Cluster) ProtoReflect() protoreflect.Message { + mi := &file_diode_v1_ingester_proto_msgTypes[2] + 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 Cluster.ProtoReflect.Descriptor instead. +func (*Cluster) Descriptor() ([]byte, []int) { + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{2} +} + +func (x *Cluster) GetName() string { + if x != nil { + return x.Name + } + return "" +} + +func (x *Cluster) GetType() *ClusterType { + if x != nil { + return x.Type + } + return nil +} + +func (x *Cluster) GetGroup() *ClusterGroup { + if x != nil { + return x.Group + } + return nil +} + +func (x *Cluster) GetSite() *Site { + if x != nil { + return x.Site + } + return nil +} + +func (x *Cluster) GetStatus() string { + if x != nil { + return x.Status + } + return "" +} + +func (x *Cluster) GetDescription() string { + if x != nil && x.Description != nil { + return *x.Description + } + return "" +} + +func (x *Cluster) GetTags() []*Tag { + if x != nil { + return x.Tags + } + return nil +} + +// A Cluster Type +type ClusterType struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` + Slug string `protobuf:"bytes,2,opt,name=slug,proto3" json:"slug,omitempty"` + Description *string `protobuf:"bytes,3,opt,name=description,proto3,oneof" json:"description,omitempty"` + Tags []*Tag `protobuf:"bytes,4,rep,name=tags,proto3" json:"tags,omitempty"` +} + +func (x *ClusterType) Reset() { + *x = ClusterType{} + if protoimpl.UnsafeEnabled { + mi := &file_diode_v1_ingester_proto_msgTypes[3] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *ClusterType) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*ClusterType) ProtoMessage() {} + +func (x *ClusterType) ProtoReflect() protoreflect.Message { + mi := &file_diode_v1_ingester_proto_msgTypes[3] + 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 ClusterType.ProtoReflect.Descriptor instead. +func (*ClusterType) Descriptor() ([]byte, []int) { + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{3} +} + +func (x *ClusterType) GetName() string { + if x != nil { + return x.Name + } + return "" +} + +func (x *ClusterType) GetSlug() string { + if x != nil { + return x.Slug + } + return "" +} + +func (x *ClusterType) GetDescription() string { + if x != nil && x.Description != nil { + return *x.Description + } + return "" +} + +func (x *ClusterType) GetTags() []*Tag { + if x != nil { + return x.Tags + } + return nil +} + +// A Cluster Group +type ClusterGroup struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` + Slug string `protobuf:"bytes,2,opt,name=slug,proto3" json:"slug,omitempty"` + Description *string `protobuf:"bytes,3,opt,name=description,proto3,oneof" json:"description,omitempty"` + Tags []*Tag `protobuf:"bytes,4,rep,name=tags,proto3" json:"tags,omitempty"` +} + +func (x *ClusterGroup) Reset() { + *x = ClusterGroup{} + if protoimpl.UnsafeEnabled { + mi := &file_diode_v1_ingester_proto_msgTypes[4] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *ClusterGroup) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*ClusterGroup) ProtoMessage() {} + +func (x *ClusterGroup) ProtoReflect() protoreflect.Message { + mi := &file_diode_v1_ingester_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 ClusterGroup.ProtoReflect.Descriptor instead. +func (*ClusterGroup) Descriptor() ([]byte, []int) { + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{4} +} + +func (x *ClusterGroup) GetName() string { + if x != nil { + return x.Name + } + return "" +} + +func (x *ClusterGroup) GetSlug() string { + if x != nil { + return x.Slug + } + return "" +} + +func (x *ClusterGroup) GetDescription() string { + if x != nil && x.Description != nil { + return *x.Description + } + return "" +} + +func (x *ClusterGroup) GetTags() []*Tag { + if x != nil { + return x.Tags + } + return nil +} + +// A Virtual Machine +type VirtualMachine struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` + Status string `protobuf:"bytes,2,opt,name=status,proto3" json:"status,omitempty"` + Site *Site `protobuf:"bytes,3,opt,name=site,proto3" json:"site,omitempty"` + Cluster *Cluster `protobuf:"bytes,4,opt,name=cluster,proto3" json:"cluster,omitempty"` + Role *Role `protobuf:"bytes,5,opt,name=role,proto3" json:"role,omitempty"` + Device *Device `protobuf:"bytes,6,opt,name=device,proto3" json:"device,omitempty"` + Platform *Platform `protobuf:"bytes,7,opt,name=platform,proto3" json:"platform,omitempty"` + PrimaryIp4 *IPAddress `protobuf:"bytes,8,opt,name=primary_ip4,json=primaryIp4,proto3" json:"primary_ip4,omitempty"` + PrimaryIp6 *IPAddress `protobuf:"bytes,9,opt,name=primary_ip6,json=primaryIp6,proto3" json:"primary_ip6,omitempty"` + Vcpus *int32 `protobuf:"varint,10,opt,name=vcpus,proto3,oneof" json:"vcpus,omitempty"` + Memory *int32 `protobuf:"varint,11,opt,name=memory,proto3,oneof" json:"memory,omitempty"` + Disk *int32 `protobuf:"varint,12,opt,name=disk,proto3,oneof" json:"disk,omitempty"` + Description *string `protobuf:"bytes,13,opt,name=description,proto3,oneof" json:"description,omitempty"` + Comments *string `protobuf:"bytes,14,opt,name=comments,proto3,oneof" json:"comments,omitempty"` + Tags []*Tag `protobuf:"bytes,15,rep,name=tags,proto3" json:"tags,omitempty"` +} + +func (x *VirtualMachine) Reset() { + *x = VirtualMachine{} + if protoimpl.UnsafeEnabled { + mi := &file_diode_v1_ingester_proto_msgTypes[5] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *VirtualMachine) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*VirtualMachine) ProtoMessage() {} + +func (x *VirtualMachine) ProtoReflect() protoreflect.Message { + mi := &file_diode_v1_ingester_proto_msgTypes[5] + 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 VirtualMachine.ProtoReflect.Descriptor instead. +func (*VirtualMachine) Descriptor() ([]byte, []int) { + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{5} +} + +func (x *VirtualMachine) GetName() string { + if x != nil { + return x.Name + } + return "" +} + +func (x *VirtualMachine) GetStatus() string { + if x != nil { + return x.Status + } + return "" +} + +func (x *VirtualMachine) GetSite() *Site { + if x != nil { + return x.Site + } + return nil +} + +func (x *VirtualMachine) GetCluster() *Cluster { + if x != nil { + return x.Cluster + } + return nil +} + +func (x *VirtualMachine) GetRole() *Role { + if x != nil { + return x.Role + } + return nil +} + +func (x *VirtualMachine) GetDevice() *Device { + if x != nil { + return x.Device + } + return nil +} + +func (x *VirtualMachine) GetPlatform() *Platform { + if x != nil { + return x.Platform + } + return nil +} + +func (x *VirtualMachine) GetPrimaryIp4() *IPAddress { + if x != nil { + return x.PrimaryIp4 + } + return nil +} + +func (x *VirtualMachine) GetPrimaryIp6() *IPAddress { + if x != nil { + return x.PrimaryIp6 + } + return nil +} + +func (x *VirtualMachine) GetVcpus() int32 { + if x != nil && x.Vcpus != nil { + return *x.Vcpus + } + return 0 +} + +func (x *VirtualMachine) GetMemory() int32 { + if x != nil && x.Memory != nil { + return *x.Memory + } + return 0 +} + +func (x *VirtualMachine) GetDisk() int32 { + if x != nil && x.Disk != nil { + return *x.Disk + } + return 0 +} + +func (x *VirtualMachine) GetDescription() string { + if x != nil && x.Description != nil { + return *x.Description + } + return "" +} + +func (x *VirtualMachine) GetComments() string { + if x != nil && x.Comments != nil { + return *x.Comments + } + return "" +} + +func (x *VirtualMachine) GetTags() []*Tag { + if x != nil { + return x.Tags + } + return nil +} + +// A Virtual Machine Interface +type VMInterface struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + VirtualMachine *VirtualMachine `protobuf:"bytes,1,opt,name=virtual_machine,json=virtualMachine,proto3" json:"virtual_machine,omitempty"` + Name string `protobuf:"bytes,2,opt,name=name,proto3" json:"name,omitempty"` + Enabled *bool `protobuf:"varint,3,opt,name=enabled,proto3,oneof" json:"enabled,omitempty"` + Mtu *int32 `protobuf:"varint,4,opt,name=mtu,proto3,oneof" json:"mtu,omitempty"` + MacAddress *string `protobuf:"bytes,5,opt,name=mac_address,json=macAddress,proto3,oneof" json:"mac_address,omitempty"` + Description *string `protobuf:"bytes,6,opt,name=description,proto3,oneof" json:"description,omitempty"` + Tags []*Tag `protobuf:"bytes,7,rep,name=tags,proto3" json:"tags,omitempty"` +} + +func (x *VMInterface) Reset() { + *x = VMInterface{} + if protoimpl.UnsafeEnabled { + mi := &file_diode_v1_ingester_proto_msgTypes[6] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *VMInterface) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*VMInterface) ProtoMessage() {} + +func (x *VMInterface) ProtoReflect() protoreflect.Message { + mi := &file_diode_v1_ingester_proto_msgTypes[6] + 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 VMInterface.ProtoReflect.Descriptor instead. +func (*VMInterface) Descriptor() ([]byte, []int) { + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{6} +} + +func (x *VMInterface) GetVirtualMachine() *VirtualMachine { + if x != nil { + return x.VirtualMachine + } + return nil +} + +func (x *VMInterface) GetName() string { + if x != nil { + return x.Name + } + return "" +} + +func (x *VMInterface) GetEnabled() bool { + if x != nil && x.Enabled != nil { + return *x.Enabled + } + return false +} + +func (x *VMInterface) GetMtu() int32 { + if x != nil && x.Mtu != nil { + return *x.Mtu + } + return 0 +} + +func (x *VMInterface) GetMacAddress() string { + if x != nil && x.MacAddress != nil { + return *x.MacAddress + } + return "" +} + +func (x *VMInterface) GetDescription() string { + if x != nil && x.Description != nil { + return *x.Description + } + return "" +} + +func (x *VMInterface) GetTags() []*Tag { + if x != nil { + return x.Tags + } + return nil +} + +// A Virtual Disk +type VirtualDisk struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + VirtualMachine *VirtualMachine `protobuf:"bytes,1,opt,name=virtual_machine,json=virtualMachine,proto3" json:"virtual_machine,omitempty"` + Name string `protobuf:"bytes,2,opt,name=name,proto3" json:"name,omitempty"` + Size int32 `protobuf:"varint,3,opt,name=size,proto3" json:"size,omitempty"` + Description *string `protobuf:"bytes,4,opt,name=description,proto3,oneof" json:"description,omitempty"` + Tags []*Tag `protobuf:"bytes,5,rep,name=tags,proto3" json:"tags,omitempty"` +} + +func (x *VirtualDisk) Reset() { + *x = VirtualDisk{} + if protoimpl.UnsafeEnabled { + mi := &file_diode_v1_ingester_proto_msgTypes[7] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *VirtualDisk) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*VirtualDisk) ProtoMessage() {} + +func (x *VirtualDisk) ProtoReflect() protoreflect.Message { + mi := &file_diode_v1_ingester_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 VirtualDisk.ProtoReflect.Descriptor instead. +func (*VirtualDisk) Descriptor() ([]byte, []int) { + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{7} +} + +func (x *VirtualDisk) GetVirtualMachine() *VirtualMachine { + if x != nil { + return x.VirtualMachine + } + return nil +} + +func (x *VirtualDisk) GetName() string { + if x != nil { + return x.Name + } + return "" +} + +func (x *VirtualDisk) GetSize() int32 { + if x != nil { + return x.Size + } + return 0 +} + +func (x *VirtualDisk) GetDescription() string { + if x != nil && x.Description != nil { + return *x.Description + } + return "" +} + +func (x *VirtualDisk) GetTags() []*Tag { + if x != nil { + return x.Tags + } + return nil +} + // An IP address. type IPAddress struct { state protoimpl.MessageState @@ -348,7 +924,7 @@ type IPAddress struct { func (x *IPAddress) Reset() { *x = IPAddress{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[2] + mi := &file_diode_v1_ingester_proto_msgTypes[8] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -361,7 +937,7 @@ func (x *IPAddress) String() string { func (*IPAddress) ProtoMessage() {} func (x *IPAddress) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[2] + mi := &file_diode_v1_ingester_proto_msgTypes[8] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -374,7 +950,7 @@ func (x *IPAddress) ProtoReflect() protoreflect.Message { // Deprecated: Use IPAddress.ProtoReflect.Descriptor instead. func (*IPAddress) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{2} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{8} } func (x *IPAddress) GetAddress() string { @@ -468,7 +1044,7 @@ type DeviceType struct { func (x *DeviceType) Reset() { *x = DeviceType{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[3] + mi := &file_diode_v1_ingester_proto_msgTypes[9] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -481,7 +1057,7 @@ func (x *DeviceType) String() string { func (*DeviceType) ProtoMessage() {} func (x *DeviceType) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[3] + mi := &file_diode_v1_ingester_proto_msgTypes[9] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -494,7 +1070,7 @@ func (x *DeviceType) ProtoReflect() protoreflect.Message { // Deprecated: Use DeviceType.ProtoReflect.Descriptor instead. func (*DeviceType) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{3} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{9} } func (x *DeviceType) GetModel() string { @@ -561,7 +1137,7 @@ type Manufacturer struct { func (x *Manufacturer) Reset() { *x = Manufacturer{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[4] + mi := &file_diode_v1_ingester_proto_msgTypes[10] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -574,7 +1150,7 @@ func (x *Manufacturer) String() string { func (*Manufacturer) ProtoMessage() {} func (x *Manufacturer) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[4] + mi := &file_diode_v1_ingester_proto_msgTypes[10] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -587,7 +1163,7 @@ func (x *Manufacturer) ProtoReflect() protoreflect.Message { // Deprecated: Use Manufacturer.ProtoReflect.Descriptor instead. func (*Manufacturer) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{4} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{10} } func (x *Manufacturer) GetName() string { @@ -634,7 +1210,7 @@ type Platform struct { func (x *Platform) Reset() { *x = Platform{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[5] + mi := &file_diode_v1_ingester_proto_msgTypes[11] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -647,7 +1223,7 @@ func (x *Platform) String() string { func (*Platform) ProtoMessage() {} func (x *Platform) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[5] + mi := &file_diode_v1_ingester_proto_msgTypes[11] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -660,7 +1236,7 @@ func (x *Platform) ProtoReflect() protoreflect.Message { // Deprecated: Use Platform.ProtoReflect.Descriptor instead. func (*Platform) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{5} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{11} } func (x *Platform) GetName() string { @@ -717,7 +1293,7 @@ type Prefix struct { func (x *Prefix) Reset() { *x = Prefix{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[6] + mi := &file_diode_v1_ingester_proto_msgTypes[12] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -730,7 +1306,7 @@ func (x *Prefix) String() string { func (*Prefix) ProtoMessage() {} func (x *Prefix) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[6] + mi := &file_diode_v1_ingester_proto_msgTypes[12] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -743,7 +1319,7 @@ func (x *Prefix) ProtoReflect() protoreflect.Message { // Deprecated: Use Prefix.ProtoReflect.Descriptor instead. func (*Prefix) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{6} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{12} } func (x *Prefix) GetPrefix() string { @@ -818,7 +1394,7 @@ type Role struct { func (x *Role) Reset() { *x = Role{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[7] + mi := &file_diode_v1_ingester_proto_msgTypes[13] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -831,7 +1407,7 @@ func (x *Role) String() string { func (*Role) ProtoMessage() {} func (x *Role) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[7] + mi := &file_diode_v1_ingester_proto_msgTypes[13] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -844,7 +1420,7 @@ func (x *Role) ProtoReflect() protoreflect.Message { // Deprecated: Use Role.ProtoReflect.Descriptor instead. func (*Role) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{7} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{13} } func (x *Role) GetName() string { @@ -901,7 +1477,7 @@ type Site struct { func (x *Site) Reset() { *x = Site{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[8] + mi := &file_diode_v1_ingester_proto_msgTypes[14] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -914,7 +1490,7 @@ func (x *Site) String() string { func (*Site) ProtoMessage() {} func (x *Site) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[8] + mi := &file_diode_v1_ingester_proto_msgTypes[14] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -927,7 +1503,7 @@ func (x *Site) ProtoReflect() protoreflect.Message { // Deprecated: Use Site.ProtoReflect.Descriptor instead. func (*Site) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{8} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{14} } func (x *Site) GetName() string { @@ -1000,7 +1576,7 @@ type Tag struct { func (x *Tag) Reset() { *x = Tag{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[9] + mi := &file_diode_v1_ingester_proto_msgTypes[15] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1013,7 +1589,7 @@ func (x *Tag) String() string { func (*Tag) ProtoMessage() {} func (x *Tag) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[9] + mi := &file_diode_v1_ingester_proto_msgTypes[15] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1026,7 +1602,7 @@ func (x *Tag) ProtoReflect() protoreflect.Message { // Deprecated: Use Tag.ProtoReflect.Descriptor instead. func (*Tag) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{9} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{15} } func (x *Tag) GetName() string { @@ -1067,6 +1643,12 @@ type Entity struct { // *Entity_Interface // *Entity_IpAddress // *Entity_Prefix + // *Entity_ClusterGroup + // *Entity_ClusterType + // *Entity_Cluster + // *Entity_VirtualMachine + // *Entity_Vminterface + // *Entity_VirtualDisk Entity isEntity_Entity `protobuf_oneof:"entity"` // The timestamp of the data discovery at source Timestamp *timestamppb.Timestamp `protobuf:"bytes,8,opt,name=timestamp,proto3" json:"timestamp,omitempty"` @@ -1075,7 +1657,7 @@ type Entity struct { func (x *Entity) Reset() { *x = Entity{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[10] + mi := &file_diode_v1_ingester_proto_msgTypes[16] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1088,7 +1670,7 @@ func (x *Entity) String() string { func (*Entity) ProtoMessage() {} func (x *Entity) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[10] + mi := &file_diode_v1_ingester_proto_msgTypes[16] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1101,7 +1683,7 @@ func (x *Entity) ProtoReflect() protoreflect.Message { // Deprecated: Use Entity.ProtoReflect.Descriptor instead. func (*Entity) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{10} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{16} } func (m *Entity) GetEntity() isEntity_Entity { @@ -1174,6 +1756,48 @@ func (x *Entity) GetPrefix() *Prefix { return nil } +func (x *Entity) GetClusterGroup() *ClusterGroup { + if x, ok := x.GetEntity().(*Entity_ClusterGroup); ok { + return x.ClusterGroup + } + return nil +} + +func (x *Entity) GetClusterType() *ClusterType { + if x, ok := x.GetEntity().(*Entity_ClusterType); ok { + return x.ClusterType + } + return nil +} + +func (x *Entity) GetCluster() *Cluster { + if x, ok := x.GetEntity().(*Entity_Cluster); ok { + return x.Cluster + } + return nil +} + +func (x *Entity) GetVirtualMachine() *VirtualMachine { + if x, ok := x.GetEntity().(*Entity_VirtualMachine); ok { + return x.VirtualMachine + } + return nil +} + +func (x *Entity) GetVminterface() *VMInterface { + if x, ok := x.GetEntity().(*Entity_Vminterface); ok { + return x.Vminterface + } + return nil +} + +func (x *Entity) GetVirtualDisk() *VirtualDisk { + if x, ok := x.GetEntity().(*Entity_VirtualDisk); ok { + return x.VirtualDisk + } + return nil +} + func (x *Entity) GetTimestamp() *timestamppb.Timestamp { if x != nil { return x.Timestamp @@ -1221,6 +1845,30 @@ type Entity_Prefix struct { Prefix *Prefix `protobuf:"bytes,10,opt,name=prefix,proto3,oneof"` } +type Entity_ClusterGroup struct { + ClusterGroup *ClusterGroup `protobuf:"bytes,11,opt,name=cluster_group,json=clusterGroup,proto3,oneof"` +} + +type Entity_ClusterType struct { + ClusterType *ClusterType `protobuf:"bytes,12,opt,name=cluster_type,json=clusterType,proto3,oneof"` +} + +type Entity_Cluster struct { + Cluster *Cluster `protobuf:"bytes,13,opt,name=cluster,proto3,oneof"` +} + +type Entity_VirtualMachine struct { + VirtualMachine *VirtualMachine `protobuf:"bytes,14,opt,name=virtual_machine,json=virtualMachine,proto3,oneof"` +} + +type Entity_Vminterface struct { + Vminterface *VMInterface `protobuf:"bytes,15,opt,name=vminterface,proto3,oneof"` +} + +type Entity_VirtualDisk struct { + VirtualDisk *VirtualDisk `protobuf:"bytes,16,opt,name=virtual_disk,json=virtualDisk,proto3,oneof"` +} + func (*Entity_Site) isEntity_Entity() {} func (*Entity_Platform) isEntity_Entity() {} @@ -1239,6 +1887,18 @@ func (*Entity_IpAddress) isEntity_Entity() {} func (*Entity_Prefix) isEntity_Entity() {} +func (*Entity_ClusterGroup) isEntity_Entity() {} + +func (*Entity_ClusterType) isEntity_Entity() {} + +func (*Entity_Cluster) isEntity_Entity() {} + +func (*Entity_VirtualMachine) isEntity_Entity() {} + +func (*Entity_Vminterface) isEntity_Entity() {} + +func (*Entity_VirtualDisk) isEntity_Entity() {} + // The request to ingest the data type IngestRequest struct { state protoimpl.MessageState @@ -1257,7 +1917,7 @@ type IngestRequest struct { func (x *IngestRequest) Reset() { *x = IngestRequest{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[11] + mi := &file_diode_v1_ingester_proto_msgTypes[17] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1270,7 +1930,7 @@ func (x *IngestRequest) String() string { func (*IngestRequest) ProtoMessage() {} func (x *IngestRequest) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[11] + mi := &file_diode_v1_ingester_proto_msgTypes[17] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1283,7 +1943,7 @@ func (x *IngestRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use IngestRequest.ProtoReflect.Descriptor instead. func (*IngestRequest) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{11} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{17} } func (x *IngestRequest) GetStream() string { @@ -1347,7 +2007,7 @@ type IngestResponse struct { func (x *IngestResponse) Reset() { *x = IngestResponse{} if protoimpl.UnsafeEnabled { - mi := &file_diode_v1_ingester_proto_msgTypes[12] + mi := &file_diode_v1_ingester_proto_msgTypes[18] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1360,7 +2020,7 @@ func (x *IngestResponse) String() string { func (*IngestResponse) ProtoMessage() {} func (x *IngestResponse) ProtoReflect() protoreflect.Message { - mi := &file_diode_v1_ingester_proto_msgTypes[12] + mi := &file_diode_v1_ingester_proto_msgTypes[18] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1373,7 +2033,7 @@ func (x *IngestResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use IngestResponse.ProtoReflect.Descriptor instead. func (*IngestResponse) Descriptor() ([]byte, []int) { - return file_diode_v1_ingester_proto_rawDescGZIP(), []int{12} + return file_diode_v1_ingester_proto_rawDescGZIP(), []int{18} } func (x *IngestResponse) GetErrors() []string { @@ -1581,194 +2241,348 @@ var file_diode_v1_ingester_proto_rawDesc = []byte{ 0x04, 0x5f, 0x77, 0x77, 0x6e, 0x42, 0x0c, 0x0a, 0x0a, 0x5f, 0x6d, 0x67, 0x6d, 0x74, 0x5f, 0x6f, 0x6e, 0x6c, 0x79, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x11, 0x0a, 0x0f, 0x5f, 0x6d, 0x61, 0x72, 0x6b, 0x5f, 0x63, 0x6f, 0x6e, - 0x6e, 0x65, 0x63, 0x74, 0x65, 0x64, 0x22, 0x8c, 0x04, 0x0a, 0x09, 0x49, 0x50, 0x41, 0x64, 0x64, - 0x72, 0x65, 0x73, 0x73, 0x12, 0x21, 0x0a, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, - 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x70, 0x01, 0x52, 0x07, - 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x12, 0x33, 0x0a, 0x09, 0x69, 0x6e, 0x74, 0x65, 0x72, - 0x66, 0x61, 0x63, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, 0x6f, - 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x48, - 0x00, 0x52, 0x09, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x48, 0x0a, 0x06, - 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x30, 0xfa, 0x42, - 0x2d, 0x72, 0x2b, 0x52, 0x06, 0x61, 0x63, 0x74, 0x69, 0x76, 0x65, 0x52, 0x08, 0x72, 0x65, 0x73, - 0x65, 0x72, 0x76, 0x65, 0x64, 0x52, 0x0a, 0x64, 0x65, 0x70, 0x72, 0x65, 0x63, 0x61, 0x74, 0x65, - 0x64, 0x52, 0x04, 0x64, 0x68, 0x63, 0x70, 0x52, 0x05, 0x73, 0x6c, 0x61, 0x61, 0x63, 0x52, 0x06, - 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x54, 0x0a, 0x04, 0x72, 0x6f, 0x6c, 0x65, 0x18, 0x04, - 0x20, 0x01, 0x28, 0x09, 0x42, 0x40, 0xfa, 0x42, 0x3d, 0x72, 0x3b, 0x52, 0x08, 0x6c, 0x6f, 0x6f, - 0x70, 0x62, 0x61, 0x63, 0x6b, 0x52, 0x09, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64, 0x61, 0x72, 0x79, - 0x52, 0x07, 0x61, 0x6e, 0x79, 0x63, 0x61, 0x73, 0x74, 0x52, 0x03, 0x76, 0x69, 0x70, 0x52, 0x04, - 0x76, 0x72, 0x72, 0x70, 0x52, 0x04, 0x68, 0x73, 0x72, 0x70, 0x52, 0x04, 0x67, 0x6c, 0x62, 0x70, - 0x52, 0x04, 0x63, 0x61, 0x72, 0x70, 0x52, 0x04, 0x72, 0x6f, 0x6c, 0x65, 0x12, 0x55, 0x0a, 0x08, - 0x64, 0x6e, 0x73, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x42, 0x35, - 0xfa, 0x42, 0x32, 0x72, 0x30, 0x18, 0xff, 0x01, 0x32, 0x2b, 0x5e, 0x28, 0x5b, 0x30, 0x2d, 0x39, - 0x41, 0x2d, 0x5a, 0x61, 0x2d, 0x7a, 0x5f, 0x2d, 0x5d, 0x2b, 0x7c, 0x5c, 0x2a, 0x29, 0x28, 0x5c, - 0x2e, 0x5b, 0x30, 0x2d, 0x39, 0x41, 0x2d, 0x5a, 0x61, 0x2d, 0x7a, 0x5f, 0x2d, 0x5d, 0x2b, 0x29, - 0x2a, 0x5c, 0x2e, 0x3f, 0x24, 0x48, 0x01, 0x52, 0x07, 0x64, 0x6e, 0x73, 0x4e, 0x61, 0x6d, 0x65, - 0x88, 0x01, 0x01, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, - 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, - 0xc8, 0x01, 0x48, 0x02, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, - 0x6e, 0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, - 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x48, 0x03, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, - 0x74, 0x73, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x08, 0x20, - 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, - 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x11, 0x0a, 0x0f, 0x61, 0x73, 0x73, 0x69, - 0x67, 0x6e, 0x65, 0x64, 0x5f, 0x6f, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x42, 0x0b, 0x0a, 0x09, 0x5f, - 0x64, 0x6e, 0x73, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, - 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, 0x6d, - 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x22, 0xeb, 0x02, 0x0a, 0x0a, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, - 0x54, 0x79, 0x70, 0x65, 0x12, 0x1f, 0x0a, 0x05, 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x18, 0x01, 0x20, - 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x05, - 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, - 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, - 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, - 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x3a, 0x0a, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, - 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x64, - 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x4d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, - 0x75, 0x72, 0x65, 0x72, 0x52, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, - 0x65, 0x72, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, - 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, - 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, - 0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, - 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, - 0x73, 0x88, 0x01, 0x01, 0x12, 0x2d, 0x0a, 0x0b, 0x70, 0x61, 0x72, 0x74, 0x5f, 0x6e, 0x75, 0x6d, - 0x62, 0x65, 0x72, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, - 0x18, 0x32, 0x48, 0x02, 0x52, 0x0a, 0x70, 0x61, 0x72, 0x74, 0x4e, 0x75, 0x6d, 0x62, 0x65, 0x72, - 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x07, 0x20, 0x03, 0x28, - 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, - 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, - 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, - 0x6e, 0x74, 0x73, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x70, 0x61, 0x72, 0x74, 0x5f, 0x6e, 0x75, 0x6d, - 0x62, 0x65, 0x72, 0x22, 0xc2, 0x01, 0x0a, 0x0c, 0x4d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, - 0x75, 0x72, 0x65, 0x72, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, - 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, - 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, - 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, 0x5b, - 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, - 0x73, 0x6c, 0x75, 0x67, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, - 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, - 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, - 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x04, 0x20, - 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, - 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, - 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xfa, 0x01, 0x0a, 0x08, 0x50, 0x6c, 0x61, - 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, - 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, - 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, - 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, - 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, - 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x3a, 0x0a, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, - 0x74, 0x75, 0x72, 0x65, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x64, 0x69, - 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x4d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, - 0x72, 0x65, 0x72, 0x52, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, - 0x72, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, - 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, + 0x6e, 0x65, 0x63, 0x74, 0x65, 0x64, 0x22, 0xe3, 0x02, 0x0a, 0x07, 0x43, 0x6c, 0x75, 0x73, 0x74, + 0x65, 0x72, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, + 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, + 0x65, 0x12, 0x29, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, + 0x15, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x43, 0x6c, 0x75, 0x73, 0x74, + 0x65, 0x72, 0x54, 0x79, 0x70, 0x65, 0x52, 0x04, 0x74, 0x79, 0x70, 0x65, 0x12, 0x2c, 0x0a, 0x05, + 0x67, 0x72, 0x6f, 0x75, 0x70, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x64, 0x69, + 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x47, 0x72, + 0x6f, 0x75, 0x70, 0x52, 0x05, 0x67, 0x72, 0x6f, 0x75, 0x70, 0x12, 0x22, 0x0a, 0x04, 0x73, 0x69, + 0x74, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, + 0x2e, 0x76, 0x31, 0x2e, 0x53, 0x69, 0x74, 0x65, 0x52, 0x04, 0x73, 0x69, 0x74, 0x65, 0x12, 0x58, + 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x42, 0x40, + 0xfa, 0x42, 0x3d, 0x72, 0x3b, 0x52, 0x07, 0x6f, 0x66, 0x66, 0x6c, 0x69, 0x6e, 0x65, 0x52, 0x06, + 0x61, 0x63, 0x74, 0x69, 0x76, 0x65, 0x52, 0x07, 0x70, 0x6c, 0x61, 0x6e, 0x6e, 0x65, 0x64, 0x52, + 0x06, 0x73, 0x74, 0x61, 0x67, 0x65, 0x64, 0x52, 0x06, 0x66, 0x61, 0x69, 0x6c, 0x65, 0x64, 0x52, + 0x0f, 0x64, 0x65, 0x63, 0x6f, 0x6d, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x69, 0x6e, 0x67, + 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, + 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, + 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, + 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, + 0x73, 0x18, 0x07, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, + 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0e, 0x0a, 0x0c, + 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xc1, 0x01, 0x0a, + 0x0b, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x54, 0x79, 0x70, 0x65, 0x12, 0x1d, 0x0a, 0x04, + 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, + 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, + 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, + 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, + 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x2f, 0x0a, 0x0b, + 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, + 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, + 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, + 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, + 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, + 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, + 0x22, 0xc2, 0x01, 0x0a, 0x0c, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x47, 0x72, 0x6f, 0x75, + 0x70, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, + 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, + 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, + 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, + 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, + 0x67, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, + 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, - 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, + 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, - 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x8d, 0x03, 0x0a, 0x06, 0x50, 0x72, 0x65, 0x66, 0x69, 0x78, - 0x12, 0x1f, 0x0a, 0x06, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, - 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x70, 0x01, 0x52, 0x06, 0x70, 0x72, 0x65, 0x66, 0x69, - 0x78, 0x12, 0x22, 0x0a, 0x04, 0x73, 0x69, 0x74, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, - 0x0e, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x53, 0x69, 0x74, 0x65, 0x52, - 0x04, 0x73, 0x69, 0x74, 0x65, 0x12, 0x46, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, - 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x2e, 0xfa, 0x42, 0x2b, 0x72, 0x29, 0x52, 0x06, 0x61, 0x63, - 0x74, 0x69, 0x76, 0x65, 0x52, 0x09, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, - 0x08, 0x72, 0x65, 0x73, 0x65, 0x72, 0x76, 0x65, 0x64, 0x52, 0x0a, 0x64, 0x65, 0x70, 0x72, 0x65, - 0x63, 0x61, 0x74, 0x65, 0x64, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x1c, 0x0a, - 0x07, 0x69, 0x73, 0x5f, 0x70, 0x6f, 0x6f, 0x6c, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x48, 0x00, - 0x52, 0x06, 0x69, 0x73, 0x50, 0x6f, 0x6f, 0x6c, 0x88, 0x01, 0x01, 0x12, 0x28, 0x0a, 0x0d, 0x6d, - 0x61, 0x72, 0x6b, 0x5f, 0x75, 0x74, 0x69, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x18, 0x05, 0x20, 0x01, - 0x28, 0x08, 0x48, 0x01, 0x52, 0x0c, 0x6d, 0x61, 0x72, 0x6b, 0x55, 0x74, 0x69, 0x6c, 0x69, 0x7a, - 0x65, 0x64, 0x88, 0x01, 0x01, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, - 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, - 0x03, 0x18, 0xc8, 0x01, 0x48, 0x02, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, - 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, - 0x74, 0x73, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x48, 0x03, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, - 0x65, 0x6e, 0x74, 0x73, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, - 0x08, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, - 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x69, - 0x73, 0x5f, 0x70, 0x6f, 0x6f, 0x6c, 0x42, 0x10, 0x0a, 0x0e, 0x5f, 0x6d, 0x61, 0x72, 0x6b, 0x5f, - 0x75, 0x74, 0x69, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, - 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, 0x6d, - 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x22, 0xea, 0x01, 0x0a, 0x04, 0x52, 0x6f, 0x6c, 0x65, 0x12, 0x1d, + 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xde, 0x05, 0x0a, 0x0e, 0x56, 0x69, 0x72, 0x74, 0x75, 0x61, + 0x6c, 0x4d, 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x12, 0x1b, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, + 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x18, 0x40, 0x52, + 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x58, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, + 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x40, 0xfa, 0x42, 0x3d, 0x72, 0x3b, 0x52, 0x07, 0x6f, 0x66, + 0x66, 0x6c, 0x69, 0x6e, 0x65, 0x52, 0x06, 0x61, 0x63, 0x74, 0x69, 0x76, 0x65, 0x52, 0x07, 0x70, + 0x6c, 0x61, 0x6e, 0x6e, 0x65, 0x64, 0x52, 0x06, 0x73, 0x74, 0x61, 0x67, 0x65, 0x64, 0x52, 0x06, + 0x66, 0x61, 0x69, 0x6c, 0x65, 0x64, 0x52, 0x0f, 0x64, 0x65, 0x63, 0x6f, 0x6d, 0x6d, 0x69, 0x73, + 0x73, 0x69, 0x6f, 0x6e, 0x69, 0x6e, 0x67, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, + 0x22, 0x0a, 0x04, 0x73, 0x69, 0x74, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, + 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x53, 0x69, 0x74, 0x65, 0x52, 0x04, 0x73, + 0x69, 0x74, 0x65, 0x12, 0x2b, 0x0a, 0x07, 0x63, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x18, 0x04, + 0x20, 0x01, 0x28, 0x0b, 0x32, 0x11, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, + 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x52, 0x07, 0x63, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, + 0x12, 0x22, 0x0a, 0x04, 0x72, 0x6f, 0x6c, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, + 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x52, 0x6f, 0x6c, 0x65, 0x52, 0x04, + 0x72, 0x6f, 0x6c, 0x65, 0x12, 0x28, 0x0a, 0x06, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x18, 0x06, + 0x20, 0x01, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, + 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x52, 0x06, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x12, 0x2e, + 0x0a, 0x08, 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0b, + 0x32, 0x12, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x50, 0x6c, 0x61, 0x74, + 0x66, 0x6f, 0x72, 0x6d, 0x52, 0x08, 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x12, 0x34, + 0x0a, 0x0b, 0x70, 0x72, 0x69, 0x6d, 0x61, 0x72, 0x79, 0x5f, 0x69, 0x70, 0x34, 0x18, 0x08, 0x20, + 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x49, + 0x50, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x52, 0x0a, 0x70, 0x72, 0x69, 0x6d, 0x61, 0x72, + 0x79, 0x49, 0x70, 0x34, 0x12, 0x34, 0x0a, 0x0b, 0x70, 0x72, 0x69, 0x6d, 0x61, 0x72, 0x79, 0x5f, + 0x69, 0x70, 0x36, 0x18, 0x09, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, 0x6f, 0x64, + 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x49, 0x50, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x52, 0x0a, + 0x70, 0x72, 0x69, 0x6d, 0x61, 0x72, 0x79, 0x49, 0x70, 0x36, 0x12, 0x22, 0x0a, 0x05, 0x76, 0x63, + 0x70, 0x75, 0x73, 0x18, 0x0a, 0x20, 0x01, 0x28, 0x05, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x1a, 0x02, + 0x28, 0x00, 0x48, 0x00, 0x52, 0x05, 0x76, 0x63, 0x70, 0x75, 0x73, 0x88, 0x01, 0x01, 0x12, 0x24, + 0x0a, 0x06, 0x6d, 0x65, 0x6d, 0x6f, 0x72, 0x79, 0x18, 0x0b, 0x20, 0x01, 0x28, 0x05, 0x42, 0x07, + 0xfa, 0x42, 0x04, 0x1a, 0x02, 0x28, 0x00, 0x48, 0x01, 0x52, 0x06, 0x6d, 0x65, 0x6d, 0x6f, 0x72, + 0x79, 0x88, 0x01, 0x01, 0x12, 0x20, 0x0a, 0x04, 0x64, 0x69, 0x73, 0x6b, 0x18, 0x0c, 0x20, 0x01, + 0x28, 0x05, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x1a, 0x02, 0x28, 0x00, 0x48, 0x02, 0x52, 0x04, 0x64, + 0x69, 0x73, 0x6b, 0x88, 0x01, 0x01, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, + 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x0d, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, + 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x03, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, + 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, + 0x6e, 0x74, 0x73, 0x18, 0x0e, 0x20, 0x01, 0x28, 0x09, 0x48, 0x04, 0x52, 0x08, 0x63, 0x6f, 0x6d, + 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, + 0x18, 0x0f, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, + 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x08, 0x0a, 0x06, 0x5f, + 0x76, 0x63, 0x70, 0x75, 0x73, 0x42, 0x09, 0x0a, 0x07, 0x5f, 0x6d, 0x65, 0x6d, 0x6f, 0x72, 0x79, + 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x64, 0x69, 0x73, 0x6b, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, + 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, + 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x22, 0xea, 0x02, 0x0a, 0x0b, 0x56, 0x4d, 0x49, 0x6e, 0x74, + 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x4b, 0x0a, 0x0f, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, + 0x6c, 0x5f, 0x6d, 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, + 0x18, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x56, 0x69, 0x72, 0x74, 0x75, + 0x61, 0x6c, 0x4d, 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x42, 0x08, 0xfa, 0x42, 0x05, 0xa2, 0x01, + 0x02, 0x08, 0x01, 0x52, 0x0e, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x4d, 0x61, 0x63, 0x68, + 0x69, 0x6e, 0x65, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, + 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x40, 0x52, 0x04, 0x6e, 0x61, + 0x6d, 0x65, 0x12, 0x1d, 0x0a, 0x07, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x18, 0x03, 0x20, + 0x01, 0x28, 0x08, 0x48, 0x00, 0x52, 0x07, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x88, 0x01, + 0x01, 0x12, 0x22, 0x0a, 0x03, 0x6d, 0x74, 0x75, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x42, 0x0b, + 0xfa, 0x42, 0x08, 0x1a, 0x06, 0x18, 0x80, 0x80, 0x04, 0x28, 0x01, 0x48, 0x01, 0x52, 0x03, 0x6d, + 0x74, 0x75, 0x88, 0x01, 0x01, 0x12, 0x24, 0x0a, 0x0b, 0x6d, 0x61, 0x63, 0x5f, 0x61, 0x64, 0x64, + 0x72, 0x65, 0x73, 0x73, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x02, 0x52, 0x0a, 0x6d, 0x61, + 0x63, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x88, 0x01, 0x01, 0x12, 0x2f, 0x0a, 0x0b, 0x64, + 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, + 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x03, 0x52, 0x0b, 0x64, 0x65, + 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, + 0x74, 0x61, 0x67, 0x73, 0x18, 0x07, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, + 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, + 0x0a, 0x0a, 0x08, 0x5f, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x42, 0x06, 0x0a, 0x04, 0x5f, + 0x6d, 0x74, 0x75, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x6d, 0x61, 0x63, 0x5f, 0x61, 0x64, 0x64, 0x72, + 0x65, 0x73, 0x73, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, + 0x69, 0x6f, 0x6e, 0x22, 0xfa, 0x01, 0x0a, 0x0b, 0x56, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x44, + 0x69, 0x73, 0x6b, 0x12, 0x4b, 0x0a, 0x0f, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x5f, 0x6d, + 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x18, 0x2e, 0x64, + 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x56, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x4d, + 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x42, 0x08, 0xfa, 0x42, 0x05, 0xa2, 0x01, 0x02, 0x08, 0x01, + 0x52, 0x0e, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x4d, 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, + 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, + 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, + 0x1b, 0x0a, 0x04, 0x73, 0x69, 0x7a, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x05, 0x42, 0x07, 0xfa, + 0x42, 0x04, 0x1a, 0x02, 0x28, 0x00, 0x52, 0x04, 0x73, 0x69, 0x7a, 0x65, 0x12, 0x2f, 0x0a, 0x0b, + 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, + 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, + 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, + 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, + 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, + 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, + 0x22, 0x8c, 0x04, 0x0a, 0x09, 0x49, 0x50, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x12, 0x21, + 0x0a, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, + 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x70, 0x01, 0x52, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, + 0x73, 0x12, 0x33, 0x0a, 0x09, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x18, 0x02, + 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, + 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x48, 0x00, 0x52, 0x09, 0x69, 0x6e, 0x74, + 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x48, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, + 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x30, 0xfa, 0x42, 0x2d, 0x72, 0x2b, 0x52, 0x06, 0x61, + 0x63, 0x74, 0x69, 0x76, 0x65, 0x52, 0x08, 0x72, 0x65, 0x73, 0x65, 0x72, 0x76, 0x65, 0x64, 0x52, + 0x0a, 0x64, 0x65, 0x70, 0x72, 0x65, 0x63, 0x61, 0x74, 0x65, 0x64, 0x52, 0x04, 0x64, 0x68, 0x63, + 0x70, 0x52, 0x05, 0x73, 0x6c, 0x61, 0x61, 0x63, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, + 0x12, 0x54, 0x0a, 0x04, 0x72, 0x6f, 0x6c, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x42, 0x40, + 0xfa, 0x42, 0x3d, 0x72, 0x3b, 0x52, 0x08, 0x6c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x52, + 0x09, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64, 0x61, 0x72, 0x79, 0x52, 0x07, 0x61, 0x6e, 0x79, 0x63, + 0x61, 0x73, 0x74, 0x52, 0x03, 0x76, 0x69, 0x70, 0x52, 0x04, 0x76, 0x72, 0x72, 0x70, 0x52, 0x04, + 0x68, 0x73, 0x72, 0x70, 0x52, 0x04, 0x67, 0x6c, 0x62, 0x70, 0x52, 0x04, 0x63, 0x61, 0x72, 0x70, + 0x52, 0x04, 0x72, 0x6f, 0x6c, 0x65, 0x12, 0x55, 0x0a, 0x08, 0x64, 0x6e, 0x73, 0x5f, 0x6e, 0x61, + 0x6d, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x42, 0x35, 0xfa, 0x42, 0x32, 0x72, 0x30, 0x18, + 0xff, 0x01, 0x32, 0x2b, 0x5e, 0x28, 0x5b, 0x30, 0x2d, 0x39, 0x41, 0x2d, 0x5a, 0x61, 0x2d, 0x7a, + 0x5f, 0x2d, 0x5d, 0x2b, 0x7c, 0x5c, 0x2a, 0x29, 0x28, 0x5c, 0x2e, 0x5b, 0x30, 0x2d, 0x39, 0x41, + 0x2d, 0x5a, 0x61, 0x2d, 0x7a, 0x5f, 0x2d, 0x5d, 0x2b, 0x29, 0x2a, 0x5c, 0x2e, 0x3f, 0x24, 0x48, + 0x01, 0x52, 0x07, 0x64, 0x6e, 0x73, 0x4e, 0x61, 0x6d, 0x65, 0x88, 0x01, 0x01, 0x12, 0x2f, 0x0a, + 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, + 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x02, 0x52, 0x0b, + 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x1f, + 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, + 0x48, 0x03, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x88, 0x01, 0x01, 0x12, + 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x08, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, + 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, + 0x67, 0x73, 0x42, 0x11, 0x0a, 0x0f, 0x61, 0x73, 0x73, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x5f, 0x6f, + 0x62, 0x6a, 0x65, 0x63, 0x74, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x64, 0x6e, 0x73, 0x5f, 0x6e, 0x61, + 0x6d, 0x65, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, + 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x22, + 0xeb, 0x02, 0x0a, 0x0a, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x54, 0x79, 0x70, 0x65, 0x12, 0x1f, + 0x0a, 0x05, 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, + 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x05, 0x6d, 0x6f, 0x64, 0x65, 0x6c, 0x12, + 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, + 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, + 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, + 0x12, 0x3a, 0x0a, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, + 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, + 0x31, 0x2e, 0x4d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x52, 0x0c, + 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x12, 0x2f, 0x0a, 0x0b, + 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, + 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, + 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, + 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, + 0x01, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x88, 0x01, 0x01, 0x12, 0x2d, + 0x0a, 0x0b, 0x70, 0x61, 0x72, 0x74, 0x5f, 0x6e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x18, 0x06, 0x20, + 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x18, 0x32, 0x48, 0x02, 0x52, 0x0a, + 0x70, 0x61, 0x72, 0x74, 0x4e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, + 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x07, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, + 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, + 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, + 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x42, 0x0e, 0x0a, + 0x0c, 0x5f, 0x70, 0x61, 0x72, 0x74, 0x5f, 0x6e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x22, 0xc2, 0x01, + 0x0a, 0x0c, 0x4d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, - 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x2e, - 0x0a, 0x05, 0x63, 0x6f, 0x6c, 0x6f, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x18, 0xfa, - 0x42, 0x15, 0x72, 0x13, 0x10, 0x06, 0x18, 0x06, 0x32, 0x0d, 0x5e, 0x5b, 0x30, 0x2d, 0x39, 0x61, - 0x2d, 0x66, 0x5d, 0x7b, 0x36, 0x7d, 0x24, 0x52, 0x05, 0x63, 0x6f, 0x6c, 0x6f, 0x72, 0x12, 0x2f, - 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, + 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x2f, + 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, - 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, + 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, - 0x6f, 0x6e, 0x22, 0xa2, 0x03, 0x0a, 0x04, 0x53, 0x69, 0x74, 0x65, 0x12, 0x1d, 0x0a, 0x04, 0x6e, - 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, - 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, - 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, - 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, - 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x51, 0x0a, 0x06, 0x73, - 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x39, 0xfa, 0x42, 0x36, - 0x72, 0x34, 0x52, 0x07, 0x70, 0x6c, 0x61, 0x6e, 0x6e, 0x65, 0x64, 0x52, 0x07, 0x73, 0x74, 0x61, - 0x67, 0x69, 0x6e, 0x67, 0x52, 0x06, 0x61, 0x63, 0x74, 0x69, 0x76, 0x65, 0x52, 0x0f, 0x64, 0x65, - 0x63, 0x6f, 0x6d, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x69, 0x6e, 0x67, 0x52, 0x07, 0x72, - 0x65, 0x74, 0x69, 0x72, 0x65, 0x64, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x28, - 0x0a, 0x08, 0x66, 0x61, 0x63, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, - 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x18, 0x32, 0x48, 0x00, 0x52, 0x08, 0x66, 0x61, 0x63, - 0x69, 0x6c, 0x69, 0x74, 0x79, 0x88, 0x01, 0x01, 0x12, 0x20, 0x0a, 0x09, 0x74, 0x69, 0x6d, 0x65, - 0x5f, 0x7a, 0x6f, 0x6e, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x08, 0x74, - 0x69, 0x6d, 0x65, 0x5a, 0x6f, 0x6e, 0x65, 0x88, 0x01, 0x01, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, - 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x42, - 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x02, 0x52, 0x0b, 0x64, 0x65, 0x73, - 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, 0x08, 0x63, - 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x48, 0x03, 0x52, - 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, - 0x74, 0x61, 0x67, 0x73, 0x18, 0x08, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, - 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, - 0x0b, 0x0a, 0x09, 0x5f, 0x66, 0x61, 0x63, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x42, 0x0c, 0x0a, 0x0a, - 0x5f, 0x74, 0x69, 0x6d, 0x65, 0x5f, 0x7a, 0x6f, 0x6e, 0x65, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, - 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, - 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x22, 0x85, 0x01, 0x0a, 0x03, 0x54, 0x61, 0x67, 0x12, + 0x6f, 0x6e, 0x22, 0xfa, 0x01, 0x0a, 0x08, 0x50, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, - 0x2e, 0x0a, 0x05, 0x63, 0x6f, 0x6c, 0x6f, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x18, - 0xfa, 0x42, 0x15, 0x72, 0x13, 0x10, 0x06, 0x18, 0x06, 0x32, 0x0d, 0x5e, 0x5b, 0x30, 0x2d, 0x39, - 0x61, 0x2d, 0x66, 0x5d, 0x7b, 0x36, 0x7d, 0x24, 0x52, 0x05, 0x63, 0x6f, 0x6c, 0x6f, 0x72, 0x22, - 0x9d, 0x04, 0x0a, 0x06, 0x45, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x12, 0x24, 0x0a, 0x04, 0x73, 0x69, - 0x74, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, - 0x2e, 0x76, 0x31, 0x2e, 0x53, 0x69, 0x74, 0x65, 0x48, 0x00, 0x52, 0x04, 0x73, 0x69, 0x74, 0x65, - 0x12, 0x30, 0x0a, 0x08, 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x18, 0x02, 0x20, 0x01, - 0x28, 0x0b, 0x32, 0x12, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x50, 0x6c, - 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x48, 0x00, 0x52, 0x08, 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, - 0x72, 0x6d, 0x12, 0x3c, 0x0a, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, - 0x65, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, - 0x2e, 0x76, 0x31, 0x2e, 0x4d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, - 0x48, 0x00, 0x52, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, - 0x12, 0x2a, 0x0a, 0x06, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, - 0x32, 0x10, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x44, 0x65, 0x76, 0x69, - 0x63, 0x65, 0x48, 0x00, 0x52, 0x06, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x12, 0x31, 0x0a, 0x0b, - 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x5f, 0x72, 0x6f, 0x6c, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, - 0x0b, 0x32, 0x0e, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x52, 0x6f, 0x6c, - 0x65, 0x48, 0x00, 0x52, 0x0a, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x52, 0x6f, 0x6c, 0x65, 0x12, - 0x37, 0x0a, 0x0b, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x06, - 0x20, 0x01, 0x28, 0x0b, 0x32, 0x14, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, - 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x0a, 0x64, 0x65, - 0x76, 0x69, 0x63, 0x65, 0x54, 0x79, 0x70, 0x65, 0x12, 0x33, 0x0a, 0x09, 0x69, 0x6e, 0x74, 0x65, - 0x72, 0x66, 0x61, 0x63, 0x65, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, - 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, - 0x48, 0x00, 0x52, 0x09, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x34, 0x0a, - 0x0a, 0x69, 0x70, 0x5f, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x09, 0x20, 0x01, 0x28, - 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x49, 0x50, 0x41, - 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x48, 0x00, 0x52, 0x09, 0x69, 0x70, 0x41, 0x64, 0x64, 0x72, - 0x65, 0x73, 0x73, 0x12, 0x2a, 0x0a, 0x06, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x18, 0x0a, 0x20, - 0x01, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x50, - 0x72, 0x65, 0x66, 0x69, 0x78, 0x48, 0x00, 0x52, 0x06, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x12, + 0x3a, 0x0a, 0x0c, 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x18, + 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, + 0x2e, 0x4d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x52, 0x0c, 0x6d, + 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x12, 0x2f, 0x0a, 0x0b, 0x64, + 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, + 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x65, + 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, + 0x74, 0x61, 0x67, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, + 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, + 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, + 0x8d, 0x03, 0x0a, 0x06, 0x50, 0x72, 0x65, 0x66, 0x69, 0x78, 0x12, 0x1f, 0x0a, 0x06, 0x70, 0x72, + 0x65, 0x66, 0x69, 0x78, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, + 0x02, 0x70, 0x01, 0x52, 0x06, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x12, 0x22, 0x0a, 0x04, 0x73, + 0x69, 0x74, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x64, 0x69, 0x6f, 0x64, + 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x53, 0x69, 0x74, 0x65, 0x52, 0x04, 0x73, 0x69, 0x74, 0x65, 0x12, + 0x46, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, + 0x2e, 0xfa, 0x42, 0x2b, 0x72, 0x29, 0x52, 0x06, 0x61, 0x63, 0x74, 0x69, 0x76, 0x65, 0x52, 0x09, + 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x08, 0x72, 0x65, 0x73, 0x65, 0x72, + 0x76, 0x65, 0x64, 0x52, 0x0a, 0x64, 0x65, 0x70, 0x72, 0x65, 0x63, 0x61, 0x74, 0x65, 0x64, 0x52, + 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x1c, 0x0a, 0x07, 0x69, 0x73, 0x5f, 0x70, 0x6f, + 0x6f, 0x6c, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x48, 0x00, 0x52, 0x06, 0x69, 0x73, 0x50, 0x6f, + 0x6f, 0x6c, 0x88, 0x01, 0x01, 0x12, 0x28, 0x0a, 0x0d, 0x6d, 0x61, 0x72, 0x6b, 0x5f, 0x75, 0x74, + 0x69, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08, 0x48, 0x01, 0x52, 0x0c, + 0x6d, 0x61, 0x72, 0x6b, 0x55, 0x74, 0x69, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x88, 0x01, 0x01, 0x12, + 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x06, + 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x02, + 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, + 0x12, 0x1f, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x07, 0x20, 0x01, + 0x28, 0x09, 0x48, 0x03, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x88, 0x01, + 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x08, 0x20, 0x03, 0x28, 0x0b, 0x32, + 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, + 0x74, 0x61, 0x67, 0x73, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x69, 0x73, 0x5f, 0x70, 0x6f, 0x6f, 0x6c, + 0x42, 0x10, 0x0a, 0x0e, 0x5f, 0x6d, 0x61, 0x72, 0x6b, 0x5f, 0x75, 0x74, 0x69, 0x6c, 0x69, 0x7a, + 0x65, 0x64, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, + 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x22, + 0xea, 0x01, 0x0a, 0x04, 0x52, 0x6f, 0x6c, 0x65, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, + 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, + 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, + 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, + 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, + 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x2e, 0x0a, 0x05, 0x63, 0x6f, 0x6c, 0x6f, + 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x18, 0xfa, 0x42, 0x15, 0x72, 0x13, 0x10, 0x06, + 0x18, 0x06, 0x32, 0x0d, 0x5e, 0x5b, 0x30, 0x2d, 0x39, 0x61, 0x2d, 0x66, 0x5d, 0x7b, 0x36, 0x7d, + 0x24, 0x52, 0x05, 0x63, 0x6f, 0x6c, 0x6f, 0x72, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, + 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, + 0x42, 0x05, 0x72, 0x03, 0x18, 0xc8, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, + 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, + 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, + 0x76, 0x31, 0x2e, 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0e, 0x0a, 0x0c, + 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xa2, 0x03, 0x0a, + 0x04, 0x53, 0x69, 0x74, 0x65, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, + 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, 0x18, 0x64, 0x52, 0x04, + 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x18, 0x02, 0x20, 0x01, + 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, 0x64, 0x32, 0x10, 0x5e, + 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, 0x5d, 0x2b, 0x24, 0x52, + 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x51, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, + 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x39, 0xfa, 0x42, 0x36, 0x72, 0x34, 0x52, 0x07, 0x70, 0x6c, + 0x61, 0x6e, 0x6e, 0x65, 0x64, 0x52, 0x07, 0x73, 0x74, 0x61, 0x67, 0x69, 0x6e, 0x67, 0x52, 0x06, + 0x61, 0x63, 0x74, 0x69, 0x76, 0x65, 0x52, 0x0f, 0x64, 0x65, 0x63, 0x6f, 0x6d, 0x6d, 0x69, 0x73, + 0x73, 0x69, 0x6f, 0x6e, 0x69, 0x6e, 0x67, 0x52, 0x07, 0x72, 0x65, 0x74, 0x69, 0x72, 0x65, 0x64, + 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x28, 0x0a, 0x08, 0x66, 0x61, 0x63, 0x69, + 0x6c, 0x69, 0x74, 0x79, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, + 0x02, 0x18, 0x32, 0x48, 0x00, 0x52, 0x08, 0x66, 0x61, 0x63, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x88, + 0x01, 0x01, 0x12, 0x20, 0x0a, 0x09, 0x74, 0x69, 0x6d, 0x65, 0x5f, 0x7a, 0x6f, 0x6e, 0x65, 0x18, + 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x08, 0x74, 0x69, 0x6d, 0x65, 0x5a, 0x6f, 0x6e, + 0x65, 0x88, 0x01, 0x01, 0x12, 0x2f, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, + 0x69, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x42, 0x08, 0xfa, 0x42, 0x05, 0x72, 0x03, + 0x18, 0xc8, 0x01, 0x48, 0x02, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, + 0x6f, 0x6e, 0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, + 0x73, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x48, 0x03, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, + 0x6e, 0x74, 0x73, 0x88, 0x01, 0x01, 0x12, 0x21, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18, 0x08, + 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, + 0x54, 0x61, 0x67, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x66, 0x61, + 0x63, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x42, 0x0c, 0x0a, 0x0a, 0x5f, 0x74, 0x69, 0x6d, 0x65, 0x5f, + 0x7a, 0x6f, 0x6e, 0x65, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, + 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x0b, 0x0a, 0x09, 0x5f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, + 0x73, 0x22, 0x85, 0x01, 0x0a, 0x03, 0x54, 0x61, 0x67, 0x12, 0x1d, 0x0a, 0x04, 0x6e, 0x61, 0x6d, + 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x09, 0xfa, 0x42, 0x06, 0x72, 0x04, 0x10, 0x01, + 0x18, 0x64, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x2f, 0x0a, 0x04, 0x73, 0x6c, 0x75, 0x67, + 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x1b, 0xfa, 0x42, 0x18, 0x72, 0x16, 0x10, 0x01, 0x18, + 0x64, 0x32, 0x10, 0x5e, 0x5b, 0x2d, 0x61, 0x2d, 0x7a, 0x41, 0x2d, 0x5a, 0x30, 0x2d, 0x39, 0x5f, + 0x5d, 0x2b, 0x24, 0x52, 0x04, 0x73, 0x6c, 0x75, 0x67, 0x12, 0x2e, 0x0a, 0x05, 0x63, 0x6f, 0x6c, + 0x6f, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x18, 0xfa, 0x42, 0x15, 0x72, 0x13, 0x10, + 0x06, 0x18, 0x06, 0x32, 0x0d, 0x5e, 0x5b, 0x30, 0x2d, 0x39, 0x61, 0x2d, 0x66, 0x5d, 0x7b, 0x36, + 0x7d, 0x24, 0x52, 0x05, 0x63, 0x6f, 0x6c, 0x6f, 0x72, 0x22, 0x83, 0x07, 0x0a, 0x06, 0x45, 0x6e, + 0x74, 0x69, 0x74, 0x79, 0x12, 0x24, 0x0a, 0x04, 0x73, 0x69, 0x74, 0x65, 0x18, 0x01, 0x20, 0x01, + 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x53, 0x69, + 0x74, 0x65, 0x48, 0x00, 0x52, 0x04, 0x73, 0x69, 0x74, 0x65, 0x12, 0x30, 0x0a, 0x08, 0x70, 0x6c, + 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x12, 0x2e, 0x64, + 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x50, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, + 0x48, 0x00, 0x52, 0x08, 0x70, 0x6c, 0x61, 0x74, 0x66, 0x6f, 0x72, 0x6d, 0x12, 0x3c, 0x0a, 0x0c, + 0x6d, 0x61, 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x18, 0x03, 0x20, 0x01, + 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x4d, 0x61, + 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x48, 0x00, 0x52, 0x0c, 0x6d, 0x61, + 0x6e, 0x75, 0x66, 0x61, 0x63, 0x74, 0x75, 0x72, 0x65, 0x72, 0x12, 0x2a, 0x0a, 0x06, 0x64, 0x65, + 0x76, 0x69, 0x63, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x64, 0x69, 0x6f, + 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x48, 0x00, 0x52, 0x06, + 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x12, 0x31, 0x0a, 0x0b, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, + 0x5f, 0x72, 0x6f, 0x6c, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x64, 0x69, + 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x52, 0x6f, 0x6c, 0x65, 0x48, 0x00, 0x52, 0x0a, 0x64, + 0x65, 0x76, 0x69, 0x63, 0x65, 0x52, 0x6f, 0x6c, 0x65, 0x12, 0x37, 0x0a, 0x0b, 0x64, 0x65, 0x76, + 0x69, 0x63, 0x65, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x14, + 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, + 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x0a, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x54, 0x79, + 0x70, 0x65, 0x12, 0x33, 0x0a, 0x09, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x18, + 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, + 0x2e, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x48, 0x00, 0x52, 0x09, 0x69, 0x6e, + 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x34, 0x0a, 0x0a, 0x69, 0x70, 0x5f, 0x61, 0x64, + 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x09, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x64, 0x69, + 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x49, 0x50, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, + 0x48, 0x00, 0x52, 0x09, 0x69, 0x70, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x12, 0x2a, 0x0a, + 0x06, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x18, 0x0a, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x10, 0x2e, + 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x50, 0x72, 0x65, 0x66, 0x69, 0x78, 0x48, + 0x00, 0x52, 0x06, 0x70, 0x72, 0x65, 0x66, 0x69, 0x78, 0x12, 0x3d, 0x0a, 0x0d, 0x63, 0x6c, 0x75, + 0x73, 0x74, 0x65, 0x72, 0x5f, 0x67, 0x72, 0x6f, 0x75, 0x70, 0x18, 0x0b, 0x20, 0x01, 0x28, 0x0b, + 0x32, 0x16, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x43, 0x6c, 0x75, 0x73, + 0x74, 0x65, 0x72, 0x47, 0x72, 0x6f, 0x75, 0x70, 0x48, 0x00, 0x52, 0x0c, 0x63, 0x6c, 0x75, 0x73, + 0x74, 0x65, 0x72, 0x47, 0x72, 0x6f, 0x75, 0x70, 0x12, 0x3a, 0x0a, 0x0c, 0x63, 0x6c, 0x75, 0x73, + 0x74, 0x65, 0x72, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x0c, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x15, + 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, + 0x72, 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x0b, 0x63, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, + 0x54, 0x79, 0x70, 0x65, 0x12, 0x2d, 0x0a, 0x07, 0x63, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x18, + 0x0d, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x11, 0x2e, 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, + 0x2e, 0x43, 0x6c, 0x75, 0x73, 0x74, 0x65, 0x72, 0x48, 0x00, 0x52, 0x07, 0x63, 0x6c, 0x75, 0x73, + 0x74, 0x65, 0x72, 0x12, 0x43, 0x0a, 0x0f, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x5f, 0x6d, + 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x18, 0x0e, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x18, 0x2e, 0x64, + 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x56, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x4d, + 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x48, 0x00, 0x52, 0x0e, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, + 0x6c, 0x4d, 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, 0x12, 0x39, 0x0a, 0x0b, 0x76, 0x6d, 0x69, 0x6e, + 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x18, 0x0f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x15, 0x2e, + 0x64, 0x69, 0x6f, 0x64, 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x56, 0x4d, 0x49, 0x6e, 0x74, 0x65, 0x72, + 0x66, 0x61, 0x63, 0x65, 0x48, 0x00, 0x52, 0x0b, 0x76, 0x6d, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, + 0x61, 0x63, 0x65, 0x12, 0x3a, 0x0a, 0x0c, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x5f, 0x64, + 0x69, 0x73, 0x6b, 0x18, 0x10, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x15, 0x2e, 0x64, 0x69, 0x6f, 0x64, + 0x65, 0x2e, 0x76, 0x31, 0x2e, 0x56, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x44, 0x69, 0x73, 0x6b, + 0x48, 0x00, 0x52, 0x0b, 0x76, 0x69, 0x72, 0x74, 0x75, 0x61, 0x6c, 0x44, 0x69, 0x73, 0x6b, 0x12, 0x44, 0x0a, 0x09, 0x74, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x18, 0x08, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x54, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x42, 0x0a, @@ -1823,62 +2637,92 @@ func file_diode_v1_ingester_proto_rawDescGZIP() []byte { return file_diode_v1_ingester_proto_rawDescData } -var file_diode_v1_ingester_proto_msgTypes = make([]protoimpl.MessageInfo, 13) +var file_diode_v1_ingester_proto_msgTypes = make([]protoimpl.MessageInfo, 19) var file_diode_v1_ingester_proto_goTypes = []interface{}{ (*Device)(nil), // 0: diode.v1.Device (*Interface)(nil), // 1: diode.v1.Interface - (*IPAddress)(nil), // 2: diode.v1.IPAddress - (*DeviceType)(nil), // 3: diode.v1.DeviceType - (*Manufacturer)(nil), // 4: diode.v1.Manufacturer - (*Platform)(nil), // 5: diode.v1.Platform - (*Prefix)(nil), // 6: diode.v1.Prefix - (*Role)(nil), // 7: diode.v1.Role - (*Site)(nil), // 8: diode.v1.Site - (*Tag)(nil), // 9: diode.v1.Tag - (*Entity)(nil), // 10: diode.v1.Entity - (*IngestRequest)(nil), // 11: diode.v1.IngestRequest - (*IngestResponse)(nil), // 12: diode.v1.IngestResponse - (*timestamppb.Timestamp)(nil), // 13: google.protobuf.Timestamp + (*Cluster)(nil), // 2: diode.v1.Cluster + (*ClusterType)(nil), // 3: diode.v1.ClusterType + (*ClusterGroup)(nil), // 4: diode.v1.ClusterGroup + (*VirtualMachine)(nil), // 5: diode.v1.VirtualMachine + (*VMInterface)(nil), // 6: diode.v1.VMInterface + (*VirtualDisk)(nil), // 7: diode.v1.VirtualDisk + (*IPAddress)(nil), // 8: diode.v1.IPAddress + (*DeviceType)(nil), // 9: diode.v1.DeviceType + (*Manufacturer)(nil), // 10: diode.v1.Manufacturer + (*Platform)(nil), // 11: diode.v1.Platform + (*Prefix)(nil), // 12: diode.v1.Prefix + (*Role)(nil), // 13: diode.v1.Role + (*Site)(nil), // 14: diode.v1.Site + (*Tag)(nil), // 15: diode.v1.Tag + (*Entity)(nil), // 16: diode.v1.Entity + (*IngestRequest)(nil), // 17: diode.v1.IngestRequest + (*IngestResponse)(nil), // 18: diode.v1.IngestResponse + (*timestamppb.Timestamp)(nil), // 19: google.protobuf.Timestamp } var file_diode_v1_ingester_proto_depIdxs = []int32{ - 3, // 0: diode.v1.Device.device_type:type_name -> diode.v1.DeviceType - 7, // 1: diode.v1.Device.role:type_name -> diode.v1.Role - 5, // 2: diode.v1.Device.platform:type_name -> diode.v1.Platform - 8, // 3: diode.v1.Device.site:type_name -> diode.v1.Site - 9, // 4: diode.v1.Device.tags:type_name -> diode.v1.Tag - 2, // 5: diode.v1.Device.primary_ip4:type_name -> diode.v1.IPAddress - 2, // 6: diode.v1.Device.primary_ip6:type_name -> diode.v1.IPAddress + 9, // 0: diode.v1.Device.device_type:type_name -> diode.v1.DeviceType + 13, // 1: diode.v1.Device.role:type_name -> diode.v1.Role + 11, // 2: diode.v1.Device.platform:type_name -> diode.v1.Platform + 14, // 3: diode.v1.Device.site:type_name -> diode.v1.Site + 15, // 4: diode.v1.Device.tags:type_name -> diode.v1.Tag + 8, // 5: diode.v1.Device.primary_ip4:type_name -> diode.v1.IPAddress + 8, // 6: diode.v1.Device.primary_ip6:type_name -> diode.v1.IPAddress 0, // 7: diode.v1.Interface.device:type_name -> diode.v1.Device - 9, // 8: diode.v1.Interface.tags:type_name -> diode.v1.Tag - 1, // 9: diode.v1.IPAddress.interface:type_name -> diode.v1.Interface - 9, // 10: diode.v1.IPAddress.tags:type_name -> diode.v1.Tag - 4, // 11: diode.v1.DeviceType.manufacturer:type_name -> diode.v1.Manufacturer - 9, // 12: diode.v1.DeviceType.tags:type_name -> diode.v1.Tag - 9, // 13: diode.v1.Manufacturer.tags:type_name -> diode.v1.Tag - 4, // 14: diode.v1.Platform.manufacturer:type_name -> diode.v1.Manufacturer - 9, // 15: diode.v1.Platform.tags:type_name -> diode.v1.Tag - 8, // 16: diode.v1.Prefix.site:type_name -> diode.v1.Site - 9, // 17: diode.v1.Prefix.tags:type_name -> diode.v1.Tag - 9, // 18: diode.v1.Role.tags:type_name -> diode.v1.Tag - 9, // 19: diode.v1.Site.tags:type_name -> diode.v1.Tag - 8, // 20: diode.v1.Entity.site:type_name -> diode.v1.Site - 5, // 21: diode.v1.Entity.platform:type_name -> diode.v1.Platform - 4, // 22: diode.v1.Entity.manufacturer:type_name -> diode.v1.Manufacturer - 0, // 23: diode.v1.Entity.device:type_name -> diode.v1.Device - 7, // 24: diode.v1.Entity.device_role:type_name -> diode.v1.Role - 3, // 25: diode.v1.Entity.device_type:type_name -> diode.v1.DeviceType - 1, // 26: diode.v1.Entity.interface:type_name -> diode.v1.Interface - 2, // 27: diode.v1.Entity.ip_address:type_name -> diode.v1.IPAddress - 6, // 28: diode.v1.Entity.prefix:type_name -> diode.v1.Prefix - 13, // 29: diode.v1.Entity.timestamp:type_name -> google.protobuf.Timestamp - 10, // 30: diode.v1.IngestRequest.entities:type_name -> diode.v1.Entity - 11, // 31: diode.v1.IngesterService.Ingest:input_type -> diode.v1.IngestRequest - 12, // 32: diode.v1.IngesterService.Ingest:output_type -> diode.v1.IngestResponse - 32, // [32:33] is the sub-list for method output_type - 31, // [31:32] is the sub-list for method input_type - 31, // [31:31] is the sub-list for extension type_name - 31, // [31:31] is the sub-list for extension extendee - 0, // [0:31] is the sub-list for field type_name + 15, // 8: diode.v1.Interface.tags:type_name -> diode.v1.Tag + 3, // 9: diode.v1.Cluster.type:type_name -> diode.v1.ClusterType + 4, // 10: diode.v1.Cluster.group:type_name -> diode.v1.ClusterGroup + 14, // 11: diode.v1.Cluster.site:type_name -> diode.v1.Site + 15, // 12: diode.v1.Cluster.tags:type_name -> diode.v1.Tag + 15, // 13: diode.v1.ClusterType.tags:type_name -> diode.v1.Tag + 15, // 14: diode.v1.ClusterGroup.tags:type_name -> diode.v1.Tag + 14, // 15: diode.v1.VirtualMachine.site:type_name -> diode.v1.Site + 2, // 16: diode.v1.VirtualMachine.cluster:type_name -> diode.v1.Cluster + 13, // 17: diode.v1.VirtualMachine.role:type_name -> diode.v1.Role + 0, // 18: diode.v1.VirtualMachine.device:type_name -> diode.v1.Device + 11, // 19: diode.v1.VirtualMachine.platform:type_name -> diode.v1.Platform + 8, // 20: diode.v1.VirtualMachine.primary_ip4:type_name -> diode.v1.IPAddress + 8, // 21: diode.v1.VirtualMachine.primary_ip6:type_name -> diode.v1.IPAddress + 15, // 22: diode.v1.VirtualMachine.tags:type_name -> diode.v1.Tag + 5, // 23: diode.v1.VMInterface.virtual_machine:type_name -> diode.v1.VirtualMachine + 15, // 24: diode.v1.VMInterface.tags:type_name -> diode.v1.Tag + 5, // 25: diode.v1.VirtualDisk.virtual_machine:type_name -> diode.v1.VirtualMachine + 15, // 26: diode.v1.VirtualDisk.tags:type_name -> diode.v1.Tag + 1, // 27: diode.v1.IPAddress.interface:type_name -> diode.v1.Interface + 15, // 28: diode.v1.IPAddress.tags:type_name -> diode.v1.Tag + 10, // 29: diode.v1.DeviceType.manufacturer:type_name -> diode.v1.Manufacturer + 15, // 30: diode.v1.DeviceType.tags:type_name -> diode.v1.Tag + 15, // 31: diode.v1.Manufacturer.tags:type_name -> diode.v1.Tag + 10, // 32: diode.v1.Platform.manufacturer:type_name -> diode.v1.Manufacturer + 15, // 33: diode.v1.Platform.tags:type_name -> diode.v1.Tag + 14, // 34: diode.v1.Prefix.site:type_name -> diode.v1.Site + 15, // 35: diode.v1.Prefix.tags:type_name -> diode.v1.Tag + 15, // 36: diode.v1.Role.tags:type_name -> diode.v1.Tag + 15, // 37: diode.v1.Site.tags:type_name -> diode.v1.Tag + 14, // 38: diode.v1.Entity.site:type_name -> diode.v1.Site + 11, // 39: diode.v1.Entity.platform:type_name -> diode.v1.Platform + 10, // 40: diode.v1.Entity.manufacturer:type_name -> diode.v1.Manufacturer + 0, // 41: diode.v1.Entity.device:type_name -> diode.v1.Device + 13, // 42: diode.v1.Entity.device_role:type_name -> diode.v1.Role + 9, // 43: diode.v1.Entity.device_type:type_name -> diode.v1.DeviceType + 1, // 44: diode.v1.Entity.interface:type_name -> diode.v1.Interface + 8, // 45: diode.v1.Entity.ip_address:type_name -> diode.v1.IPAddress + 12, // 46: diode.v1.Entity.prefix:type_name -> diode.v1.Prefix + 4, // 47: diode.v1.Entity.cluster_group:type_name -> diode.v1.ClusterGroup + 3, // 48: diode.v1.Entity.cluster_type:type_name -> diode.v1.ClusterType + 2, // 49: diode.v1.Entity.cluster:type_name -> diode.v1.Cluster + 5, // 50: diode.v1.Entity.virtual_machine:type_name -> diode.v1.VirtualMachine + 6, // 51: diode.v1.Entity.vminterface:type_name -> diode.v1.VMInterface + 7, // 52: diode.v1.Entity.virtual_disk:type_name -> diode.v1.VirtualDisk + 19, // 53: diode.v1.Entity.timestamp:type_name -> google.protobuf.Timestamp + 16, // 54: diode.v1.IngestRequest.entities:type_name -> diode.v1.Entity + 17, // 55: diode.v1.IngesterService.Ingest:input_type -> diode.v1.IngestRequest + 18, // 56: diode.v1.IngesterService.Ingest:output_type -> diode.v1.IngestResponse + 56, // [56:57] is the sub-list for method output_type + 55, // [55:56] is the sub-list for method input_type + 55, // [55:55] is the sub-list for extension type_name + 55, // [55:55] is the sub-list for extension extendee + 0, // [0:55] is the sub-list for field type_name } func init() { file_diode_v1_ingester_proto_init() } @@ -1912,7 +2756,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*IPAddress); i { + switch v := v.(*Cluster); i { case 0: return &v.state case 1: @@ -1924,7 +2768,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*DeviceType); i { + switch v := v.(*ClusterType); i { case 0: return &v.state case 1: @@ -1936,7 +2780,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*Manufacturer); i { + switch v := v.(*ClusterGroup); i { case 0: return &v.state case 1: @@ -1948,7 +2792,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*Platform); i { + switch v := v.(*VirtualMachine); i { case 0: return &v.state case 1: @@ -1960,7 +2804,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*Prefix); i { + switch v := v.(*VMInterface); i { case 0: return &v.state case 1: @@ -1972,7 +2816,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*Role); i { + switch v := v.(*VirtualDisk); i { case 0: return &v.state case 1: @@ -1984,7 +2828,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*Site); i { + switch v := v.(*IPAddress); i { case 0: return &v.state case 1: @@ -1996,7 +2840,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*Tag); i { + switch v := v.(*DeviceType); i { case 0: return &v.state case 1: @@ -2008,7 +2852,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[10].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*Entity); i { + switch v := v.(*Manufacturer); i { case 0: return &v.state case 1: @@ -2020,7 +2864,7 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[11].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*IngestRequest); i { + switch v := v.(*Platform); i { case 0: return &v.state case 1: @@ -2032,6 +2876,78 @@ func file_diode_v1_ingester_proto_init() { } } file_diode_v1_ingester_proto_msgTypes[12].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*Prefix); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_diode_v1_ingester_proto_msgTypes[13].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*Role); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_diode_v1_ingester_proto_msgTypes[14].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*Site); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_diode_v1_ingester_proto_msgTypes[15].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*Tag); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_diode_v1_ingester_proto_msgTypes[16].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*Entity); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_diode_v1_ingester_proto_msgTypes[17].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*IngestRequest); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_diode_v1_ingester_proto_msgTypes[18].Exporter = func(v interface{}, i int) interface{} { switch v := v.(*IngestResponse); i { case 0: return &v.state @@ -2046,16 +2962,22 @@ func file_diode_v1_ingester_proto_init() { } file_diode_v1_ingester_proto_msgTypes[0].OneofWrappers = []interface{}{} file_diode_v1_ingester_proto_msgTypes[1].OneofWrappers = []interface{}{} - file_diode_v1_ingester_proto_msgTypes[2].OneofWrappers = []interface{}{ - (*IPAddress_Interface)(nil), - } + file_diode_v1_ingester_proto_msgTypes[2].OneofWrappers = []interface{}{} file_diode_v1_ingester_proto_msgTypes[3].OneofWrappers = []interface{}{} file_diode_v1_ingester_proto_msgTypes[4].OneofWrappers = []interface{}{} file_diode_v1_ingester_proto_msgTypes[5].OneofWrappers = []interface{}{} file_diode_v1_ingester_proto_msgTypes[6].OneofWrappers = []interface{}{} file_diode_v1_ingester_proto_msgTypes[7].OneofWrappers = []interface{}{} - file_diode_v1_ingester_proto_msgTypes[8].OneofWrappers = []interface{}{} - file_diode_v1_ingester_proto_msgTypes[10].OneofWrappers = []interface{}{ + file_diode_v1_ingester_proto_msgTypes[8].OneofWrappers = []interface{}{ + (*IPAddress_Interface)(nil), + } + file_diode_v1_ingester_proto_msgTypes[9].OneofWrappers = []interface{}{} + file_diode_v1_ingester_proto_msgTypes[10].OneofWrappers = []interface{}{} + file_diode_v1_ingester_proto_msgTypes[11].OneofWrappers = []interface{}{} + file_diode_v1_ingester_proto_msgTypes[12].OneofWrappers = []interface{}{} + file_diode_v1_ingester_proto_msgTypes[13].OneofWrappers = []interface{}{} + file_diode_v1_ingester_proto_msgTypes[14].OneofWrappers = []interface{}{} + file_diode_v1_ingester_proto_msgTypes[16].OneofWrappers = []interface{}{ (*Entity_Site)(nil), (*Entity_Platform)(nil), (*Entity_Manufacturer)(nil), @@ -2065,6 +2987,12 @@ func file_diode_v1_ingester_proto_init() { (*Entity_Interface)(nil), (*Entity_IpAddress)(nil), (*Entity_Prefix)(nil), + (*Entity_ClusterGroup)(nil), + (*Entity_ClusterType)(nil), + (*Entity_Cluster)(nil), + (*Entity_VirtualMachine)(nil), + (*Entity_Vminterface)(nil), + (*Entity_VirtualDisk)(nil), } type x struct{} out := protoimpl.TypeBuilder{ @@ -2072,7 +3000,7 @@ func file_diode_v1_ingester_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: file_diode_v1_ingester_proto_rawDesc, NumEnums: 0, - NumMessages: 13, + NumMessages: 19, NumExtensions: 0, NumServices: 1, }, diff --git a/diode/v1/diodepb/ingester.pb.validate.go b/diode/v1/diodepb/ingester.pb.validate.go index 5db634b..102869a 100644 --- a/diode/v1/diodepb/ingester.pb.validate.go +++ b/diode/v1/diodepb/ingester.pb.validate.go @@ -825,6 +825,1451 @@ var _Interface_Mode_InLookup = map[string]struct{}{ "tagged-all": {}, } +// Validate checks the field values on Cluster with the rules defined in the +// proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *Cluster) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on Cluster with the rules defined in the +// proto definition for this message. If any rules are violated, the result is +// a list of violation errors wrapped in ClusterMultiError, or nil if none found. +func (m *Cluster) ValidateAll() error { + return m.validate(true) +} + +func (m *Cluster) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + if l := utf8.RuneCountInString(m.GetName()); l < 1 || l > 100 { + err := ClusterValidationError{ + field: "Name", + reason: "value length must be between 1 and 100 runes, inclusive", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetType()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, ClusterValidationError{ + field: "Type", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, ClusterValidationError{ + field: "Type", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetType()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return ClusterValidationError{ + field: "Type", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetGroup()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, ClusterValidationError{ + field: "Group", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, ClusterValidationError{ + field: "Group", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetGroup()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return ClusterValidationError{ + field: "Group", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetSite()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, ClusterValidationError{ + field: "Site", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, ClusterValidationError{ + field: "Site", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetSite()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return ClusterValidationError{ + field: "Site", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if _, ok := _Cluster_Status_InLookup[m.GetStatus()]; !ok { + err := ClusterValidationError{ + field: "Status", + reason: "value must be in list [offline active planned staged failed decommissioning]", + } + if !all { + return err + } + errors = append(errors, err) + } + + for idx, item := range m.GetTags() { + _, _ = idx, item + + if all { + switch v := interface{}(item).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, ClusterValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, ClusterValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(item).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return ClusterValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + } + } + } + + } + + if m.Description != nil { + + if utf8.RuneCountInString(m.GetDescription()) > 200 { + err := ClusterValidationError{ + field: "Description", + reason: "value length must be at most 200 runes", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if len(errors) > 0 { + return ClusterMultiError(errors) + } + + return nil +} + +// ClusterMultiError is an error wrapping multiple validation errors returned +// by Cluster.ValidateAll() if the designated constraints aren't met. +type ClusterMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m ClusterMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m ClusterMultiError) AllErrors() []error { return m } + +// ClusterValidationError is the validation error returned by Cluster.Validate +// if the designated constraints aren't met. +type ClusterValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e ClusterValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e ClusterValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e ClusterValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e ClusterValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e ClusterValidationError) ErrorName() string { return "ClusterValidationError" } + +// Error satisfies the builtin error interface +func (e ClusterValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sCluster.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = ClusterValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = ClusterValidationError{} + +var _Cluster_Status_InLookup = map[string]struct{}{ + "offline": {}, + "active": {}, + "planned": {}, + "staged": {}, + "failed": {}, + "decommissioning": {}, +} + +// Validate checks the field values on ClusterType with the rules defined in +// the proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *ClusterType) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on ClusterType with the rules defined in +// the proto definition for this message. If any rules are violated, the +// result is a list of violation errors wrapped in ClusterTypeMultiError, or +// nil if none found. +func (m *ClusterType) ValidateAll() error { + return m.validate(true) +} + +func (m *ClusterType) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + if l := utf8.RuneCountInString(m.GetName()); l < 1 || l > 100 { + err := ClusterTypeValidationError{ + field: "Name", + reason: "value length must be between 1 and 100 runes, inclusive", + } + if !all { + return err + } + errors = append(errors, err) + } + + if l := utf8.RuneCountInString(m.GetSlug()); l < 1 || l > 100 { + err := ClusterTypeValidationError{ + field: "Slug", + reason: "value length must be between 1 and 100 runes, inclusive", + } + if !all { + return err + } + errors = append(errors, err) + } + + if !_ClusterType_Slug_Pattern.MatchString(m.GetSlug()) { + err := ClusterTypeValidationError{ + field: "Slug", + reason: "value does not match regex pattern \"^[-a-zA-Z0-9_]+$\"", + } + if !all { + return err + } + errors = append(errors, err) + } + + for idx, item := range m.GetTags() { + _, _ = idx, item + + if all { + switch v := interface{}(item).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, ClusterTypeValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, ClusterTypeValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(item).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return ClusterTypeValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + } + } + } + + } + + if m.Description != nil { + + if utf8.RuneCountInString(m.GetDescription()) > 200 { + err := ClusterTypeValidationError{ + field: "Description", + reason: "value length must be at most 200 runes", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if len(errors) > 0 { + return ClusterTypeMultiError(errors) + } + + return nil +} + +// ClusterTypeMultiError is an error wrapping multiple validation errors +// returned by ClusterType.ValidateAll() if the designated constraints aren't met. +type ClusterTypeMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m ClusterTypeMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m ClusterTypeMultiError) AllErrors() []error { return m } + +// ClusterTypeValidationError is the validation error returned by +// ClusterType.Validate if the designated constraints aren't met. +type ClusterTypeValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e ClusterTypeValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e ClusterTypeValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e ClusterTypeValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e ClusterTypeValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e ClusterTypeValidationError) ErrorName() string { return "ClusterTypeValidationError" } + +// Error satisfies the builtin error interface +func (e ClusterTypeValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sClusterType.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = ClusterTypeValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = ClusterTypeValidationError{} + +var _ClusterType_Slug_Pattern = regexp.MustCompile("^[-a-zA-Z0-9_]+$") + +// Validate checks the field values on ClusterGroup with the rules defined in +// the proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *ClusterGroup) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on ClusterGroup with the rules defined +// in the proto definition for this message. If any rules are violated, the +// result is a list of violation errors wrapped in ClusterGroupMultiError, or +// nil if none found. +func (m *ClusterGroup) ValidateAll() error { + return m.validate(true) +} + +func (m *ClusterGroup) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + if l := utf8.RuneCountInString(m.GetName()); l < 1 || l > 100 { + err := ClusterGroupValidationError{ + field: "Name", + reason: "value length must be between 1 and 100 runes, inclusive", + } + if !all { + return err + } + errors = append(errors, err) + } + + if l := utf8.RuneCountInString(m.GetSlug()); l < 1 || l > 100 { + err := ClusterGroupValidationError{ + field: "Slug", + reason: "value length must be between 1 and 100 runes, inclusive", + } + if !all { + return err + } + errors = append(errors, err) + } + + if !_ClusterGroup_Slug_Pattern.MatchString(m.GetSlug()) { + err := ClusterGroupValidationError{ + field: "Slug", + reason: "value does not match regex pattern \"^[-a-zA-Z0-9_]+$\"", + } + if !all { + return err + } + errors = append(errors, err) + } + + for idx, item := range m.GetTags() { + _, _ = idx, item + + if all { + switch v := interface{}(item).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, ClusterGroupValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, ClusterGroupValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(item).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return ClusterGroupValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + } + } + } + + } + + if m.Description != nil { + + if utf8.RuneCountInString(m.GetDescription()) > 200 { + err := ClusterGroupValidationError{ + field: "Description", + reason: "value length must be at most 200 runes", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if len(errors) > 0 { + return ClusterGroupMultiError(errors) + } + + return nil +} + +// ClusterGroupMultiError is an error wrapping multiple validation errors +// returned by ClusterGroup.ValidateAll() if the designated constraints aren't met. +type ClusterGroupMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m ClusterGroupMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m ClusterGroupMultiError) AllErrors() []error { return m } + +// ClusterGroupValidationError is the validation error returned by +// ClusterGroup.Validate if the designated constraints aren't met. +type ClusterGroupValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e ClusterGroupValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e ClusterGroupValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e ClusterGroupValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e ClusterGroupValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e ClusterGroupValidationError) ErrorName() string { return "ClusterGroupValidationError" } + +// Error satisfies the builtin error interface +func (e ClusterGroupValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sClusterGroup.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = ClusterGroupValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = ClusterGroupValidationError{} + +var _ClusterGroup_Slug_Pattern = regexp.MustCompile("^[-a-zA-Z0-9_]+$") + +// Validate checks the field values on VirtualMachine with the rules defined in +// the proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *VirtualMachine) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on VirtualMachine with the rules defined +// in the proto definition for this message. If any rules are violated, the +// result is a list of violation errors wrapped in VirtualMachineMultiError, +// or nil if none found. +func (m *VirtualMachine) ValidateAll() error { + return m.validate(true) +} + +func (m *VirtualMachine) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + if utf8.RuneCountInString(m.GetName()) > 64 { + err := VirtualMachineValidationError{ + field: "Name", + reason: "value length must be at most 64 runes", + } + if !all { + return err + } + errors = append(errors, err) + } + + if _, ok := _VirtualMachine_Status_InLookup[m.GetStatus()]; !ok { + err := VirtualMachineValidationError{ + field: "Status", + reason: "value must be in list [offline active planned staged failed decommissioning]", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetSite()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Site", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Site", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetSite()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: "Site", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetCluster()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Cluster", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Cluster", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetCluster()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: "Cluster", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetRole()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Role", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Role", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetRole()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: "Role", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetDevice()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Device", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Device", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetDevice()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: "Device", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetPlatform()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Platform", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "Platform", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetPlatform()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: "Platform", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetPrimaryIp4()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "PrimaryIp4", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "PrimaryIp4", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetPrimaryIp4()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: "PrimaryIp4", + reason: "embedded message failed validation", + cause: err, + } + } + } + + if all { + switch v := interface{}(m.GetPrimaryIp6()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "PrimaryIp6", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: "PrimaryIp6", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetPrimaryIp6()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: "PrimaryIp6", + reason: "embedded message failed validation", + cause: err, + } + } + } + + for idx, item := range m.GetTags() { + _, _ = idx, item + + if all { + switch v := interface{}(item).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualMachineValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(item).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualMachineValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + } + } + } + + } + + if m.Vcpus != nil { + + if m.GetVcpus() < 0 { + err := VirtualMachineValidationError{ + field: "Vcpus", + reason: "value must be greater than or equal to 0", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if m.Memory != nil { + + if m.GetMemory() < 0 { + err := VirtualMachineValidationError{ + field: "Memory", + reason: "value must be greater than or equal to 0", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if m.Disk != nil { + + if m.GetDisk() < 0 { + err := VirtualMachineValidationError{ + field: "Disk", + reason: "value must be greater than or equal to 0", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if m.Description != nil { + + if utf8.RuneCountInString(m.GetDescription()) > 200 { + err := VirtualMachineValidationError{ + field: "Description", + reason: "value length must be at most 200 runes", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if m.Comments != nil { + // no validation rules for Comments + } + + if len(errors) > 0 { + return VirtualMachineMultiError(errors) + } + + return nil +} + +// VirtualMachineMultiError is an error wrapping multiple validation errors +// returned by VirtualMachine.ValidateAll() if the designated constraints +// aren't met. +type VirtualMachineMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m VirtualMachineMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m VirtualMachineMultiError) AllErrors() []error { return m } + +// VirtualMachineValidationError is the validation error returned by +// VirtualMachine.Validate if the designated constraints aren't met. +type VirtualMachineValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e VirtualMachineValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e VirtualMachineValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e VirtualMachineValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e VirtualMachineValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e VirtualMachineValidationError) ErrorName() string { return "VirtualMachineValidationError" } + +// Error satisfies the builtin error interface +func (e VirtualMachineValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sVirtualMachine.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = VirtualMachineValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = VirtualMachineValidationError{} + +var _VirtualMachine_Status_InLookup = map[string]struct{}{ + "offline": {}, + "active": {}, + "planned": {}, + "staged": {}, + "failed": {}, + "decommissioning": {}, +} + +// Validate checks the field values on VMInterface with the rules defined in +// the proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *VMInterface) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on VMInterface with the rules defined in +// the proto definition for this message. If any rules are violated, the +// result is a list of violation errors wrapped in VMInterfaceMultiError, or +// nil if none found. +func (m *VMInterface) ValidateAll() error { + return m.validate(true) +} + +func (m *VMInterface) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + if m.GetVirtualMachine() == nil { + err := VMInterfaceValidationError{ + field: "VirtualMachine", + reason: "value is required", + } + if !all { + return err + } + errors = append(errors, err) + } + + if a := m.GetVirtualMachine(); a != nil { + + } + + if l := utf8.RuneCountInString(m.GetName()); l < 1 || l > 64 { + err := VMInterfaceValidationError{ + field: "Name", + reason: "value length must be between 1 and 64 runes, inclusive", + } + if !all { + return err + } + errors = append(errors, err) + } + + for idx, item := range m.GetTags() { + _, _ = idx, item + + if all { + switch v := interface{}(item).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VMInterfaceValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VMInterfaceValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(item).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VMInterfaceValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + } + } + } + + } + + if m.Enabled != nil { + // no validation rules for Enabled + } + + if m.Mtu != nil { + + if val := m.GetMtu(); val < 1 || val > 65536 { + err := VMInterfaceValidationError{ + field: "Mtu", + reason: "value must be inside range [1, 65536]", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if m.MacAddress != nil { + // no validation rules for MacAddress + } + + if m.Description != nil { + + if utf8.RuneCountInString(m.GetDescription()) > 200 { + err := VMInterfaceValidationError{ + field: "Description", + reason: "value length must be at most 200 runes", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if len(errors) > 0 { + return VMInterfaceMultiError(errors) + } + + return nil +} + +// VMInterfaceMultiError is an error wrapping multiple validation errors +// returned by VMInterface.ValidateAll() if the designated constraints aren't met. +type VMInterfaceMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m VMInterfaceMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m VMInterfaceMultiError) AllErrors() []error { return m } + +// VMInterfaceValidationError is the validation error returned by +// VMInterface.Validate if the designated constraints aren't met. +type VMInterfaceValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e VMInterfaceValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e VMInterfaceValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e VMInterfaceValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e VMInterfaceValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e VMInterfaceValidationError) ErrorName() string { return "VMInterfaceValidationError" } + +// Error satisfies the builtin error interface +func (e VMInterfaceValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sVMInterface.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = VMInterfaceValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = VMInterfaceValidationError{} + +// Validate checks the field values on VirtualDisk with the rules defined in +// the proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *VirtualDisk) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on VirtualDisk with the rules defined in +// the proto definition for this message. If any rules are violated, the +// result is a list of violation errors wrapped in VirtualDiskMultiError, or +// nil if none found. +func (m *VirtualDisk) ValidateAll() error { + return m.validate(true) +} + +func (m *VirtualDisk) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + if m.GetVirtualMachine() == nil { + err := VirtualDiskValidationError{ + field: "VirtualMachine", + reason: "value is required", + } + if !all { + return err + } + errors = append(errors, err) + } + + if a := m.GetVirtualMachine(); a != nil { + + } + + if l := utf8.RuneCountInString(m.GetName()); l < 1 || l > 100 { + err := VirtualDiskValidationError{ + field: "Name", + reason: "value length must be between 1 and 100 runes, inclusive", + } + if !all { + return err + } + errors = append(errors, err) + } + + if m.GetSize() < 0 { + err := VirtualDiskValidationError{ + field: "Size", + reason: "value must be greater than or equal to 0", + } + if !all { + return err + } + errors = append(errors, err) + } + + for idx, item := range m.GetTags() { + _, _ = idx, item + + if all { + switch v := interface{}(item).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, VirtualDiskValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, VirtualDiskValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(item).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return VirtualDiskValidationError{ + field: fmt.Sprintf("Tags[%v]", idx), + reason: "embedded message failed validation", + cause: err, + } + } + } + + } + + if m.Description != nil { + + if utf8.RuneCountInString(m.GetDescription()) > 200 { + err := VirtualDiskValidationError{ + field: "Description", + reason: "value length must be at most 200 runes", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if len(errors) > 0 { + return VirtualDiskMultiError(errors) + } + + return nil +} + +// VirtualDiskMultiError is an error wrapping multiple validation errors +// returned by VirtualDisk.ValidateAll() if the designated constraints aren't met. +type VirtualDiskMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m VirtualDiskMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m VirtualDiskMultiError) AllErrors() []error { return m } + +// VirtualDiskValidationError is the validation error returned by +// VirtualDisk.Validate if the designated constraints aren't met. +type VirtualDiskValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e VirtualDiskValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e VirtualDiskValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e VirtualDiskValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e VirtualDiskValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e VirtualDiskValidationError) ErrorName() string { return "VirtualDiskValidationError" } + +// Error satisfies the builtin error interface +func (e VirtualDiskValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sVirtualDisk.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = VirtualDiskValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = VirtualDiskValidationError{} + // Validate checks the field values on IPAddress with the rules defined in the // proto definition for this message. If any rules are violated, the first // error encountered is returned, or nil if there are no violations. @@ -2967,6 +4412,252 @@ func (m *Entity) validate(all bool) error { } } + case *Entity_ClusterGroup: + if v == nil { + err := EntityValidationError{ + field: "Entity", + reason: "oneof value cannot be a typed-nil", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetClusterGroup()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, EntityValidationError{ + field: "ClusterGroup", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, EntityValidationError{ + field: "ClusterGroup", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetClusterGroup()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return EntityValidationError{ + field: "ClusterGroup", + reason: "embedded message failed validation", + cause: err, + } + } + } + + case *Entity_ClusterType: + if v == nil { + err := EntityValidationError{ + field: "Entity", + reason: "oneof value cannot be a typed-nil", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetClusterType()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, EntityValidationError{ + field: "ClusterType", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, EntityValidationError{ + field: "ClusterType", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetClusterType()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return EntityValidationError{ + field: "ClusterType", + reason: "embedded message failed validation", + cause: err, + } + } + } + + case *Entity_Cluster: + if v == nil { + err := EntityValidationError{ + field: "Entity", + reason: "oneof value cannot be a typed-nil", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetCluster()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, EntityValidationError{ + field: "Cluster", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, EntityValidationError{ + field: "Cluster", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetCluster()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return EntityValidationError{ + field: "Cluster", + reason: "embedded message failed validation", + cause: err, + } + } + } + + case *Entity_VirtualMachine: + if v == nil { + err := EntityValidationError{ + field: "Entity", + reason: "oneof value cannot be a typed-nil", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetVirtualMachine()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, EntityValidationError{ + field: "VirtualMachine", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, EntityValidationError{ + field: "VirtualMachine", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetVirtualMachine()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return EntityValidationError{ + field: "VirtualMachine", + reason: "embedded message failed validation", + cause: err, + } + } + } + + case *Entity_Vminterface: + if v == nil { + err := EntityValidationError{ + field: "Entity", + reason: "oneof value cannot be a typed-nil", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetVminterface()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, EntityValidationError{ + field: "Vminterface", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, EntityValidationError{ + field: "Vminterface", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetVminterface()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return EntityValidationError{ + field: "Vminterface", + reason: "embedded message failed validation", + cause: err, + } + } + } + + case *Entity_VirtualDisk: + if v == nil { + err := EntityValidationError{ + field: "Entity", + reason: "oneof value cannot be a typed-nil", + } + if !all { + return err + } + errors = append(errors, err) + } + + if all { + switch v := interface{}(m.GetVirtualDisk()).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, EntityValidationError{ + field: "VirtualDisk", + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, EntityValidationError{ + field: "VirtualDisk", + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(m.GetVirtualDisk()).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return EntityValidationError{ + field: "VirtualDisk", + reason: "embedded message failed validation", + cause: err, + } + } + } + default: _ = v // ensures v is used } diff --git a/examples/main.go b/examples/main.go index 75331f9..49a435e 100644 --- a/examples/main.go +++ b/examples/main.go @@ -262,6 +262,119 @@ func main() { }, } + // Create a cluster group + clusterGroupEntity := &diode.ClusterGroup{ + Name: diode.String("cluster group B"), + Description: diode.String("cluster group B description"), + Tags: []*diode.Tag{ + { + Name: diode.String("tag 1"), + }, + }, + } + + // Create a cluster type + clusterTypeEntity := &diode.ClusterType{ + Name: diode.String("cluster type B"), + Description: diode.String("cluster type B description"), + Tags: []*diode.Tag{ + { + Name: diode.String("tag 1"), + }, + }, + } + + // Create a cluster + clusterEntity := &diode.Cluster{ + Name: diode.String("cluster A"), + Type: &diode.ClusterType{ + Name: diode.String("cluster type A"), + Description: diode.String("cluster type A description"), + }, + Group: &diode.ClusterGroup{ + Name: diode.String("cluster group A"), + }, + Site: &diode.Site{ + Name: diode.String("site A"), + }, + Status: diode.String("active"), + Description: diode.String("cluster A description"), + Tags: []*diode.Tag{ + { + Name: diode.String("tag 1"), + }, + }, + } + + // Create a virtual machine + virtualMachineEntity := &diode.VirtualMachine{ + Name: diode.String("Virtual Machine A"), + Status: diode.String("active"), + Site: &diode.Site{ + Name: diode.String("site 10"), + }, + Cluster: &diode.Cluster{ + Name: diode.String("cluster 10"), + Type: &diode.ClusterType{ + Name: diode.String("cluster type 10"), + }, + Group: &diode.ClusterGroup{ + Name: diode.String("cluster group 10"), + }, + Site: &diode.Site{ + Name: diode.String("site 10"), + }, + Status: diode.String("active"), + }, + Role: &diode.Role{ + Name: diode.String("Role 10"), + }, + Platform: &diode.Platform{ + Name: diode.String("Platform 10"), + Manufacturer: &diode.Manufacturer{ + Name: diode.String("Manufacturer 10"), + }, + }, + Vcpus: diode.Int32(1), + Memory: diode.Int32(4096), + Disk: diode.Int32(100), + Description: diode.String("Virtual Machine A description"), + Comments: diode.String("Lorem ipsum dolor sit amet"), + Tags: []*diode.Tag{ + { + Name: diode.String("tag 1"), + }, + }, + } + + // Create a virtual machine interface + virtualMachineInterfaceEntity := &diode.VMInterface{ + VirtualMachine: virtualMachineEntity, + Name: diode.String("Interface A"), + Enabled: diode.Bool(true), + Mtu: diode.Int32(1500), + MacAddress: diode.String("00:00:00:00:00:00"), + Description: diode.String("Interface A description"), + Tags: []*diode.Tag{ + { + Name: diode.String("tag 1"), + }, + }, + } + + // Create a virtual disk + virtualDiskEntity := &diode.VirtualDisk{ + VirtualMachine: virtualMachineEntity, + Name: diode.String("Disk A"), + Size: diode.Int32(100), + Description: diode.String("Disk A description"), + Tags: []*diode.Tag{ + { + Name: diode.String("tag 1"), + }, + }, + } + entities := []diode.Entity{ deviceEntity, deviceTypeEntity, @@ -272,8 +385,15 @@ func main() { prefixEntity, roleEntity, siteEntity, + clusterGroupEntity, + clusterTypeEntity, + clusterEntity, + virtualMachineEntity, + virtualMachineInterfaceEntity, + virtualDiskEntity, } + // Ingest entities resp, err := client.Ingest(context.Background(), entities) if err != nil { log.Fatal(err) diff --git a/internal/codegen/codegen.go b/internal/codegen/codegen.go index 8e88e11..2ab2f5c 100644 --- a/internal/codegen/codegen.go +++ b/internal/codegen/codegen.go @@ -33,6 +33,9 @@ func GenerateDiodeStructs() { assignableEntityTypes := retrieveTypesAssignableToEntities((*diodepb.Entity)(nil).ProtoReflect(), "") protoTypes := []protoreflect.ProtoMessage{ + (*diodepb.Cluster)(nil), + (*diodepb.ClusterGroup)(nil), + (*diodepb.ClusterType)(nil), (*diodepb.Device)(nil), (*diodepb.DeviceType)(nil), (*diodepb.IPAddress)(nil), @@ -43,6 +46,9 @@ func GenerateDiodeStructs() { (*diodepb.Role)(nil), (*diodepb.Site)(nil), (*diodepb.Tag)(nil), + (*diodepb.VMInterface)(nil), + (*diodepb.VirtualDisk)(nil), + (*diodepb.VirtualMachine)(nil), } fmt.Print("// Code generated by github.com/diode-sdk-go/internal/cmd/codegen. DO NOT EDIT.\n\n") @@ -300,10 +306,21 @@ func generateGetterMethod(t reflect.Type, params methodParams) { fmt.Printf("\t}\n") fmt.Printf("\treturn nil\n") } else { + defaultReturnValue := "\"\"" + if returnType == reflect.String.String() { + defaultReturnValue = "\"\"" + } else if returnType == reflect.Bool.String() { + defaultReturnValue = "false" + } else if returnType == reflect.Int32.String() { + defaultReturnValue = "0" + } else { + panic(fmt.Sprintf("unsupported return type %s for %s", returnType, params.fieldName)) + } + fmt.Printf("\tif e != nil && e.%s != nil {\n", params.fieldName) fmt.Printf("\t\treturn *e.%s\n", params.fieldName) fmt.Printf("\t}\n") - fmt.Printf("\treturn \"\"\n") + fmt.Printf("\treturn %s\n", defaultReturnValue) } fmt.Printf("}\n\n") } From 2e7e6014380cd4271127ce163a52862d9e5a3dc4 Mon Sep 17 00:00:00 2001 From: Michal Fiedorowicz Date: Fri, 30 Aug 2024 10:17:56 +0100 Subject: [PATCH 2/2] update README Signed-off-by: Michal Fiedorowicz --- README.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/README.md b/README.md index dc9909e..b9d7db3 100644 --- a/README.md +++ b/README.md @@ -122,6 +122,12 @@ See all [examples](./examples/main.go) for reference. * Prefix * Role * Site +* Cluster Group +* Cluster Type +* Cluster +* Virtual Machine +* Virtual Machine Interface +* Virtual Disk #### Linting