From 74b5adad00b8aa40b5a51a909db1cfdfe4051cff Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 11:59:39 -0800 Subject: [PATCH 1/8] feat: enables container filter to be configured at multiple places --- internal/agent/client.go | 12 +- internal/agent/pb/rpc.pb.go | 595 ++++++++++-------- internal/agent/pb/rpc_grpc.pb.go | 2 +- internal/agent/pb/types.pb.go | 2 +- internal/agent/server.go | 19 +- internal/docker/client.go | 51 +- internal/docker/container_store.go | 26 +- internal/docker/stats_collector.go | 6 +- internal/docker/types.go | 30 + internal/healthcheck/rpc.go | 3 +- internal/support/cli/clients.go | 12 +- internal/support/docker/agent_service.go | 4 +- internal/support/docker/client_service.go | 10 +- internal/support/docker/multi_host_service.go | 12 +- .../support/docker/swarm_client_manager.go | 4 +- internal/web/debug.go | 4 +- internal/web/events.go | 5 +- internal/web/logs.go | 2 +- main.go | 10 +- protos/rpc.proto | 7 +- 20 files changed, 467 insertions(+), 349 deletions(-) diff --git a/internal/agent/client.go b/internal/agent/client.go index 5d7185a3da75..d509f8fb35e4 100644 --- a/internal/agent/client.go +++ b/internal/agent/client.go @@ -303,8 +303,16 @@ func (c *Client) FindContainer(ctx context.Context, containerID string) (docker. }, nil } -func (c *Client) ListContainers(ctx context.Context) ([]docker.Container, error) { - response, err := c.client.ListContainers(ctx, &pb.ListContainersRequest{}) +func (c *Client) ListContainers(ctx context.Context, filter docker.ContainerFilter) ([]docker.Container, error) { + in := &pb.ListContainersRequest{} + + if filter != nil { + for k, v := range filter { + in.Filter[k] = &pb.RepeatedString{Values: v} + } + } + + response, err := c.client.ListContainers(ctx, in) if err != nil { return nil, err } diff --git a/internal/agent/pb/rpc.pb.go b/internal/agent/pb/rpc.pb.go index f2ef1ad1bc23..0d274306f5b7 100644 --- a/internal/agent/pb/rpc.pb.go +++ b/internal/agent/pb/rpc.pb.go @@ -1,7 +1,7 @@ // Code generated by protoc-gen-go. DO NOT EDIT. // versions: // protoc-gen-go v1.35.1 -// protoc v5.28.3 +// protoc v5.29.1 // source: rpc.proto package pb @@ -25,6 +25,8 @@ type ListContainersRequest struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache unknownFields protoimpl.UnknownFields + + Filter map[string]*RepeatedString `protobuf:"bytes,1,rep,name=filter,proto3" json:"filter,omitempty" protobuf_key:"bytes,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"` } func (x *ListContainersRequest) Reset() { @@ -57,6 +59,58 @@ func (*ListContainersRequest) Descriptor() ([]byte, []int) { return file_rpc_proto_rawDescGZIP(), []int{0} } +func (x *ListContainersRequest) GetFilter() map[string]*RepeatedString { + if x != nil { + return x.Filter + } + return nil +} + +type RepeatedString struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Values []string `protobuf:"bytes,1,rep,name=values,proto3" json:"values,omitempty"` +} + +func (x *RepeatedString) Reset() { + *x = RepeatedString{} + mi := &file_rpc_proto_msgTypes[1] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *RepeatedString) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*RepeatedString) ProtoMessage() {} + +func (x *RepeatedString) ProtoReflect() protoreflect.Message { + mi := &file_rpc_proto_msgTypes[1] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use RepeatedString.ProtoReflect.Descriptor instead. +func (*RepeatedString) Descriptor() ([]byte, []int) { + return file_rpc_proto_rawDescGZIP(), []int{1} +} + +func (x *RepeatedString) GetValues() []string { + if x != nil { + return x.Values + } + return nil +} + type ListContainersResponse struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache @@ -67,7 +121,7 @@ type ListContainersResponse struct { func (x *ListContainersResponse) Reset() { *x = ListContainersResponse{} - mi := &file_rpc_proto_msgTypes[1] + mi := &file_rpc_proto_msgTypes[2] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -79,7 +133,7 @@ func (x *ListContainersResponse) String() string { func (*ListContainersResponse) ProtoMessage() {} func (x *ListContainersResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[1] + mi := &file_rpc_proto_msgTypes[2] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -92,7 +146,7 @@ func (x *ListContainersResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ListContainersResponse.ProtoReflect.Descriptor instead. func (*ListContainersResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{1} + return file_rpc_proto_rawDescGZIP(), []int{2} } func (x *ListContainersResponse) GetContainers() []*Container { @@ -112,7 +166,7 @@ type FindContainerRequest struct { func (x *FindContainerRequest) Reset() { *x = FindContainerRequest{} - mi := &file_rpc_proto_msgTypes[2] + mi := &file_rpc_proto_msgTypes[3] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -124,7 +178,7 @@ func (x *FindContainerRequest) String() string { func (*FindContainerRequest) ProtoMessage() {} func (x *FindContainerRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[2] + mi := &file_rpc_proto_msgTypes[3] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -137,7 +191,7 @@ func (x *FindContainerRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use FindContainerRequest.ProtoReflect.Descriptor instead. func (*FindContainerRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{2} + return file_rpc_proto_rawDescGZIP(), []int{3} } func (x *FindContainerRequest) GetContainerId() string { @@ -157,7 +211,7 @@ type FindContainerResponse struct { func (x *FindContainerResponse) Reset() { *x = FindContainerResponse{} - mi := &file_rpc_proto_msgTypes[3] + mi := &file_rpc_proto_msgTypes[4] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -169,7 +223,7 @@ func (x *FindContainerResponse) String() string { func (*FindContainerResponse) ProtoMessage() {} func (x *FindContainerResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[3] + mi := &file_rpc_proto_msgTypes[4] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -182,7 +236,7 @@ func (x *FindContainerResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use FindContainerResponse.ProtoReflect.Descriptor instead. func (*FindContainerResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{3} + return file_rpc_proto_rawDescGZIP(), []int{4} } func (x *FindContainerResponse) GetContainer() *Container { @@ -204,7 +258,7 @@ type StreamLogsRequest struct { func (x *StreamLogsRequest) Reset() { *x = StreamLogsRequest{} - mi := &file_rpc_proto_msgTypes[4] + mi := &file_rpc_proto_msgTypes[5] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -216,7 +270,7 @@ func (x *StreamLogsRequest) String() string { func (*StreamLogsRequest) ProtoMessage() {} func (x *StreamLogsRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[4] + mi := &file_rpc_proto_msgTypes[5] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -229,7 +283,7 @@ func (x *StreamLogsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamLogsRequest.ProtoReflect.Descriptor instead. func (*StreamLogsRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{4} + return file_rpc_proto_rawDescGZIP(), []int{5} } func (x *StreamLogsRequest) GetContainerId() string { @@ -263,7 +317,7 @@ type StreamLogsResponse struct { func (x *StreamLogsResponse) Reset() { *x = StreamLogsResponse{} - mi := &file_rpc_proto_msgTypes[5] + mi := &file_rpc_proto_msgTypes[6] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -275,7 +329,7 @@ func (x *StreamLogsResponse) String() string { func (*StreamLogsResponse) ProtoMessage() {} func (x *StreamLogsResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[5] + mi := &file_rpc_proto_msgTypes[6] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -288,7 +342,7 @@ func (x *StreamLogsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamLogsResponse.ProtoReflect.Descriptor instead. func (*StreamLogsResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{5} + return file_rpc_proto_rawDescGZIP(), []int{6} } func (x *StreamLogsResponse) GetEvent() *LogEvent { @@ -311,7 +365,7 @@ type LogsBetweenDatesRequest struct { func (x *LogsBetweenDatesRequest) Reset() { *x = LogsBetweenDatesRequest{} - mi := &file_rpc_proto_msgTypes[6] + mi := &file_rpc_proto_msgTypes[7] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -323,7 +377,7 @@ func (x *LogsBetweenDatesRequest) String() string { func (*LogsBetweenDatesRequest) ProtoMessage() {} func (x *LogsBetweenDatesRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[6] + mi := &file_rpc_proto_msgTypes[7] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -336,7 +390,7 @@ func (x *LogsBetweenDatesRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use LogsBetweenDatesRequest.ProtoReflect.Descriptor instead. func (*LogsBetweenDatesRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{6} + return file_rpc_proto_rawDescGZIP(), []int{7} } func (x *LogsBetweenDatesRequest) GetContainerId() string { @@ -380,7 +434,7 @@ type StreamRawBytesRequest struct { func (x *StreamRawBytesRequest) Reset() { *x = StreamRawBytesRequest{} - mi := &file_rpc_proto_msgTypes[7] + mi := &file_rpc_proto_msgTypes[8] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -392,7 +446,7 @@ func (x *StreamRawBytesRequest) String() string { func (*StreamRawBytesRequest) ProtoMessage() {} func (x *StreamRawBytesRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[7] + mi := &file_rpc_proto_msgTypes[8] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -405,7 +459,7 @@ func (x *StreamRawBytesRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamRawBytesRequest.ProtoReflect.Descriptor instead. func (*StreamRawBytesRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{7} + return file_rpc_proto_rawDescGZIP(), []int{8} } func (x *StreamRawBytesRequest) GetContainerId() string { @@ -446,7 +500,7 @@ type StreamRawBytesResponse struct { func (x *StreamRawBytesResponse) Reset() { *x = StreamRawBytesResponse{} - mi := &file_rpc_proto_msgTypes[8] + mi := &file_rpc_proto_msgTypes[9] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -458,7 +512,7 @@ func (x *StreamRawBytesResponse) String() string { func (*StreamRawBytesResponse) ProtoMessage() {} func (x *StreamRawBytesResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[8] + mi := &file_rpc_proto_msgTypes[9] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -471,7 +525,7 @@ func (x *StreamRawBytesResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamRawBytesResponse.ProtoReflect.Descriptor instead. func (*StreamRawBytesResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{8} + return file_rpc_proto_rawDescGZIP(), []int{9} } func (x *StreamRawBytesResponse) GetData() []byte { @@ -489,7 +543,7 @@ type StreamEventsRequest struct { func (x *StreamEventsRequest) Reset() { *x = StreamEventsRequest{} - mi := &file_rpc_proto_msgTypes[9] + mi := &file_rpc_proto_msgTypes[10] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -501,7 +555,7 @@ func (x *StreamEventsRequest) String() string { func (*StreamEventsRequest) ProtoMessage() {} func (x *StreamEventsRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[9] + mi := &file_rpc_proto_msgTypes[10] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -514,7 +568,7 @@ func (x *StreamEventsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamEventsRequest.ProtoReflect.Descriptor instead. func (*StreamEventsRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{9} + return file_rpc_proto_rawDescGZIP(), []int{10} } type StreamEventsResponse struct { @@ -527,7 +581,7 @@ type StreamEventsResponse struct { func (x *StreamEventsResponse) Reset() { *x = StreamEventsResponse{} - mi := &file_rpc_proto_msgTypes[10] + mi := &file_rpc_proto_msgTypes[11] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -539,7 +593,7 @@ func (x *StreamEventsResponse) String() string { func (*StreamEventsResponse) ProtoMessage() {} func (x *StreamEventsResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[10] + mi := &file_rpc_proto_msgTypes[11] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -552,7 +606,7 @@ func (x *StreamEventsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamEventsResponse.ProtoReflect.Descriptor instead. func (*StreamEventsResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{10} + return file_rpc_proto_rawDescGZIP(), []int{11} } func (x *StreamEventsResponse) GetEvent() *ContainerEvent { @@ -570,7 +624,7 @@ type StreamStatsRequest struct { func (x *StreamStatsRequest) Reset() { *x = StreamStatsRequest{} - mi := &file_rpc_proto_msgTypes[11] + mi := &file_rpc_proto_msgTypes[12] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -582,7 +636,7 @@ func (x *StreamStatsRequest) String() string { func (*StreamStatsRequest) ProtoMessage() {} func (x *StreamStatsRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[11] + mi := &file_rpc_proto_msgTypes[12] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -595,7 +649,7 @@ func (x *StreamStatsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamStatsRequest.ProtoReflect.Descriptor instead. func (*StreamStatsRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{11} + return file_rpc_proto_rawDescGZIP(), []int{12} } type StreamStatsResponse struct { @@ -608,7 +662,7 @@ type StreamStatsResponse struct { func (x *StreamStatsResponse) Reset() { *x = StreamStatsResponse{} - mi := &file_rpc_proto_msgTypes[12] + mi := &file_rpc_proto_msgTypes[13] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -620,7 +674,7 @@ func (x *StreamStatsResponse) String() string { func (*StreamStatsResponse) ProtoMessage() {} func (x *StreamStatsResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[12] + mi := &file_rpc_proto_msgTypes[13] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -633,7 +687,7 @@ func (x *StreamStatsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamStatsResponse.ProtoReflect.Descriptor instead. func (*StreamStatsResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{12} + return file_rpc_proto_rawDescGZIP(), []int{13} } func (x *StreamStatsResponse) GetStat() *ContainerStat { @@ -651,7 +705,7 @@ type HostInfoRequest struct { func (x *HostInfoRequest) Reset() { *x = HostInfoRequest{} - mi := &file_rpc_proto_msgTypes[13] + mi := &file_rpc_proto_msgTypes[14] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -663,7 +717,7 @@ func (x *HostInfoRequest) String() string { func (*HostInfoRequest) ProtoMessage() {} func (x *HostInfoRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[13] + mi := &file_rpc_proto_msgTypes[14] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -676,7 +730,7 @@ func (x *HostInfoRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use HostInfoRequest.ProtoReflect.Descriptor instead. func (*HostInfoRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{13} + return file_rpc_proto_rawDescGZIP(), []int{14} } type HostInfoResponse struct { @@ -689,7 +743,7 @@ type HostInfoResponse struct { func (x *HostInfoResponse) Reset() { *x = HostInfoResponse{} - mi := &file_rpc_proto_msgTypes[14] + mi := &file_rpc_proto_msgTypes[15] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -701,7 +755,7 @@ func (x *HostInfoResponse) String() string { func (*HostInfoResponse) ProtoMessage() {} func (x *HostInfoResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[14] + mi := &file_rpc_proto_msgTypes[15] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -714,7 +768,7 @@ func (x *HostInfoResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use HostInfoResponse.ProtoReflect.Descriptor instead. func (*HostInfoResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{14} + return file_rpc_proto_rawDescGZIP(), []int{15} } func (x *HostInfoResponse) GetHost() *Host { @@ -732,7 +786,7 @@ type StreamContainerStartedRequest struct { func (x *StreamContainerStartedRequest) Reset() { *x = StreamContainerStartedRequest{} - mi := &file_rpc_proto_msgTypes[15] + mi := &file_rpc_proto_msgTypes[16] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -744,7 +798,7 @@ func (x *StreamContainerStartedRequest) String() string { func (*StreamContainerStartedRequest) ProtoMessage() {} func (x *StreamContainerStartedRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[15] + mi := &file_rpc_proto_msgTypes[16] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -757,7 +811,7 @@ func (x *StreamContainerStartedRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamContainerStartedRequest.ProtoReflect.Descriptor instead. func (*StreamContainerStartedRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{15} + return file_rpc_proto_rawDescGZIP(), []int{16} } type StreamContainerStartedResponse struct { @@ -770,7 +824,7 @@ type StreamContainerStartedResponse struct { func (x *StreamContainerStartedResponse) Reset() { *x = StreamContainerStartedResponse{} - mi := &file_rpc_proto_msgTypes[16] + mi := &file_rpc_proto_msgTypes[17] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -782,7 +836,7 @@ func (x *StreamContainerStartedResponse) String() string { func (*StreamContainerStartedResponse) ProtoMessage() {} func (x *StreamContainerStartedResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[16] + mi := &file_rpc_proto_msgTypes[17] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -795,7 +849,7 @@ func (x *StreamContainerStartedResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use StreamContainerStartedResponse.ProtoReflect.Descriptor instead. func (*StreamContainerStartedResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{16} + return file_rpc_proto_rawDescGZIP(), []int{17} } func (x *StreamContainerStartedResponse) GetContainer() *Container { @@ -816,7 +870,7 @@ type ContainerActionRequest struct { func (x *ContainerActionRequest) Reset() { *x = ContainerActionRequest{} - mi := &file_rpc_proto_msgTypes[17] + mi := &file_rpc_proto_msgTypes[18] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -828,7 +882,7 @@ func (x *ContainerActionRequest) String() string { func (*ContainerActionRequest) ProtoMessage() {} func (x *ContainerActionRequest) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[17] + mi := &file_rpc_proto_msgTypes[18] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -841,7 +895,7 @@ func (x *ContainerActionRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ContainerActionRequest.ProtoReflect.Descriptor instead. func (*ContainerActionRequest) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{17} + return file_rpc_proto_rawDescGZIP(), []int{18} } func (x *ContainerActionRequest) GetContainerId() string { @@ -866,7 +920,7 @@ type ContainerActionResponse struct { func (x *ContainerActionResponse) Reset() { *x = ContainerActionResponse{} - mi := &file_rpc_proto_msgTypes[18] + mi := &file_rpc_proto_msgTypes[19] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -878,7 +932,7 @@ func (x *ContainerActionResponse) String() string { func (*ContainerActionResponse) ProtoMessage() {} func (x *ContainerActionResponse) ProtoReflect() protoreflect.Message { - mi := &file_rpc_proto_msgTypes[18] + mi := &file_rpc_proto_msgTypes[19] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -891,7 +945,7 @@ func (x *ContainerActionResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ContainerActionResponse.ProtoReflect.Descriptor instead. func (*ContainerActionResponse) Descriptor() ([]byte, []int) { - return file_rpc_proto_rawDescGZIP(), []int{18} + return file_rpc_proto_rawDescGZIP(), []int{19} } var File_rpc_proto protoreflect.FileDescriptor @@ -901,150 +955,163 @@ var file_rpc_proto_rawDesc = []byte{ 0x74, 0x6f, 0x62, 0x75, 0x66, 0x1a, 0x0b, 0x74, 0x79, 0x70, 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x74, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x2e, 0x70, 0x72, - 0x6f, 0x74, 0x6f, 0x22, 0x17, 0x0a, 0x15, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, 0x74, 0x61, - 0x69, 0x6e, 0x65, 0x72, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x4d, 0x0a, 0x16, - 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x52, 0x65, - 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x33, 0x0a, 0x0a, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, - 0x6e, 0x65, 0x72, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x70, 0x72, 0x6f, - 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, - 0x0a, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x22, 0x38, 0x0a, 0x14, 0x46, + 0x6f, 0x74, 0x6f, 0x22, 0xb1, 0x01, 0x0a, 0x15, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, 0x74, + 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x43, 0x0a, + 0x06, 0x66, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x2b, 0x2e, + 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, + 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x2e, 0x46, + 0x69, 0x6c, 0x74, 0x65, 0x72, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x06, 0x66, 0x69, 0x6c, 0x74, + 0x65, 0x72, 0x1a, 0x53, 0x0a, 0x0b, 0x46, 0x69, 0x6c, 0x74, 0x65, 0x72, 0x45, 0x6e, 0x74, 0x72, + 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, + 0x6b, 0x65, 0x79, 0x12, 0x2e, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, + 0x28, 0x0b, 0x32, 0x18, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x52, 0x65, + 0x70, 0x65, 0x61, 0x74, 0x65, 0x64, 0x53, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x52, 0x05, 0x76, 0x61, + 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x28, 0x0a, 0x0e, 0x52, 0x65, 0x70, 0x65, 0x61, + 0x74, 0x65, 0x64, 0x53, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x12, 0x16, 0x0a, 0x06, 0x76, 0x61, 0x6c, + 0x75, 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x09, 0x52, 0x06, 0x76, 0x61, 0x6c, 0x75, 0x65, + 0x73, 0x22, 0x4d, 0x0a, 0x16, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, + 0x65, 0x72, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x33, 0x0a, 0x0a, 0x63, + 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, + 0x13, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, + 0x69, 0x6e, 0x65, 0x72, 0x52, 0x0a, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, + 0x22, 0x38, 0x0a, 0x14, 0x46, 0x69, 0x6e, 0x64, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, + 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x63, 0x6f, 0x6e, 0x74, + 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x63, + 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x22, 0x4a, 0x0a, 0x15, 0x46, 0x69, + 0x6e, 0x64, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x65, 0x73, 0x70, 0x6f, + 0x6e, 0x73, 0x65, 0x12, 0x31, 0x0a, 0x09, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, + 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, + 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x09, 0x63, 0x6f, 0x6e, + 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x22, 0x89, 0x01, 0x0a, 0x11, 0x53, 0x74, 0x72, 0x65, 0x61, + 0x6d, 0x4c, 0x6f, 0x67, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, + 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, + 0x09, 0x52, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x30, + 0x0a, 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x18, 0x02, 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, 0x52, 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, + 0x12, 0x20, 0x0a, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, 0x65, 0x73, 0x18, + 0x03, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, + 0x65, 0x73, 0x22, 0x3e, 0x0a, 0x12, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, + 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x28, 0x0a, 0x05, 0x65, 0x76, 0x65, 0x6e, + 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x12, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, + 0x75, 0x66, 0x2e, 0x4c, 0x6f, 0x67, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x52, 0x05, 0x65, 0x76, 0x65, + 0x6e, 0x74, 0x22, 0xc1, 0x01, 0x0a, 0x17, 0x4c, 0x6f, 0x67, 0x73, 0x42, 0x65, 0x74, 0x77, 0x65, + 0x65, 0x6e, 0x44, 0x61, 0x74, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, + 0x0a, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, + 0x01, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, + 0x12, 0x30, 0x0a, 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x18, 0x02, 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, 0x52, 0x05, 0x73, 0x69, 0x6e, + 0x63, 0x65, 0x12, 0x30, 0x0a, 0x05, 0x75, 0x6e, 0x74, 0x69, 0x6c, 0x18, 0x03, 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, 0x52, 0x05, 0x75, + 0x6e, 0x74, 0x69, 0x6c, 0x12, 0x20, 0x0a, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, + 0x70, 0x65, 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, + 0x6d, 0x54, 0x79, 0x70, 0x65, 0x73, 0x22, 0xbf, 0x01, 0x0a, 0x15, 0x53, 0x74, 0x72, 0x65, 0x61, + 0x6d, 0x52, 0x61, 0x77, 0x42, 0x79, 0x74, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, + 0x12, 0x20, 0x0a, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, + 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, + 0x49, 0x64, 0x12, 0x30, 0x0a, 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x18, 0x02, 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, 0x52, 0x05, 0x73, + 0x69, 0x6e, 0x63, 0x65, 0x12, 0x30, 0x0a, 0x05, 0x75, 0x6e, 0x74, 0x69, 0x6c, 0x18, 0x03, 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, 0x52, + 0x05, 0x75, 0x6e, 0x74, 0x69, 0x6c, 0x12, 0x20, 0x0a, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, + 0x54, 0x79, 0x70, 0x65, 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0b, 0x73, 0x74, 0x72, + 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, 0x65, 0x73, 0x22, 0x2c, 0x0a, 0x16, 0x53, 0x74, 0x72, 0x65, + 0x61, 0x6d, 0x52, 0x61, 0x77, 0x42, 0x79, 0x74, 0x65, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, + 0x73, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x64, 0x61, 0x74, 0x61, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, + 0x52, 0x04, 0x64, 0x61, 0x74, 0x61, 0x22, 0x15, 0x0a, 0x13, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, + 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x46, 0x0a, + 0x14, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x73, + 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x2e, 0x0a, 0x05, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x18, 0x01, + 0x20, 0x01, 0x28, 0x0b, 0x32, 0x18, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, + 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x52, 0x05, + 0x65, 0x76, 0x65, 0x6e, 0x74, 0x22, 0x14, 0x0a, 0x12, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x53, + 0x74, 0x61, 0x74, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x42, 0x0a, 0x13, 0x53, + 0x74, 0x72, 0x65, 0x61, 0x6d, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, + 0x73, 0x65, 0x12, 0x2b, 0x0a, 0x04, 0x73, 0x74, 0x61, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, + 0x32, 0x17, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, + 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, 0x74, 0x52, 0x04, 0x73, 0x74, 0x61, 0x74, 0x22, + 0x11, 0x0a, 0x0f, 0x48, 0x6f, 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x71, 0x75, 0x65, + 0x73, 0x74, 0x22, 0x36, 0x0a, 0x10, 0x48, 0x6f, 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, + 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x22, 0x0a, 0x04, 0x68, 0x6f, 0x73, 0x74, 0x18, 0x01, + 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, + 0x48, 0x6f, 0x73, 0x74, 0x52, 0x04, 0x68, 0x6f, 0x73, 0x74, 0x22, 0x1f, 0x0a, 0x1d, 0x53, 0x74, + 0x72, 0x65, 0x61, 0x6d, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, + 0x72, 0x74, 0x65, 0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x53, 0x0a, 0x1e, 0x53, + 0x74, 0x72, 0x65, 0x61, 0x6d, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, + 0x61, 0x72, 0x74, 0x65, 0x64, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x31, 0x0a, + 0x09, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, + 0x32, 0x13, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, + 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x09, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, + 0x22, 0x6d, 0x0a, 0x16, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, + 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x63, 0x6f, + 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, + 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x31, 0x0a, 0x06, + 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x19, 0x2e, 0x70, + 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, + 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x06, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x22, + 0x19, 0x0a, 0x17, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, + 0x6f, 0x6e, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x32, 0xeb, 0x06, 0x0a, 0x0c, 0x41, + 0x67, 0x65, 0x6e, 0x74, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x12, 0x55, 0x0a, 0x0e, 0x4c, + 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x12, 0x1f, 0x2e, + 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, + 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x20, + 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, + 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, + 0x22, 0x00, 0x12, 0x52, 0x0a, 0x0d, 0x46, 0x69, 0x6e, 0x64, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, + 0x6e, 0x65, 0x72, 0x12, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x46, 0x69, 0x6e, 0x64, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, - 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, - 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, - 0x6e, 0x65, 0x72, 0x49, 0x64, 0x22, 0x4a, 0x0a, 0x15, 0x46, 0x69, 0x6e, 0x64, 0x43, 0x6f, 0x6e, - 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x31, - 0x0a, 0x09, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, - 0x0b, 0x32, 0x13, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, - 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x09, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, - 0x72, 0x22, 0x89, 0x01, 0x0a, 0x11, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, - 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, - 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x6f, - 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x30, 0x0a, 0x05, 0x73, 0x69, 0x6e, - 0x63, 0x65, 0x18, 0x02, 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, 0x52, 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x12, 0x20, 0x0a, 0x0b, 0x73, - 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, 0x65, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x05, - 0x52, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, 0x65, 0x73, 0x22, 0x3e, 0x0a, - 0x12, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, - 0x6e, 0x73, 0x65, 0x12, 0x28, 0x0a, 0x05, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x18, 0x01, 0x20, 0x01, - 0x28, 0x0b, 0x32, 0x12, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4c, 0x6f, - 0x67, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x52, 0x05, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x22, 0xc1, 0x01, - 0x0a, 0x17, 0x4c, 0x6f, 0x67, 0x73, 0x42, 0x65, 0x74, 0x77, 0x65, 0x65, 0x6e, 0x44, 0x61, 0x74, - 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x63, 0x6f, 0x6e, - 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, - 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x30, 0x0a, 0x05, 0x73, - 0x69, 0x6e, 0x63, 0x65, 0x18, 0x02, 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, 0x52, 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x12, 0x30, 0x0a, - 0x05, 0x75, 0x6e, 0x74, 0x69, 0x6c, 0x18, 0x03, 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, 0x52, 0x05, 0x75, 0x6e, 0x74, 0x69, 0x6c, 0x12, - 0x20, 0x0a, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, 0x65, 0x73, 0x18, 0x04, - 0x20, 0x01, 0x28, 0x05, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, 0x65, - 0x73, 0x22, 0xbf, 0x01, 0x0a, 0x15, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x52, 0x61, 0x77, 0x42, - 0x79, 0x74, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x63, - 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, - 0x52, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x30, 0x0a, - 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x18, 0x02, 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, 0x52, 0x05, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x12, - 0x30, 0x0a, 0x05, 0x75, 0x6e, 0x74, 0x69, 0x6c, 0x18, 0x03, 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, 0x52, 0x05, 0x75, 0x6e, 0x74, 0x69, - 0x6c, 0x12, 0x20, 0x0a, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, 0x70, 0x65, 0x73, - 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x54, 0x79, - 0x70, 0x65, 0x73, 0x22, 0x2c, 0x0a, 0x16, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x52, 0x61, 0x77, - 0x42, 0x79, 0x74, 0x65, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x12, 0x0a, - 0x04, 0x64, 0x61, 0x74, 0x61, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x04, 0x64, 0x61, 0x74, - 0x61, 0x22, 0x15, 0x0a, 0x13, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, - 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x46, 0x0a, 0x14, 0x53, 0x74, 0x72, 0x65, - 0x61, 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, - 0x12, 0x2e, 0x0a, 0x05, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, - 0x18, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, - 0x69, 0x6e, 0x65, 0x72, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x52, 0x05, 0x65, 0x76, 0x65, 0x6e, 0x74, - 0x22, 0x14, 0x0a, 0x12, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, - 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x42, 0x0a, 0x13, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, - 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x2b, 0x0a, - 0x04, 0x73, 0x74, 0x61, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x70, 0x72, - 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, - 0x53, 0x74, 0x61, 0x74, 0x52, 0x04, 0x73, 0x74, 0x61, 0x74, 0x22, 0x11, 0x0a, 0x0f, 0x48, 0x6f, - 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x36, 0x0a, - 0x10, 0x48, 0x6f, 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, - 0x65, 0x12, 0x22, 0x0a, 0x04, 0x68, 0x6f, 0x73, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, - 0x0e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x48, 0x6f, 0x73, 0x74, 0x52, - 0x04, 0x68, 0x6f, 0x73, 0x74, 0x22, 0x1f, 0x0a, 0x1d, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x43, - 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, 0x72, 0x74, 0x65, 0x64, 0x52, - 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x53, 0x0a, 0x1e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, - 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, 0x72, 0x74, 0x65, 0x64, - 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x31, 0x0a, 0x09, 0x63, 0x6f, 0x6e, 0x74, - 0x61, 0x69, 0x6e, 0x65, 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x70, 0x72, - 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, - 0x52, 0x09, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x22, 0x6d, 0x0a, 0x16, 0x43, + 0x65, 0x73, 0x74, 0x1a, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x46, + 0x69, 0x6e, 0x64, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x65, 0x73, 0x70, + 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x4b, 0x0a, 0x0a, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, + 0x4c, 0x6f, 0x67, 0x73, 0x12, 0x1b, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, + 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, + 0x74, 0x1a, 0x1c, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, + 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, + 0x00, 0x30, 0x01, 0x12, 0x57, 0x0a, 0x10, 0x4c, 0x6f, 0x67, 0x73, 0x42, 0x65, 0x74, 0x77, 0x65, + 0x65, 0x6e, 0x44, 0x61, 0x74, 0x65, 0x73, 0x12, 0x21, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, + 0x75, 0x66, 0x2e, 0x4c, 0x6f, 0x67, 0x73, 0x42, 0x65, 0x74, 0x77, 0x65, 0x65, 0x6e, 0x44, 0x61, + 0x74, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1c, 0x2e, 0x70, 0x72, 0x6f, + 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, + 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x30, 0x01, 0x12, 0x57, 0x0a, 0x0e, + 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x52, 0x61, 0x77, 0x42, 0x79, 0x74, 0x65, 0x73, 0x12, 0x1f, + 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, + 0x52, 0x61, 0x77, 0x42, 0x79, 0x74, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, + 0x20, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, + 0x6d, 0x52, 0x61, 0x77, 0x42, 0x79, 0x74, 0x65, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, + 0x65, 0x22, 0x00, 0x30, 0x01, 0x12, 0x51, 0x0a, 0x0c, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x45, + 0x76, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x1d, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, + 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x71, + 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, + 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, + 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x30, 0x01, 0x12, 0x4e, 0x0a, 0x0b, 0x53, 0x74, 0x72, 0x65, + 0x61, 0x6d, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12, 0x1c, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, + 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x65, + 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1d, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, + 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, + 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x30, 0x01, 0x12, 0x6f, 0x0a, 0x16, 0x53, 0x74, 0x72, 0x65, + 0x61, 0x6d, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, 0x72, 0x74, + 0x65, 0x64, 0x12, 0x27, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, + 0x72, 0x65, 0x61, 0x6d, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, + 0x72, 0x74, 0x65, 0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x28, 0x2e, 0x70, 0x72, + 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x43, 0x6f, 0x6e, + 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, 0x72, 0x74, 0x65, 0x64, 0x52, 0x65, 0x73, + 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x30, 0x01, 0x12, 0x43, 0x0a, 0x08, 0x48, 0x6f, 0x73, + 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x19, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, + 0x2e, 0x48, 0x6f, 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, + 0x1a, 0x1a, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x48, 0x6f, 0x73, 0x74, + 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x58, + 0x0a, 0x0f, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, + 0x6e, 0x12, 0x20, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, + 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x71, 0x75, + 0x65, 0x73, 0x74, 0x1a, 0x21, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x65, - 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, - 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x6f, 0x6e, 0x74, - 0x61, 0x69, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x31, 0x0a, 0x06, 0x61, 0x63, 0x74, 0x69, 0x6f, - 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x19, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, - 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, - 0x6f, 0x6e, 0x52, 0x06, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x19, 0x0a, 0x17, 0x43, 0x6f, - 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x73, - 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x32, 0xeb, 0x06, 0x0a, 0x0c, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x53, - 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x12, 0x55, 0x0a, 0x0e, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, - 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x73, 0x12, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, - 0x62, 0x75, 0x66, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, - 0x72, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x20, 0x2e, 0x70, 0x72, 0x6f, 0x74, - 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, - 0x65, 0x72, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x52, 0x0a, - 0x0d, 0x46, 0x69, 0x6e, 0x64, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x12, 0x1e, - 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x46, 0x69, 0x6e, 0x64, 0x43, 0x6f, - 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1f, - 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x46, 0x69, 0x6e, 0x64, 0x43, 0x6f, - 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, - 0x00, 0x12, 0x4b, 0x0a, 0x0a, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, 0x12, - 0x1b, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, - 0x6d, 0x4c, 0x6f, 0x67, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1c, 0x2e, 0x70, - 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, - 0x67, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x30, 0x01, 0x12, 0x57, - 0x0a, 0x10, 0x4c, 0x6f, 0x67, 0x73, 0x42, 0x65, 0x74, 0x77, 0x65, 0x65, 0x6e, 0x44, 0x61, 0x74, - 0x65, 0x73, 0x12, 0x21, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4c, 0x6f, - 0x67, 0x73, 0x42, 0x65, 0x74, 0x77, 0x65, 0x65, 0x6e, 0x44, 0x61, 0x74, 0x65, 0x73, 0x52, 0x65, - 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1c, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, - 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x4c, 0x6f, 0x67, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, - 0x6e, 0x73, 0x65, 0x22, 0x00, 0x30, 0x01, 0x12, 0x57, 0x0a, 0x0e, 0x53, 0x74, 0x72, 0x65, 0x61, - 0x6d, 0x52, 0x61, 0x77, 0x42, 0x79, 0x74, 0x65, 0x73, 0x12, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x74, - 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x52, 0x61, 0x77, 0x42, 0x79, - 0x74, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x20, 0x2e, 0x70, 0x72, 0x6f, - 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x52, 0x61, 0x77, 0x42, - 0x79, 0x74, 0x65, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x30, 0x01, - 0x12, 0x51, 0x0a, 0x0c, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, - 0x12, 0x1d, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, - 0x61, 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, - 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, - 0x6d, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, - 0x00, 0x30, 0x01, 0x12, 0x4e, 0x0a, 0x0b, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x53, 0x74, 0x61, - 0x74, 0x73, 0x12, 0x1c, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, - 0x72, 0x65, 0x61, 0x6d, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, - 0x1a, 0x1d, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, - 0x61, 0x6d, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, - 0x00, 0x30, 0x01, 0x12, 0x6f, 0x0a, 0x16, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x43, 0x6f, 0x6e, - 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, 0x72, 0x74, 0x65, 0x64, 0x12, 0x27, 0x2e, - 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x43, - 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x53, 0x74, 0x61, 0x72, 0x74, 0x65, 0x64, 0x52, - 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x28, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, - 0x66, 0x2e, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, - 0x72, 0x53, 0x74, 0x61, 0x72, 0x74, 0x65, 0x64, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, - 0x22, 0x00, 0x30, 0x01, 0x12, 0x43, 0x0a, 0x08, 0x48, 0x6f, 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, - 0x12, 0x19, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x48, 0x6f, 0x73, 0x74, - 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1a, 0x2e, 0x70, 0x72, - 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x48, 0x6f, 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x52, - 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x12, 0x58, 0x0a, 0x0f, 0x43, 0x6f, 0x6e, - 0x74, 0x61, 0x69, 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x20, 0x2e, 0x70, - 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, 0x6e, 0x65, - 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x21, - 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6e, 0x74, 0x61, 0x69, - 0x6e, 0x65, 0x72, 0x41, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, - 0x65, 0x22, 0x00, 0x42, 0x13, 0x5a, 0x11, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x61, 0x6c, 0x2f, - 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2f, 0x70, 0x62, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x42, 0x13, 0x5a, 0x11, 0x69, 0x6e, 0x74, 0x65, + 0x72, 0x6e, 0x61, 0x6c, 0x2f, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2f, 0x70, 0x62, 0x62, 0x06, 0x70, + 0x72, 0x6f, 0x74, 0x6f, 0x33, } var ( @@ -1059,74 +1126,78 @@ func file_rpc_proto_rawDescGZIP() []byte { return file_rpc_proto_rawDescData } -var file_rpc_proto_msgTypes = make([]protoimpl.MessageInfo, 19) +var file_rpc_proto_msgTypes = make([]protoimpl.MessageInfo, 21) var file_rpc_proto_goTypes = []any{ (*ListContainersRequest)(nil), // 0: protobuf.ListContainersRequest - (*ListContainersResponse)(nil), // 1: protobuf.ListContainersResponse - (*FindContainerRequest)(nil), // 2: protobuf.FindContainerRequest - (*FindContainerResponse)(nil), // 3: protobuf.FindContainerResponse - (*StreamLogsRequest)(nil), // 4: protobuf.StreamLogsRequest - (*StreamLogsResponse)(nil), // 5: protobuf.StreamLogsResponse - (*LogsBetweenDatesRequest)(nil), // 6: protobuf.LogsBetweenDatesRequest - (*StreamRawBytesRequest)(nil), // 7: protobuf.StreamRawBytesRequest - (*StreamRawBytesResponse)(nil), // 8: protobuf.StreamRawBytesResponse - (*StreamEventsRequest)(nil), // 9: protobuf.StreamEventsRequest - (*StreamEventsResponse)(nil), // 10: protobuf.StreamEventsResponse - (*StreamStatsRequest)(nil), // 11: protobuf.StreamStatsRequest - (*StreamStatsResponse)(nil), // 12: protobuf.StreamStatsResponse - (*HostInfoRequest)(nil), // 13: protobuf.HostInfoRequest - (*HostInfoResponse)(nil), // 14: protobuf.HostInfoResponse - (*StreamContainerStartedRequest)(nil), // 15: protobuf.StreamContainerStartedRequest - (*StreamContainerStartedResponse)(nil), // 16: protobuf.StreamContainerStartedResponse - (*ContainerActionRequest)(nil), // 17: protobuf.ContainerActionRequest - (*ContainerActionResponse)(nil), // 18: protobuf.ContainerActionResponse - (*Container)(nil), // 19: protobuf.Container - (*timestamppb.Timestamp)(nil), // 20: google.protobuf.Timestamp - (*LogEvent)(nil), // 21: protobuf.LogEvent - (*ContainerEvent)(nil), // 22: protobuf.ContainerEvent - (*ContainerStat)(nil), // 23: protobuf.ContainerStat - (*Host)(nil), // 24: protobuf.Host - (ContainerAction)(0), // 25: protobuf.ContainerAction + (*RepeatedString)(nil), // 1: protobuf.RepeatedString + (*ListContainersResponse)(nil), // 2: protobuf.ListContainersResponse + (*FindContainerRequest)(nil), // 3: protobuf.FindContainerRequest + (*FindContainerResponse)(nil), // 4: protobuf.FindContainerResponse + (*StreamLogsRequest)(nil), // 5: protobuf.StreamLogsRequest + (*StreamLogsResponse)(nil), // 6: protobuf.StreamLogsResponse + (*LogsBetweenDatesRequest)(nil), // 7: protobuf.LogsBetweenDatesRequest + (*StreamRawBytesRequest)(nil), // 8: protobuf.StreamRawBytesRequest + (*StreamRawBytesResponse)(nil), // 9: protobuf.StreamRawBytesResponse + (*StreamEventsRequest)(nil), // 10: protobuf.StreamEventsRequest + (*StreamEventsResponse)(nil), // 11: protobuf.StreamEventsResponse + (*StreamStatsRequest)(nil), // 12: protobuf.StreamStatsRequest + (*StreamStatsResponse)(nil), // 13: protobuf.StreamStatsResponse + (*HostInfoRequest)(nil), // 14: protobuf.HostInfoRequest + (*HostInfoResponse)(nil), // 15: protobuf.HostInfoResponse + (*StreamContainerStartedRequest)(nil), // 16: protobuf.StreamContainerStartedRequest + (*StreamContainerStartedResponse)(nil), // 17: protobuf.StreamContainerStartedResponse + (*ContainerActionRequest)(nil), // 18: protobuf.ContainerActionRequest + (*ContainerActionResponse)(nil), // 19: protobuf.ContainerActionResponse + nil, // 20: protobuf.ListContainersRequest.FilterEntry + (*Container)(nil), // 21: protobuf.Container + (*timestamppb.Timestamp)(nil), // 22: google.protobuf.Timestamp + (*LogEvent)(nil), // 23: protobuf.LogEvent + (*ContainerEvent)(nil), // 24: protobuf.ContainerEvent + (*ContainerStat)(nil), // 25: protobuf.ContainerStat + (*Host)(nil), // 26: protobuf.Host + (ContainerAction)(0), // 27: protobuf.ContainerAction } var file_rpc_proto_depIdxs = []int32{ - 19, // 0: protobuf.ListContainersResponse.containers:type_name -> protobuf.Container - 19, // 1: protobuf.FindContainerResponse.container:type_name -> protobuf.Container - 20, // 2: protobuf.StreamLogsRequest.since:type_name -> google.protobuf.Timestamp - 21, // 3: protobuf.StreamLogsResponse.event:type_name -> protobuf.LogEvent - 20, // 4: protobuf.LogsBetweenDatesRequest.since:type_name -> google.protobuf.Timestamp - 20, // 5: protobuf.LogsBetweenDatesRequest.until:type_name -> google.protobuf.Timestamp - 20, // 6: protobuf.StreamRawBytesRequest.since:type_name -> google.protobuf.Timestamp - 20, // 7: protobuf.StreamRawBytesRequest.until:type_name -> google.protobuf.Timestamp - 22, // 8: protobuf.StreamEventsResponse.event:type_name -> protobuf.ContainerEvent - 23, // 9: protobuf.StreamStatsResponse.stat:type_name -> protobuf.ContainerStat - 24, // 10: protobuf.HostInfoResponse.host:type_name -> protobuf.Host - 19, // 11: protobuf.StreamContainerStartedResponse.container:type_name -> protobuf.Container - 25, // 12: protobuf.ContainerActionRequest.action:type_name -> protobuf.ContainerAction - 0, // 13: protobuf.AgentService.ListContainers:input_type -> protobuf.ListContainersRequest - 2, // 14: protobuf.AgentService.FindContainer:input_type -> protobuf.FindContainerRequest - 4, // 15: protobuf.AgentService.StreamLogs:input_type -> protobuf.StreamLogsRequest - 6, // 16: protobuf.AgentService.LogsBetweenDates:input_type -> protobuf.LogsBetweenDatesRequest - 7, // 17: protobuf.AgentService.StreamRawBytes:input_type -> protobuf.StreamRawBytesRequest - 9, // 18: protobuf.AgentService.StreamEvents:input_type -> protobuf.StreamEventsRequest - 11, // 19: protobuf.AgentService.StreamStats:input_type -> protobuf.StreamStatsRequest - 15, // 20: protobuf.AgentService.StreamContainerStarted:input_type -> protobuf.StreamContainerStartedRequest - 13, // 21: protobuf.AgentService.HostInfo:input_type -> protobuf.HostInfoRequest - 17, // 22: protobuf.AgentService.ContainerAction:input_type -> protobuf.ContainerActionRequest - 1, // 23: protobuf.AgentService.ListContainers:output_type -> protobuf.ListContainersResponse - 3, // 24: protobuf.AgentService.FindContainer:output_type -> protobuf.FindContainerResponse - 5, // 25: protobuf.AgentService.StreamLogs:output_type -> protobuf.StreamLogsResponse - 5, // 26: protobuf.AgentService.LogsBetweenDates:output_type -> protobuf.StreamLogsResponse - 8, // 27: protobuf.AgentService.StreamRawBytes:output_type -> protobuf.StreamRawBytesResponse - 10, // 28: protobuf.AgentService.StreamEvents:output_type -> protobuf.StreamEventsResponse - 12, // 29: protobuf.AgentService.StreamStats:output_type -> protobuf.StreamStatsResponse - 16, // 30: protobuf.AgentService.StreamContainerStarted:output_type -> protobuf.StreamContainerStartedResponse - 14, // 31: protobuf.AgentService.HostInfo:output_type -> protobuf.HostInfoResponse - 18, // 32: protobuf.AgentService.ContainerAction:output_type -> protobuf.ContainerActionResponse - 23, // [23:33] is the sub-list for method output_type - 13, // [13:23] is the sub-list for method input_type - 13, // [13:13] is the sub-list for extension type_name - 13, // [13:13] is the sub-list for extension extendee - 0, // [0:13] is the sub-list for field type_name + 20, // 0: protobuf.ListContainersRequest.filter:type_name -> protobuf.ListContainersRequest.FilterEntry + 21, // 1: protobuf.ListContainersResponse.containers:type_name -> protobuf.Container + 21, // 2: protobuf.FindContainerResponse.container:type_name -> protobuf.Container + 22, // 3: protobuf.StreamLogsRequest.since:type_name -> google.protobuf.Timestamp + 23, // 4: protobuf.StreamLogsResponse.event:type_name -> protobuf.LogEvent + 22, // 5: protobuf.LogsBetweenDatesRequest.since:type_name -> google.protobuf.Timestamp + 22, // 6: protobuf.LogsBetweenDatesRequest.until:type_name -> google.protobuf.Timestamp + 22, // 7: protobuf.StreamRawBytesRequest.since:type_name -> google.protobuf.Timestamp + 22, // 8: protobuf.StreamRawBytesRequest.until:type_name -> google.protobuf.Timestamp + 24, // 9: protobuf.StreamEventsResponse.event:type_name -> protobuf.ContainerEvent + 25, // 10: protobuf.StreamStatsResponse.stat:type_name -> protobuf.ContainerStat + 26, // 11: protobuf.HostInfoResponse.host:type_name -> protobuf.Host + 21, // 12: protobuf.StreamContainerStartedResponse.container:type_name -> protobuf.Container + 27, // 13: protobuf.ContainerActionRequest.action:type_name -> protobuf.ContainerAction + 1, // 14: protobuf.ListContainersRequest.FilterEntry.value:type_name -> protobuf.RepeatedString + 0, // 15: protobuf.AgentService.ListContainers:input_type -> protobuf.ListContainersRequest + 3, // 16: protobuf.AgentService.FindContainer:input_type -> protobuf.FindContainerRequest + 5, // 17: protobuf.AgentService.StreamLogs:input_type -> protobuf.StreamLogsRequest + 7, // 18: protobuf.AgentService.LogsBetweenDates:input_type -> protobuf.LogsBetweenDatesRequest + 8, // 19: protobuf.AgentService.StreamRawBytes:input_type -> protobuf.StreamRawBytesRequest + 10, // 20: protobuf.AgentService.StreamEvents:input_type -> protobuf.StreamEventsRequest + 12, // 21: protobuf.AgentService.StreamStats:input_type -> protobuf.StreamStatsRequest + 16, // 22: protobuf.AgentService.StreamContainerStarted:input_type -> protobuf.StreamContainerStartedRequest + 14, // 23: protobuf.AgentService.HostInfo:input_type -> protobuf.HostInfoRequest + 18, // 24: protobuf.AgentService.ContainerAction:input_type -> protobuf.ContainerActionRequest + 2, // 25: protobuf.AgentService.ListContainers:output_type -> protobuf.ListContainersResponse + 4, // 26: protobuf.AgentService.FindContainer:output_type -> protobuf.FindContainerResponse + 6, // 27: protobuf.AgentService.StreamLogs:output_type -> protobuf.StreamLogsResponse + 6, // 28: protobuf.AgentService.LogsBetweenDates:output_type -> protobuf.StreamLogsResponse + 9, // 29: protobuf.AgentService.StreamRawBytes:output_type -> protobuf.StreamRawBytesResponse + 11, // 30: protobuf.AgentService.StreamEvents:output_type -> protobuf.StreamEventsResponse + 13, // 31: protobuf.AgentService.StreamStats:output_type -> protobuf.StreamStatsResponse + 17, // 32: protobuf.AgentService.StreamContainerStarted:output_type -> protobuf.StreamContainerStartedResponse + 15, // 33: protobuf.AgentService.HostInfo:output_type -> protobuf.HostInfoResponse + 19, // 34: protobuf.AgentService.ContainerAction:output_type -> protobuf.ContainerActionResponse + 25, // [25:35] is the sub-list for method output_type + 15, // [15:25] is the sub-list for method input_type + 15, // [15:15] is the sub-list for extension type_name + 15, // [15:15] is the sub-list for extension extendee + 0, // [0:15] is the sub-list for field type_name } func init() { file_rpc_proto_init() } @@ -1141,7 +1212,7 @@ func file_rpc_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: file_rpc_proto_rawDesc, NumEnums: 0, - NumMessages: 19, + NumMessages: 21, NumExtensions: 0, NumServices: 1, }, diff --git a/internal/agent/pb/rpc_grpc.pb.go b/internal/agent/pb/rpc_grpc.pb.go index 6876651f4b21..b4c3d7a7b97e 100644 --- a/internal/agent/pb/rpc_grpc.pb.go +++ b/internal/agent/pb/rpc_grpc.pb.go @@ -1,7 +1,7 @@ // Code generated by protoc-gen-go-grpc. DO NOT EDIT. // versions: // - protoc-gen-go-grpc v1.5.1 -// - protoc v5.28.3 +// - protoc v5.29.1 // source: rpc.proto package pb diff --git a/internal/agent/pb/types.pb.go b/internal/agent/pb/types.pb.go index b609a265de8b..065c8d7cd335 100644 --- a/internal/agent/pb/types.pb.go +++ b/internal/agent/pb/types.pb.go @@ -1,7 +1,7 @@ // Code generated by protoc-gen-go. DO NOT EDIT. // versions: // protoc-gen-go v1.35.1 -// protoc v5.28.3 +// protoc v5.29.1 // source: types.proto package pb diff --git a/internal/agent/server.go b/internal/agent/server.go index 28df182da7a7..04797b7e539b 100644 --- a/internal/agent/server.go +++ b/internal/agent/server.go @@ -32,12 +32,12 @@ type server struct { pb.UnimplementedAgentServiceServer } -func newServer(client docker.Client, dozzleVersion string) pb.AgentServiceServer { +func newServer(client docker.Client, dozzleVersion string, filter docker.ContainerFilter) pb.AgentServiceServer { return &server{ client: client, version: dozzleVersion, - store: docker.NewContainerStore(context.Background(), client), + store: docker.NewContainerStore(context.Background(), client, filter), } } @@ -196,7 +196,16 @@ func (s *server) FindContainer(ctx context.Context, in *pb.FindContainerRequest) } func (s *server) ListContainers(ctx context.Context, in *pb.ListContainersRequest) (*pb.ListContainersResponse, error) { - containers, err := s.store.ListContainers() + filter := make(docker.ContainerFilter) + if in.GetFilter() != nil { + for k, v := range in.GetFilter() { + for _, vv := range v.GetValues() { + filter[k] = append(filter[k], vv) + } + } + } + + containers, err := s.store.ListContainers(filter) if err != nil { return nil, err } @@ -304,7 +313,7 @@ func (s *server) ContainerAction(ctx context.Context, in *pb.ContainerActionRequ return &pb.ContainerActionResponse{}, nil } -func NewServer(client docker.Client, certificates tls.Certificate, dozzleVersion string) (*grpc.Server, error) { +func NewServer(client docker.Client, certificates tls.Certificate, dozzleVersion string, filter docker.ContainerFilter) (*grpc.Server, error) { caCertPool := x509.NewCertPool() c, err := x509.ParseCertificate(certificates.Certificate[0]) if err != nil { @@ -323,7 +332,7 @@ func NewServer(client docker.Client, certificates tls.Certificate, dozzleVersion creds := credentials.NewTLS(tlsConfig) grpcServer := grpc.NewServer(grpc.Creds(creds)) - pb.RegisterAgentServiceServer(grpcServer, newServer(client, dozzleVersion)) + pb.RegisterAgentServiceServer(grpcServer, newServer(client, dozzleVersion, filter)) return grpcServer, nil } diff --git a/internal/docker/client.go b/internal/docker/client.go index c1a160ac0b3a..974ab8619aab 100644 --- a/internal/docker/client.go +++ b/internal/docker/client.go @@ -15,7 +15,6 @@ import ( "github.com/docker/docker/api/types" "github.com/docker/docker/api/types/container" "github.com/docker/docker/api/types/events" - "github.com/docker/docker/api/types/filters" "github.com/docker/docker/api/types/swarm" "github.com/docker/docker/api/types/system" "github.com/docker/docker/client" @@ -59,7 +58,7 @@ type DockerCLI interface { } type Client interface { - ListContainers(context.Context) ([]Container, error) + ListContainers(context.Context, ContainerFilter) ([]Container, error) FindContainer(context.Context, string) (Container, error) ContainerLogs(context.Context, string, time.Time, StdType) (io.ReadCloser, error) ContainerEvents(context.Context, chan<- ContainerEvent) error @@ -73,13 +72,12 @@ type Client interface { } type httpClient struct { - cli DockerCLI - filters filters.Args - host Host - info system.Info + cli DockerCLI + host Host + info system.Info } -func NewClient(cli DockerCLI, filters filters.Args, host Host) Client { +func NewClient(cli DockerCLI, host Host) Client { info, err := cli.Info(context.Background()) if err != nil { log.Error().Err(err).Msg("Failed to get docker info") @@ -90,24 +88,14 @@ func NewClient(cli DockerCLI, filters filters.Args, host Host) Client { host.DockerVersion = info.ServerVersion return &httpClient{ - cli: cli, - filters: filters, - host: host, - info: info, + cli: cli, + host: host, + info: info, } } // NewClientWithFilters creates a new instance of Client with docker filters -func NewLocalClient(f map[string][]string, hostname string) (Client, error) { - filterArgs := filters.NewArgs() - for key, values := range f { - for _, value := range values { - filterArgs.Add(key, value) - } - } - - log.Debug().Interface("filterArgs", filterArgs).Msg("Creating local client") - +func NewLocalClient(hostname string) (Client, error) { cli, err := client.NewClientWithOpts(client.FromEnv, client.WithAPIVersionNegotiation()) if err != nil { @@ -137,19 +125,10 @@ func NewLocalClient(f map[string][]string, hostname string) (Client, error) { host.Name = hostname } - return NewClient(cli, filterArgs, host), nil + return NewClient(cli, host), nil } -func NewRemoteClient(f map[string][]string, host Host) (Client, error) { - filterArgs := filters.NewArgs() - for key, values := range f { - for _, value := range values { - filterArgs.Add(key, value) - } - } - - log.Debug().Interface("filterArgs", filterArgs).Msg("Creating remote client") - +func NewRemoteClient(host Host) (Client, error) { if host.URL.Scheme != "tcp" { return nil, fmt.Errorf("invalid scheme: %s", host.URL.Scheme) } @@ -175,7 +154,7 @@ func NewRemoteClient(f map[string][]string, host Host) (Client, error) { host.Type = "remote" - return NewClient(cli, filterArgs, host), nil + return NewClient(cli, host), nil } // Finds a container by id, skipping the filters @@ -202,10 +181,10 @@ func (d *httpClient) ContainerActions(ctx context.Context, action ContainerActio } } -func (d *httpClient) ListContainers(ctx context.Context) ([]Container, error) { - log.Debug().Interface("filter", d.filters).Str("host", d.host.Name).Msg("Listing containers") +func (d *httpClient) ListContainers(ctx context.Context, filter ContainerFilter) ([]Container, error) { + log.Debug().Interface("filter", filter).Str("host", d.host.Name).Msg("Listing containers") containerListOptions := container.ListOptions{ - Filters: d.filters, + Filters: filter.asArgs(), All: true, } list, err := d.cli.ContainerList(ctx, containerListOptions) diff --git a/internal/docker/container_store.go b/internal/docker/container_store.go index cbe933a7523a..1067803caabb 100644 --- a/internal/docker/container_store.go +++ b/internal/docker/container_store.go @@ -23,18 +23,20 @@ type ContainerStore struct { connected atomic.Bool events chan ContainerEvent ctx context.Context + filter ContainerFilter } -func NewContainerStore(ctx context.Context, client Client) *ContainerStore { +func NewContainerStore(ctx context.Context, client Client, filter ContainerFilter) *ContainerStore { s := &ContainerStore{ containers: xsync.NewMapOf[string, *Container](), client: client, subscribers: xsync.NewMapOf[context.Context, chan<- ContainerEvent](), newContainerSubscribers: xsync.NewMapOf[context.Context, chan<- Container](), - statsCollector: NewStatsCollector(client), + statsCollector: NewStatsCollector(client, filter), wg: sync.WaitGroup{}, events: make(chan ContainerEvent), ctx: ctx, + filter: filter, } s.wg.Add(1) @@ -62,7 +64,7 @@ func (s *ContainerStore) checkConnectivity() error { ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second) // 3s is enough to fetch all containers defer cancel() - if containers, err := s.client.ListContainers(ctx); err != nil { + if containers, err := s.client.ListContainers(ctx, s.filter); err != nil { return err } else { s.containers.Clear() @@ -103,15 +105,27 @@ func (s *ContainerStore) checkConnectivity() error { return nil } -func (s *ContainerStore) ListContainers() ([]Container, error) { +func (s *ContainerStore) ListContainers(filter ContainerFilter) ([]Container, error) { s.wg.Wait() if err := s.checkConnectivity(); err != nil { return nil, err } + + validContainers, err := s.client.ListContainers(s.ctx, filter) + if err != nil { + return nil, err + } + + validIDMap := lo.KeyBy(validContainers, func(item Container) string { + return item.ID + }) + containers := make([]Container, 0) s.containers.Range(func(_ string, c *Container) bool { - containers = append(containers, *c) + if _, ok := validIDMap[c.ID]; ok { + containers = append(containers, *c) + } return true }) @@ -181,7 +195,7 @@ func (s *ContainerStore) init() { ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second) if container, err := s.client.FindContainer(ctx, event.ActorID); err == nil { - list, _ := s.client.ListContainers(ctx) + list, _ := s.client.ListContainers(ctx, s.filter) // make sure the container is in the list of containers when using filter valid := lo.ContainsBy(list, func(item Container) bool { diff --git a/internal/docker/stats_collector.go b/internal/docker/stats_collector.go index 488183f6c49b..e6d382c3e843 100644 --- a/internal/docker/stats_collector.go +++ b/internal/docker/stats_collector.go @@ -21,16 +21,18 @@ type StatsCollector struct { timer *time.Timer mu sync.Mutex totalStarted atomic.Int32 + filter ContainerFilter } var timeToStop = 6 * time.Hour -func NewStatsCollector(client Client) *StatsCollector { +func NewStatsCollector(client Client, filter ContainerFilter) *StatsCollector { return &StatsCollector{ stream: make(chan ContainerStat), subscribers: xsync.NewMapOf[context.Context, chan<- ContainerStat](), client: client, cancelers: xsync.NewMapOf[string, context.CancelFunc](), + filter: filter, } } @@ -98,7 +100,7 @@ func (sc *StatsCollector) Start(parentCtx context.Context) bool { sc.mu.Unlock() timeoutCtx, cancel := context.WithTimeout(parentCtx, 3*time.Second) // 3 seconds to list containers is hard limit - if containers, err := sc.client.ListContainers(timeoutCtx); err == nil { + if containers, err := sc.client.ListContainers(timeoutCtx, sc.filter); err == nil { for _, c := range containers { if c.State == "running" { go streamStats(ctx, sc, c.ID) diff --git a/internal/docker/types.go b/internal/docker/types.go index 933745214344..595a54648f30 100644 --- a/internal/docker/types.go +++ b/internal/docker/types.go @@ -3,9 +3,11 @@ package docker import ( "fmt" "math" + "strings" "time" "github.com/amir20/dozzle/internal/utils" + "github.com/docker/docker/api/types/filters" ) // Container represents an internal representation of docker containers @@ -41,6 +43,34 @@ type ContainerEvent struct { ActorAttributes map[string]string `json:"actorAttributes,omitempty"` } +type ContainerFilter map[string][]string + +func NewContainerFilter(values map[string]string) (ContainerFilter, error) { + containerFilter := make(ContainerFilter) + for _, filter := range values { + pos := strings.Index(filter, "=") + if pos == -1 { + return nil, fmt.Errorf("invalid filter: %s. each filter should be of the form key=value", filter) + } + key := filter[:pos] + val := filter[pos+1:] + containerFilter[key] = append(containerFilter[key], val) + } + + return containerFilter, nil +} + +func (f ContainerFilter) asArgs() filters.Args { + filterArgs := filters.NewArgs() + for key, values := range f { + for _, value := range values { + filterArgs.Add(key, value) + } + } + + return filterArgs +} + type LogPosition string const ( diff --git a/internal/healthcheck/rpc.go b/internal/healthcheck/rpc.go index b9405d21a93f..3fe7b244b1fb 100644 --- a/internal/healthcheck/rpc.go +++ b/internal/healthcheck/rpc.go @@ -5,6 +5,7 @@ import ( "crypto/tls" "github.com/amir20/dozzle/internal/agent" + "github.com/amir20/dozzle/internal/docker" "github.com/rs/zerolog/log" ) @@ -13,7 +14,7 @@ func RPCRequest(ctx context.Context, addr string, certs tls.Certificate) error { if err != nil { log.Fatal().Err(err).Msg("Failed to create agent client") } - containers, err := client.ListContainers(ctx) + containers, err := client.ListContainers(ctx, docker.ContainerFilter{}) log.Trace().Int("containers", len(containers)).Msg("Healtcheck RPC request completed") return err } diff --git a/internal/support/cli/clients.go b/internal/support/cli/clients.go index 8dd5cf0b4b02..94071964cc36 100644 --- a/internal/support/cli/clients.go +++ b/internal/support/cli/clients.go @@ -22,11 +22,11 @@ func CreateMultiHostService(embeddedCerts embed.FS, args Args) (docker.Client, * } log.Info().Interface("host", host).Msg("Adding remote host") - if client, err := docker.NewRemoteClient(args.Filter, host); err == nil { + if client, err := docker.NewRemoteClient(host); err == nil { ctx, cancel := context.WithTimeout(context.Background(), args.Timeout) defer cancel() - if _, err := client.ListContainers(ctx); err == nil { - clients = append(clients, docker_support.NewDockerClientService(client)) + if _, err := client.ListContainers(ctx, args.Filter); err == nil { + clients = append(clients, docker_support.NewDockerClientService(client, args.Filter)) } else { log.Warn().Err(err).Interface("host", host).Msg("Could not connect to remote host") } @@ -35,16 +35,16 @@ func CreateMultiHostService(embeddedCerts embed.FS, args Args) (docker.Client, * } } - localClient, err := docker.NewLocalClient(args.Filter, args.Hostname) + localClient, err := docker.NewLocalClient(args.Hostname) if err == nil { ctx, cancel := context.WithTimeout(context.Background(), args.Timeout) defer cancel() - _, err := localClient.ListContainers(ctx) + _, err := localClient.ListContainers(ctx, args.Filter) if err != nil { log.Debug().Err(err).Msg("Could not connect to local Docker Engine") } else { log.Debug().Msg("Adding local Docker Engine") - clients = append(clients, docker_support.NewDockerClientService(localClient)) + clients = append(clients, docker_support.NewDockerClientService(localClient, args.Filter)) } } diff --git a/internal/support/docker/agent_service.go b/internal/support/docker/agent_service.go index cd3d0382d28f..51016db95433 100644 --- a/internal/support/docker/agent_service.go +++ b/internal/support/docker/agent_service.go @@ -36,8 +36,8 @@ func (a *agentService) StreamLogs(ctx context.Context, container docker.Containe return a.client.StreamContainerLogs(ctx, container.ID, from, stdTypes, events) } -func (a *agentService) ListContainers(ctx context.Context) ([]docker.Container, error) { - return a.client.ListContainers(ctx) +func (a *agentService) ListContainers(ctx context.Context, filter docker.ContainerFilter) ([]docker.Container, error) { + return a.client.ListContainers(ctx, filter) } func (a *agentService) Host(ctx context.Context) (docker.Host, error) { diff --git a/internal/support/docker/client_service.go b/internal/support/docker/client_service.go index 60ecde2e7a30..0fe59b0b8c74 100644 --- a/internal/support/docker/client_service.go +++ b/internal/support/docker/client_service.go @@ -10,7 +10,7 @@ import ( type ClientService interface { FindContainer(ctx context.Context, id string) (docker.Container, error) - ListContainers(ctx context.Context) ([]docker.Container, error) + ListContainers(ctx context.Context, filter docker.ContainerFilter) ([]docker.Container, error) Host(ctx context.Context) (docker.Host, error) ContainerAction(ctx context.Context, container docker.Container, action docker.ContainerAction) error LogsBetweenDates(ctx context.Context, container docker.Container, from time.Time, to time.Time, stdTypes docker.StdType) (<-chan *docker.LogEvent, error) @@ -30,10 +30,10 @@ type dockerClientService struct { store *docker.ContainerStore } -func NewDockerClientService(client docker.Client) ClientService { +func NewDockerClientService(client docker.Client, filter docker.ContainerFilter) ClientService { return &dockerClientService{ client: client, - store: docker.NewContainerStore(context.Background(), client), + store: docker.NewContainerStore(context.Background(), client, filter), } } @@ -78,8 +78,8 @@ func (d *dockerClientService) ContainerAction(ctx context.Context, container doc return d.client.ContainerActions(ctx, action, container.ID) } -func (d *dockerClientService) ListContainers(ctx context.Context) ([]docker.Container, error) { - return d.store.ListContainers() +func (d *dockerClientService) ListContainers(ctx context.Context, filter docker.ContainerFilter) ([]docker.Container, error) { + return d.store.ListContainers(filter) } func (d *dockerClientService) Host(ctx context.Context) (docker.Host, error) { diff --git a/internal/support/docker/multi_host_service.go b/internal/support/docker/multi_host_service.go index 9da7e76fb1c3..d0d59da62284 100644 --- a/internal/support/docker/multi_host_service.go +++ b/internal/support/docker/multi_host_service.go @@ -61,7 +61,7 @@ func (m *MultiHostService) FindContainer(host string, id string) (*containerServ }, nil } -func (m *MultiHostService) ListContainersForHost(host string) ([]docker.Container, error) { +func (m *MultiHostService) ListContainersForHost(host string, filter docker.ContainerFilter) ([]docker.Container, error) { client, ok := m.manager.Find(host) if !ok { return nil, fmt.Errorf("host %s not found", host) @@ -69,17 +69,17 @@ func (m *MultiHostService) ListContainersForHost(host string) ([]docker.Containe ctx, cancel := context.WithTimeout(context.Background(), m.timeout) defer cancel() - return client.ListContainers(ctx) + return client.ListContainers(ctx, filter) } -func (m *MultiHostService) ListAllContainers() ([]docker.Container, []error) { +func (m *MultiHostService) ListAllContainers(filter docker.ContainerFilter) ([]docker.Container, []error) { containers := make([]docker.Container, 0) clients, errors := m.manager.RetryAndList() for _, client := range clients { ctx, cancel := context.WithTimeout(context.Background(), m.timeout) defer cancel() - list, err := client.ListContainers(ctx) + list, err := client.ListContainers(ctx, filter) if err != nil { host, _ := client.Host(ctx) log.Debug().Err(err).Str("host", host.Name).Msg("error listing containers") @@ -94,8 +94,8 @@ func (m *MultiHostService) ListAllContainers() ([]docker.Container, []error) { return containers, errors } -func (m *MultiHostService) ListAllContainersFiltered(filter ContainerFilter) ([]docker.Container, []error) { - containers, err := m.ListAllContainers() +func (m *MultiHostService) ListAllContainersFiltered(userFilter docker.ContainerFilter, filter ContainerFilter) ([]docker.Container, []error) { + containers, err := m.ListAllContainers(userFilter) filtered := make([]docker.Container, 0, len(containers)) for _, container := range containers { if filter(&container) { diff --git a/internal/support/docker/swarm_client_manager.go b/internal/support/docker/swarm_client_manager.go index 687148e1b8b3..c07070d968fa 100644 --- a/internal/support/docker/swarm_client_manager.go +++ b/internal/support/docker/swarm_client_manager.go @@ -47,9 +47,9 @@ func localIPs() []string { return ips } -func NewSwarmClientManager(localClient docker.Client, certs tls.Certificate, timeout time.Duration, agentManager *RetriableClientManager) *SwarmClientManager { +func NewSwarmClientManager(localClient docker.Client, certs tls.Certificate, timeout time.Duration, agentManager *RetriableClientManager, filter docker.ContainerFilter) *SwarmClientManager { clientMap := make(map[string]ClientService) - localService := NewDockerClientService(localClient) + localService := NewDockerClientService(localClient, filter) clientMap[localClient.Host().ID] = localService id, ok := os.LookupEnv("HOSTNAME") diff --git a/internal/web/debug.go b/internal/web/debug.go index f72400d02fc2..ebc39610f76f 100644 --- a/internal/web/debug.go +++ b/internal/web/debug.go @@ -3,12 +3,14 @@ package web import ( "encoding/json" "net/http" + + "github.com/amir20/dozzle/internal/docker" ) func (h *handler) debugStore(w http.ResponseWriter, r *http.Request) { respone := make(map[string]interface{}) respone["hosts"] = h.multiHostService.Hosts() - containers, errors := h.multiHostService.ListAllContainers() + containers, errors := h.multiHostService.ListAllContainers(docker.ContainerFilter{}) respone["containers"] = containers respone["errors"] = errors diff --git a/internal/web/events.go b/internal/web/events.go index bbf248d53601..9c8689fd2e7b 100644 --- a/internal/web/events.go +++ b/internal/web/events.go @@ -25,7 +25,8 @@ func (h *handler) streamEvents(w http.ResponseWriter, r *http.Request) { h.multiHostService.SubscribeEventsAndStats(r.Context(), events, stats) h.multiHostService.SubscribeAvailableHosts(r.Context(), availableHosts) - allContainers, errors := h.multiHostService.ListAllContainers() + // TODO - No user data so just fetch all containers + allContainers, errors := h.multiHostService.ListAllContainers(docker.ContainerFilter{}) for _, err := range errors { log.Warn().Err(err).Msg("error listing containers") @@ -63,7 +64,7 @@ func (h *handler) streamEvents(w http.ResponseWriter, r *http.Request) { if event.Name == "start" || event.Name == "rename" { log.Debug().Str("action", event.Name).Str("id", event.ActorID).Msg("container event") - if containers, err := h.multiHostService.ListContainersForHost(event.Host); err == nil { + if containers, err := h.multiHostService.ListContainersForHost(event.Host, docker.ContainerFilter{}); err == nil { if err := sseWriter.Event("containers-changed", containers); err != nil { log.Error().Err(err).Msg("error writing containers to event stream") return diff --git a/internal/web/logs.go b/internal/web/logs.go index d108d72a317c..652c0952eb63 100644 --- a/internal/web/logs.go +++ b/internal/web/logs.go @@ -288,7 +288,7 @@ func streamLogsForContainers(w http.ResponseWriter, r *http.Request, multiHostCl return } - existingContainers, errs := multiHostClient.ListAllContainersFiltered(filter) + existingContainers, errs := multiHostClient.ListAllContainersFiltered(docker.ContainerFilter{}, filter) if len(errs) > 0 { log.Warn().Err(errs[0]).Msg("error while listing containers") } diff --git a/main.go b/main.go index 8ba4f64044c5..b20c3f244222 100644 --- a/main.go +++ b/main.go @@ -37,7 +37,7 @@ func main() { if subcommand != nil { switch subcommand.(type) { case *cli.AgentCmd: - client, err := docker.NewLocalClient(args.Filter, args.Hostname) + client, err := docker.NewLocalClient(args.Hostname) if err != nil { log.Fatal().Err(err).Msg("Could not create docker client") } @@ -56,7 +56,7 @@ func main() { } io.WriteString(tempFile, listener.Addr().String()) go cli.StartEvent(args, "", client, "agent") - server, err := agent.NewServer(client, certs, args.Version()) + server, err := agent.NewServer(client, certs, args.Version(), args.Filter) if err != nil { log.Fatal().Err(err).Msg("failed to create agent server") } @@ -170,7 +170,7 @@ func main() { go cli.StartEvent(args, "server", localClient, "") } else if args.Mode == "swarm" { - localClient, err := docker.NewLocalClient(args.Filter, args.Hostname) + localClient, err := docker.NewLocalClient(args.Hostname) if err != nil { log.Fatal().Err(err).Msg("Could not create docker client") } @@ -179,14 +179,14 @@ func main() { log.Fatal().Err(err).Msg("Could not read certificates") } agentManager := docker_support.NewRetriableClientManager(args.RemoteAgent, args.Timeout, certs) - manager := docker_support.NewSwarmClientManager(localClient, certs, args.Timeout, agentManager) + manager := docker_support.NewSwarmClientManager(localClient, certs, args.Timeout, agentManager, args.Filter) multiHostService = docker_support.NewMultiHostService(manager, args.Timeout) log.Info().Msg("Starting in swarm mode") listener, err := net.Listen("tcp", ":7007") if err != nil { log.Fatal().Err(err).Msg("failed to listen") } - server, err := agent.NewServer(localClient, certs, args.Version()) + server, err := agent.NewServer(localClient, certs, args.Version(), args.Filter) if err != nil { log.Fatal().Err(err).Msg("failed to create agent") } diff --git a/protos/rpc.proto b/protos/rpc.proto index ff2bdc9a75de..0722b157f7ee 100644 --- a/protos/rpc.proto +++ b/protos/rpc.proto @@ -23,7 +23,9 @@ service AgentService { returns (ContainerActionResponse) {} } -message ListContainersRequest {} +message ListContainersRequest { map filter = 1; } + +message RepeatedString { repeated string values = 1; } message ListContainersResponse { repeated Container containers = 1; } @@ -72,5 +74,4 @@ message ContainerActionRequest { ContainerAction action = 2; } -message ContainerActionResponse { -} +message ContainerActionResponse {} From 9a73d18da687a8e8de27ab882ac9bbec6fddb2ad Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 12:07:43 -0800 Subject: [PATCH 2/8] removes unused code --- internal/docker/types.go | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/internal/docker/types.go b/internal/docker/types.go index 595a54648f30..69367c72f454 100644 --- a/internal/docker/types.go +++ b/internal/docker/types.go @@ -3,7 +3,6 @@ package docker import ( "fmt" "math" - "strings" "time" "github.com/amir20/dozzle/internal/utils" @@ -45,21 +44,6 @@ type ContainerEvent struct { type ContainerFilter map[string][]string -func NewContainerFilter(values map[string]string) (ContainerFilter, error) { - containerFilter := make(ContainerFilter) - for _, filter := range values { - pos := strings.Index(filter, "=") - if pos == -1 { - return nil, fmt.Errorf("invalid filter: %s. each filter should be of the form key=value", filter) - } - key := filter[:pos] - val := filter[pos+1:] - containerFilter[key] = append(containerFilter[key], val) - } - - return containerFilter, nil -} - func (f ContainerFilter) asArgs() filters.Args { filterArgs := filters.NewArgs() for key, values := range f { From 242c3e74dc83736f4029e3ee4abdaca9042c5fd2 Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 13:15:17 -0800 Subject: [PATCH 3/8] fixes some tests --- internal/agent/client_test.go | 8 ++++---- internal/docker/client_test.go | 25 ++++++++++++------------- internal/docker/container_store_test.go | 12 ++++++------ internal/docker/stats_collector_test.go | 2 +- internal/web/events_test.go | 2 +- internal/web/routes_test.go | 4 ++-- 6 files changed, 26 insertions(+), 27 deletions(-) diff --git a/internal/agent/client_test.go b/internal/agent/client_test.go index 46c944d45741..a3e97e6748d9 100644 --- a/internal/agent/client_test.go +++ b/internal/agent/client_test.go @@ -46,8 +46,8 @@ func (m *MockedClient) ContainerEvents(ctx context.Context, events chan<- docker return args.Error(0) } -func (m *MockedClient) ListContainers(ctx context.Context) ([]docker.Container, error) { - args := m.Called(ctx) +func (m *MockedClient) ListContainers(ctx context.Context, filter docker.ContainerFilter) ([]docker.Container, error) { + args := m.Called(ctx, filter) return args.Get(0).([]docker.Container), args.Error(1) } @@ -127,7 +127,7 @@ func init() { Stats: utils.NewRingBuffer[docker.ContainerStat](300), }, nil) - server, _ := NewServer(client, certs, "test") + server, _ := NewServer(client, certs, "test", docker.ContainerFilter{}) go server.Serve(lis) } @@ -167,7 +167,7 @@ func TestListContainers(t *testing.T) { t.Fatal(err) } - containers, _ := rpc.ListContainers(context.Background()) + containers, _ := rpc.ListContainers(context.Background(), docker.ContainerFilter{}) assert.Equal(t, containers, []docker.Container{ { diff --git a/internal/docker/client_test.go b/internal/docker/client_test.go index 67a29ea9b38b..2b478822e112 100644 --- a/internal/docker/client_test.go +++ b/internal/docker/client_test.go @@ -12,7 +12,6 @@ import ( "github.com/docker/docker/api/types" "github.com/docker/docker/api/types/container" - "github.com/docker/docker/api/types/filters" "github.com/docker/docker/api/types/system" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/mock" @@ -90,9 +89,9 @@ func (m *mockedProxy) ContainerRestart(ctx context.Context, containerID string, func Test_dockerClient_ListContainers_null(t *testing.T) { proxy := new(mockedProxy) proxy.On("ContainerList", mock.Anything, mock.Anything).Return(nil, nil) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} - list, err := client.ListContainers(context.Background()) + list, err := client.ListContainers(context.Background(), ContainerFilter{}) assert.Empty(t, list, "list should be empty") require.NoError(t, err, "error should not return an error.") @@ -102,9 +101,9 @@ func Test_dockerClient_ListContainers_null(t *testing.T) { func Test_dockerClient_ListContainers_error(t *testing.T) { proxy := new(mockedProxy) proxy.On("ContainerList", mock.Anything, mock.Anything).Return(nil, errors.New("test")) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} - list, err := client.ListContainers(context.Background()) + list, err := client.ListContainers(context.Background(), ContainerFilter{}) assert.Nil(t, list, "list should be nil") require.Error(t, err, "test.") @@ -125,9 +124,9 @@ func Test_dockerClient_ListContainers_happy(t *testing.T) { proxy := new(mockedProxy) proxy.On("ContainerList", mock.Anything, mock.Anything).Return(containers, nil) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} - list, err := client.ListContainers(context.Background()) + list, err := client.ListContainers(context.Background(), ContainerFilter{}) require.NoError(t, err, "error should not return an error.") Ids := []string{"1234567890_a", "abcdefghijkl"} @@ -159,7 +158,7 @@ func Test_dockerClient_ContainerLogs_happy(t *testing.T) { Since: "2020-12-31T23:59:59.95Z"} proxy.On("ContainerLogs", mock.Anything, id, options).Return(reader, nil) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} logReader, _ := client.ContainerLogs(context.Background(), id, since, STDALL) actual, _ := io.ReadAll(logReader) @@ -173,7 +172,7 @@ func Test_dockerClient_ContainerLogs_error(t *testing.T) { proxy.On("ContainerLogs", mock.Anything, id, mock.Anything).Return(nil, errors.New("test")) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} reader, err := client.ContainerLogs(context.Background(), id, time.Time{}, STDALL) @@ -189,7 +188,7 @@ func Test_dockerClient_FindContainer_happy(t *testing.T) { json := types.ContainerJSON{ContainerJSONBase: &types.ContainerJSONBase{ID: "abcdefghijklmnopqrst", State: state}, Config: &container.Config{Tty: false}} proxy.On("ContainerInspect", mock.Anything, "abcdefghijkl").Return(json, nil) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} container, err := client.FindContainer(context.Background(), "abcdefghijkl") require.NoError(t, err, "error should not be thrown") @@ -202,7 +201,7 @@ func Test_dockerClient_FindContainer_happy(t *testing.T) { func Test_dockerClient_FindContainer_error(t *testing.T) { proxy := new(mockedProxy) proxy.On("ContainerInspect", mock.Anything, "not_valid").Return(types.ContainerJSON{}, errors.New("not found")) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} _, err := client.FindContainer(context.Background(), "not_valid") require.Error(t, err, "error should be thrown") @@ -212,7 +211,7 @@ func Test_dockerClient_FindContainer_error(t *testing.T) { func Test_dockerClient_ContainerActions_happy(t *testing.T) { proxy := new(mockedProxy) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} state := &types.ContainerState{Status: "running", StartedAt: time.Now().Format(time.RFC3339Nano)} json := types.ContainerJSON{ContainerJSONBase: &types.ContainerJSONBase{ID: "abcdefghijkl", State: state}, Config: &container.Config{Tty: false}} @@ -240,7 +239,7 @@ func Test_dockerClient_ContainerActions_happy(t *testing.T) { func Test_dockerClient_ContainerActions_error(t *testing.T) { proxy := new(mockedProxy) - client := &httpClient{proxy, filters.NewArgs(), Host{ID: "localhost"}, system.Info{}} + client := &httpClient{proxy, Host{ID: "localhost"}, system.Info{}} proxy.On("ContainerInspect", mock.Anything, "random-id").Return(types.ContainerJSON{}, errors.New("not found")) proxy.On("ContainerStart", mock.Anything, mock.Anything, mock.Anything).Return(errors.New("test")) proxy.On("ContainerStop", mock.Anything, mock.Anything, mock.Anything).Return(errors.New("test")) diff --git a/internal/docker/container_store_test.go b/internal/docker/container_store_test.go index 64ab4869c35f..1a61e5958c98 100644 --- a/internal/docker/container_store_test.go +++ b/internal/docker/container_store_test.go @@ -14,8 +14,8 @@ type mockedClient struct { Client } -func (m *mockedClient) ListContainers(ctx context.Context) ([]Container, error) { - args := m.Called(ctx) +func (m *mockedClient) ListContainers(ctx context.Context, filter ContainerFilter) ([]Container, error) { + args := m.Called(ctx, filter) return args.Get(0).([]Container), args.Error(1) } @@ -66,8 +66,8 @@ func TestContainerStore_List(t *testing.T) { ctx, cancel := context.WithCancel(context.Background()) t.Cleanup(cancel) - store := NewContainerStore(ctx, client) - containers, _ := store.ListContainers() + store := NewContainerStore(ctx, client, ContainerFilter{}) + containers, _ := store.ListContainers(ContainerFilter{}) assert.Equal(t, containers[0].ID, "1234") } @@ -109,13 +109,13 @@ func TestContainerStore_die(t *testing.T) { ctx, cancel := context.WithCancel(context.Background()) t.Cleanup(cancel) - store := NewContainerStore(ctx, client) + store := NewContainerStore(ctx, client, ContainerFilter{}) // Wait until we get the event events := make(chan ContainerEvent) store.SubscribeEvents(ctx, events) <-events - containers, _ := store.ListContainers() + containers, _ := store.ListContainers(ContainerFilter{}) assert.Equal(t, containers[0].State, "exited") } diff --git a/internal/docker/stats_collector_test.go b/internal/docker/stats_collector_test.go index bd8ce297dcfa..87601386f5ea 100644 --- a/internal/docker/stats_collector_test.go +++ b/internal/docker/stats_collector_test.go @@ -35,7 +35,7 @@ func startedCollector(ctx context.Context) *StatsCollector { ID: "localhost", }) - collector := NewStatsCollector(client) + collector := NewStatsCollector(client, ContainerFilter{}) stats := make(chan ContainerStat) collector.Subscribe(ctx, stats) diff --git a/internal/web/events_test.go b/internal/web/events_test.go index be0322a001e5..51f0106a912b 100644 --- a/internal/web/events_test.go +++ b/internal/web/events_test.go @@ -54,7 +54,7 @@ func Test_handler_streamEvents_happy(t *testing.T) { }) // This is needed so that the server is initialized for store - manager := docker_support.NewRetriableClientManager(nil, 3*time.Second, tls.Certificate{}, docker_support.NewDockerClientService(mockedClient)) + manager := docker_support.NewRetriableClientManager(nil, 3*time.Second, tls.Certificate{}, docker_support.NewDockerClientService(mockedClient, docker.ContainerFilter{})) multiHostService := docker_support.NewMultiHostService(manager, 3*time.Second) server := CreateServer(multiHostService, nil, Config{Base: "/", Authorization: Authorization{Provider: NONE}}) diff --git a/internal/web/routes_test.go b/internal/web/routes_test.go index 3cfa286f30d0..12822e179ab3 100644 --- a/internal/web/routes_test.go +++ b/internal/web/routes_test.go @@ -38,8 +38,8 @@ func (m *MockedClient) ContainerEvents(ctx context.Context, events chan<- docker return args.Error(0) } -func (m *MockedClient) ListContainers(ctx context.Context) ([]docker.Container, error) { - args := m.Called(ctx) +func (m *MockedClient) ListContainers(ctx context.Context, filter docker.ContainerFilter) ([]docker.Container, error) { + args := m.Called(ctx, filter) return args.Get(0).([]docker.Container), args.Error(1) } From c0b40da585543691ffbb08bde8a2c69b08d43058 Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 13:20:15 -0800 Subject: [PATCH 4/8] adds logging --- internal/docker/container_store.go | 2 ++ 1 file changed, 2 insertions(+) diff --git a/internal/docker/container_store.go b/internal/docker/container_store.go index 1067803caabb..b139c9352784 100644 --- a/internal/docker/container_store.go +++ b/internal/docker/container_store.go @@ -27,6 +27,8 @@ type ContainerStore struct { } func NewContainerStore(ctx context.Context, client Client, filter ContainerFilter) *ContainerStore { + log.Debug().Str("host", client.Host().Name).Interface("filter", filter).Msg("initializing container store") + s := &ContainerStore{ containers: xsync.NewMapOf[string, *Container](), client: client, From 864af3c24d87cedf66cc5bd76ed1a3f355e5e129 Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 14:14:51 -0800 Subject: [PATCH 5/8] fixes nil pointer --- internal/agent/client.go | 1 + internal/support/docker/agent_service.go | 3 +++ internal/web/events.go | 3 +-- internal/web/routes.go | 2 ++ main.go | 1 + 5 files changed, 8 insertions(+), 2 deletions(-) diff --git a/internal/agent/client.go b/internal/agent/client.go index d509f8fb35e4..0d1d94fa262f 100644 --- a/internal/agent/client.go +++ b/internal/agent/client.go @@ -307,6 +307,7 @@ func (c *Client) ListContainers(ctx context.Context, filter docker.ContainerFilt in := &pb.ListContainersRequest{} if filter != nil { + in.Filter = make(map[string]*pb.RepeatedString) for k, v := range filter { in.Filter[k] = &pb.RepeatedString{Values: v} } diff --git a/internal/support/docker/agent_service.go b/internal/support/docker/agent_service.go index 51016db95433..27e21f62a7ce 100644 --- a/internal/support/docker/agent_service.go +++ b/internal/support/docker/agent_service.go @@ -3,10 +3,12 @@ package docker_support import ( "context" "io" + "time" "github.com/amir20/dozzle/internal/agent" "github.com/amir20/dozzle/internal/docker" + "github.com/rs/zerolog/log" ) type agentService struct { @@ -37,6 +39,7 @@ func (a *agentService) StreamLogs(ctx context.Context, container docker.Containe } func (a *agentService) ListContainers(ctx context.Context, filter docker.ContainerFilter) ([]docker.Container, error) { + log.Debug().Interface("filter", filter).Msg("Listing containers from agent") return a.client.ListContainers(ctx, filter) } diff --git a/internal/web/events.go b/internal/web/events.go index 9c8689fd2e7b..77377cc9638f 100644 --- a/internal/web/events.go +++ b/internal/web/events.go @@ -25,8 +25,7 @@ func (h *handler) streamEvents(w http.ResponseWriter, r *http.Request) { h.multiHostService.SubscribeEventsAndStats(r.Context(), events, stats) h.multiHostService.SubscribeAvailableHosts(r.Context(), availableHosts) - // TODO - No user data so just fetch all containers - allContainers, errors := h.multiHostService.ListAllContainers(docker.ContainerFilter{}) + allContainers, errors := h.multiHostService.ListAllContainers(h.config.Filter) for _, err := range errors { log.Warn().Err(err).Msg("error listing containers") diff --git a/internal/web/routes.go b/internal/web/routes.go index 36451b540a1f..47274ffc5f20 100644 --- a/internal/web/routes.go +++ b/internal/web/routes.go @@ -8,6 +8,7 @@ import ( "strings" "github.com/amir20/dozzle/internal/auth" + "github.com/amir20/dozzle/internal/docker" docker_support "github.com/amir20/dozzle/internal/support/docker" "github.com/go-chi/chi/v5" @@ -33,6 +34,7 @@ type Config struct { Dev bool Authorization Authorization EnableActions bool + Filter docker.ContainerFilter } type Authorization struct { diff --git a/main.go b/main.go index b20c3f244222..c9ced77c4f00 100644 --- a/main.go +++ b/main.go @@ -284,6 +284,7 @@ func createServer(args cli.Args, multiHostService *docker_support.MultiHostServi TTL: authTTL, }, EnableActions: args.EnableActions, + Filter: args.Filter, } assets, err := fs.Sub(content, "dist") From d2e1b26fb4988227219f2b8b4d9cbf905ceb8a12 Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 14:30:46 -0800 Subject: [PATCH 6/8] fixes all tests --- internal/agent/client_test.go | 2 +- internal/docker/container_store_test.go | 4 ++-- internal/docker/stats_collector_test.go | 2 +- internal/web/actions_test.go | 2 +- internal/web/download_test.go | 2 +- internal/web/events_test.go | 2 +- internal/web/logs_test.go | 14 +++++++------- internal/web/routes_test.go | 4 ++-- 8 files changed, 16 insertions(+), 16 deletions(-) diff --git a/internal/agent/client_test.go b/internal/agent/client_test.go index a3e97e6748d9..fafa7e947ce6 100644 --- a/internal/agent/client_test.go +++ b/internal/agent/client_test.go @@ -92,7 +92,7 @@ func init() { } client = &MockedClient{} - client.On("ListContainers", mock.Anything).Return([]docker.Container{ + client.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ { ID: "123456", Name: "test", diff --git a/internal/docker/container_store_test.go b/internal/docker/container_store_test.go index 1a61e5958c98..c2a9764e87fb 100644 --- a/internal/docker/container_store_test.go +++ b/internal/docker/container_store_test.go @@ -42,7 +42,7 @@ func (m *mockedClient) Host() Host { func TestContainerStore_List(t *testing.T) { client := new(mockedClient) - client.On("ListContainers", mock.Anything).Return([]Container{ + client.On("ListContainers", mock.Anything, mock.Anything).Return([]Container{ { ID: "1234", Name: "test", @@ -74,7 +74,7 @@ func TestContainerStore_List(t *testing.T) { func TestContainerStore_die(t *testing.T) { client := new(mockedClient) - client.On("ListContainers", mock.Anything).Return([]Container{ + client.On("ListContainers", mock.Anything, mock.Anything).Return([]Container{ { ID: "1234", Name: "test", diff --git a/internal/docker/stats_collector_test.go b/internal/docker/stats_collector_test.go index 87601386f5ea..47a8ab1dd5a8 100644 --- a/internal/docker/stats_collector_test.go +++ b/internal/docker/stats_collector_test.go @@ -10,7 +10,7 @@ import ( func startedCollector(ctx context.Context) *StatsCollector { client := new(mockedClient) - client.On("ListContainers", mock.Anything).Return([]Container{ + client.On("ListContainers", mock.Anything, mock.Anything).Return([]Container{ { ID: "1234", Name: "test", diff --git a/internal/web/actions_test.go b/internal/web/actions_test.go index c30426539060..9f9800408614 100644 --- a/internal/web/actions_test.go +++ b/internal/web/actions_test.go @@ -25,7 +25,7 @@ func mockedClient() *MockedClient { mockedClient.On("ContainerActions", mock.Anything, docker.Start, mock.Anything).Return(errors.New("container not found")) mockedClient.On("ContainerActions", mock.Anything, docker.ContainerAction("something-else"), container.ID).Return(errors.New("unknown action")) mockedClient.On("Host").Return(docker.Host{ID: "localhost"}) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{container}, nil) + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{container}, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.Anything).Return(nil) return mockedClient diff --git a/internal/web/download_test.go b/internal/web/download_test.go index 3dd07f6246d0..b66e1fb72a7b 100644 --- a/internal/web/download_test.go +++ b/internal/web/download_test.go @@ -33,7 +33,7 @@ func Test_handler_download_logs(t *testing.T) { mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil).Run(func(args mock.Arguments) { time.Sleep(1 * time.Second) }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", State: "running"}, }, nil) diff --git a/internal/web/events_test.go b/internal/web/events_test.go index 51f0106a912b..3e86717f4a68 100644 --- a/internal/web/events_test.go +++ b/internal/web/events_test.go @@ -24,7 +24,7 @@ func Test_handler_streamEvents_happy(t *testing.T) { mockedClient := new(MockedClient) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{}, nil) + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{}, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil).Run(func(args mock.Arguments) { messages := args.Get(1).(chan<- docker.ContainerEvent) diff --git a/internal/web/logs_test.go b/internal/web/logs_test.go index 7cfb30946f36..5a3a1d8f3497 100644 --- a/internal/web/logs_test.go +++ b/internal/web/logs_test.go @@ -50,7 +50,7 @@ func Test_handler_streamLogs_happy(t *testing.T) { mockedClient.On("Host").Return(docker.Host{ ID: "localhost", }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", Host: "localhost", State: "running"}, }, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil).Run(func(args mock.Arguments) { @@ -94,7 +94,7 @@ func Test_handler_streamLogs_happy_with_id(t *testing.T) { ID: "localhost", }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", Host: "localhost", State: "running"}, }, nil) @@ -133,7 +133,7 @@ func Test_handler_streamLogs_happy_container_stopped(t *testing.T) { mockedClient.On("Host").Return(docker.Host{ ID: "localhost", }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", Host: "localhost", State: "running"}, }, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil) @@ -170,7 +170,7 @@ func Test_handler_streamLogs_error_reading(t *testing.T) { mockedClient.On("Host").Return(docker.Host{ ID: "localhost", }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", Host: "localhost", State: "running"}, }, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil) @@ -193,7 +193,7 @@ func Test_handler_streamLogs_error_std(t *testing.T) { mockedClient.On("Host").Return(docker.Host{ ID: "localhost", }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", Host: "localhost", State: "running"}, }, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil). @@ -235,7 +235,7 @@ func Test_handler_between_dates(t *testing.T) { mockedClient.On("Host").Return(docker.Host{ ID: "localhost", }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", Host: "localhost", State: "running"}, }, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil) @@ -281,7 +281,7 @@ func Test_handler_between_dates_with_fill(t *testing.T) { mockedClient.On("Host").Return(docker.Host{ ID: "localhost", }) - mockedClient.On("ListContainers", mock.Anything).Return([]docker.Container{ + mockedClient.On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{ {ID: id, Name: "test", Host: "localhost", State: "running"}, }, nil) mockedClient.On("ContainerEvents", mock.Anything, mock.AnythingOfType("chan<- docker.ContainerEvent")).Return(nil) diff --git a/internal/web/routes_test.go b/internal/web/routes_test.go index 12822e179ab3..bb23e31ce06a 100644 --- a/internal/web/routes_test.go +++ b/internal/web/routes_test.go @@ -73,7 +73,7 @@ func (m *MockedClient) SystemInfo() system.Info { func createHandler(client docker.Client, content fs.FS, config Config) *chi.Mux { if client == nil { client = new(MockedClient) - client.(*MockedClient).On("ListContainers", mock.Anything).Return([]docker.Container{}, nil) + client.(*MockedClient).On("ListContainers", mock.Anything, mock.Anything).Return([]docker.Container{}, nil) client.(*MockedClient).On("Host").Return(docker.Host{ ID: "localhost", }) @@ -86,7 +86,7 @@ func createHandler(client docker.Client, content fs.FS, config Config) *chi.Mux content = afero.NewIOFS(fs) } - manager := docker_support.NewRetriableClientManager(nil, 3*time.Second, tls.Certificate{}, docker_support.NewDockerClientService(client)) + manager := docker_support.NewRetriableClientManager(nil, 3*time.Second, tls.Certificate{}, docker_support.NewDockerClientService(client, docker.ContainerFilter{})) multiHostService := docker_support.NewMultiHostService(manager, 3*time.Second) return createRouter(&handler{ multiHostService: multiHostService, From 55baf9e12cd0517ae9220d7b9e771f1b3b14610a Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 14:36:06 -0800 Subject: [PATCH 7/8] fixes static checker --- internal/agent/server.go | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/internal/agent/server.go b/internal/agent/server.go index 04797b7e539b..44192ad43076 100644 --- a/internal/agent/server.go +++ b/internal/agent/server.go @@ -199,9 +199,7 @@ func (s *server) ListContainers(ctx context.Context, in *pb.ListContainersReques filter := make(docker.ContainerFilter) if in.GetFilter() != nil { for k, v := range in.GetFilter() { - for _, vv := range v.GetValues() { - filter[k] = append(filter[k], vv) - } + filter[k] = append(filter[k], v.GetValues()...) } } From 9f2d1722779f135b4177ccd5c08dea7c9ed5bdc9 Mon Sep 17 00:00:00 2001 From: Amir Raminfar Date: Fri, 13 Dec 2024 15:25:23 -0800 Subject: [PATCH 8/8] fixes missed filter --- internal/web/logs.go | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/internal/web/logs.go b/internal/web/logs.go index 652c0952eb63..f673876168aa 100644 --- a/internal/web/logs.go +++ b/internal/web/logs.go @@ -226,7 +226,7 @@ func (h *handler) fetchLogsBetweenDates(w http.ResponseWriter, r *http.Request) func (h *handler) streamContainerLogs(w http.ResponseWriter, r *http.Request) { id := chi.URLParam(r, "id") - streamLogsForContainers(w, r, h.multiHostService, func(container *docker.Container) bool { + h.streamLogsForContainers(w, r, func(container *docker.Container) bool { return container.ID == id && container.Host == hostKey(r) }) } @@ -239,14 +239,14 @@ func (h *handler) streamLogsMerged(w http.ResponseWriter, r *http.Request) { ids[id] = true } - streamLogsForContainers(w, r, h.multiHostService, func(container *docker.Container) bool { + h.streamLogsForContainers(w, r, func(container *docker.Container) bool { return ids[container.ID] && container.Host == hostKey(r) }) } func (h *handler) streamServiceLogs(w http.ResponseWriter, r *http.Request) { service := chi.URLParam(r, "service") - streamLogsForContainers(w, r, h.multiHostService, func(container *docker.Container) bool { + h.streamLogsForContainers(w, r, func(container *docker.Container) bool { return container.State == "running" && container.Labels["com.docker.swarm.service.name"] == service }) } @@ -254,7 +254,7 @@ func (h *handler) streamServiceLogs(w http.ResponseWriter, r *http.Request) { func (h *handler) streamGroupedLogs(w http.ResponseWriter, r *http.Request) { group := chi.URLParam(r, "group") - streamLogsForContainers(w, r, h.multiHostService, func(container *docker.Container) bool { + h.streamLogsForContainers(w, r, func(container *docker.Container) bool { return container.State == "running" && container.Group == group }) } @@ -262,12 +262,12 @@ func (h *handler) streamGroupedLogs(w http.ResponseWriter, r *http.Request) { func (h *handler) streamStackLogs(w http.ResponseWriter, r *http.Request) { stack := chi.URLParam(r, "stack") - streamLogsForContainers(w, r, h.multiHostService, func(container *docker.Container) bool { + h.streamLogsForContainers(w, r, func(container *docker.Container) bool { return container.State == "running" && container.Labels["com.docker.stack.namespace"] == stack }) } -func streamLogsForContainers(w http.ResponseWriter, r *http.Request, multiHostClient *MultiHostService, filter ContainerFilter) { +func (h *handler) streamLogsForContainers(w http.ResponseWriter, r *http.Request, containerFilter ContainerFilter) { var stdTypes docker.StdType if r.URL.Query().Has("stdout") { stdTypes |= docker.STDOUT @@ -288,7 +288,7 @@ func streamLogsForContainers(w http.ResponseWriter, r *http.Request, multiHostCl return } - existingContainers, errs := multiHostClient.ListAllContainersFiltered(docker.ContainerFilter{}, filter) + existingContainers, errs := h.multiHostService.ListAllContainersFiltered(h.config.Filter, containerFilter) if len(errs) > 0 { log.Warn().Err(errs[0]).Msg("error while listing containers") } @@ -323,7 +323,7 @@ func streamLogsForContainers(w http.ResponseWriter, r *http.Request, multiHostCl stillRunning := false for _, container := range existingContainers { - containerService, err := multiHostClient.FindContainer(container.Host, container.ID) + containerService, err := h.multiHostService.FindContainer(container.Host, container.ID) if err != nil { log.Error().Err(err).Msg("error while finding container") @@ -370,7 +370,7 @@ func streamLogsForContainers(w http.ResponseWriter, r *http.Request, multiHostCl } streamLogs := func(container docker.Container) { - containerService, err := multiHostClient.FindContainer(container.Host, container.ID) + containerService, err := h.multiHostService.FindContainer(container.Host, container.ID) if err != nil { log.Error().Err(err).Msg("error while finding container") return @@ -392,7 +392,7 @@ func streamLogsForContainers(w http.ResponseWriter, r *http.Request, multiHostCl } newContainers := make(chan docker.Container) - multiHostClient.SubscribeContainersStarted(r.Context(), newContainers, filter) + h.multiHostService.SubscribeContainersStarted(r.Context(), newContainers, containerFilter) ticker := time.NewTicker(5 * time.Second) sseWriter.Ping()