From 37e92e8473aef714245b5c747505dbfea807426a Mon Sep 17 00:00:00 2001 From: Evstigneev Denis Date: Mon, 14 Aug 2023 14:27:29 +0300 Subject: [PATCH] add GetComments and update proto --- handler/handlers.go | 31 ++ models/mapping.go | 27 ++ proto/apidocs.swagger.yaml | 48 +++ proto/pkgdash.pb.go | 377 ++++++++++++------ proto/pkgdash.pb.validate.go | 315 ++++++++++++++- proto/pkgdash.proto | 33 +- proto/pkgdash_micro.pb.go | 2 + proto/pkgdash_micro_http.pb.go | 30 ++ storage/sqlite/queries.go | 5 + storage/sqlite/storage.go | 30 ++ storage/storage.go | 1 + storage/storage_test.go | 28 ++ ui/src/app/api/models.ts | 2 + ui/src/app/api/models/comment.ts | 9 + ui/src/app/api/models/get-comments-rsp.ts | 6 + .../api/services/pkgdash-service.service.ts | 48 +++ 16 files changed, 850 insertions(+), 142 deletions(-) create mode 100644 ui/src/app/api/models/comment.ts create mode 100644 ui/src/app/api/models/get-comments-rsp.ts diff --git a/handler/handlers.go b/handler/handlers.go index 089007c..41b7508 100644 --- a/handler/handlers.go +++ b/handler/handlers.go @@ -117,6 +117,13 @@ func (h *Handler) GetModule(ctx context.Context, req *pb.GetModuleReq, rsp *pb.G logger := h.svc.Logger() logger.Debug(ctx, "Start GetModule") + err := req.Validate() + if err != nil { + logger.Error(ctx, err) + httpsrv.SetRspCode(ctx, http.StatusBadRequest) + return httpsrv.SetError(NewValidationError(err)) + } + modules, err := h.store.GetModule(ctx, req) if err != nil { logger.Error(ctx, err) @@ -130,6 +137,30 @@ func (h *Handler) GetModule(ctx context.Context, req *pb.GetModuleReq, rsp *pb.G return nil } +func (h *Handler) GetComments(ctx context.Context, req *pb.GetCommentsReq, rsp *pb.GetCommentsRsp) error { + logger := h.svc.Logger() + logger.Debug(ctx, "Start GetModule") + + err := req.Validate() + if err != nil { + logger.Error(ctx, err) + httpsrv.SetRspCode(ctx, http.StatusBadRequest) + return httpsrv.SetError(NewValidationError(err)) + } + + comments, err := h.store.GetComment(ctx, req) + if err != nil { + logger.Error(ctx, err) + httpsrv.SetRspCode(ctx, http.StatusInternalServerError) + return httpsrv.SetError(NewInternalError(err)) + } + + rsp.Comments = comments.Decode() + + logger.Debug(ctx, "Success finish getModule") + return nil +} + func NewHandler(svc micro.Service, client cligit.Client) *Handler { h := &Handler{ svc: svc, diff --git a/models/mapping.go b/models/mapping.go index c03226b..6f1c4ba 100644 --- a/models/mapping.go +++ b/models/mapping.go @@ -1,7 +1,9 @@ package models import ( + "github.com/jackc/pgtype" pb "go.unistack.org/unistack-org/pkgdash/proto" + "time" ) type ListPackage []*Package @@ -42,3 +44,28 @@ func (l ListModule) Decode() []*pb.Module { return result } + +type ListComment []*Comment + +func (l ListComment) Decode() []*pb.Comment { + result := make([]*pb.Comment, 0, len(l)) + for i := range l { + temp := &pb.Comment{ + Id: l[i].ID, + //Package: l[i]., + Text: l[i].Text, + } + + if l[i].Created.Status == pgtype.Present { + temp.Created = l[i].Created.Time.Format(time.DateTime) + } + + if l[i].Updated.Status == pgtype.Present { + temp.Updated = l[i].Updated.Time.Format(time.DateTime) + } + + result = append(result, temp) + } + + return result +} diff --git a/proto/apidocs.swagger.yaml b/proto/apidocs.swagger.yaml index 731f048..836b89d 100644 --- a/proto/apidocs.swagger.yaml +++ b/proto/apidocs.swagger.yaml @@ -5,6 +5,32 @@ info: title: PkgdashService API version: 0.0.1 paths: + /v1/comment: + get: + tags: + - PkgdashService + operationId: GetComments + parameters: + - name: id + in: query + schema: + type: array + items: + type: integer + format: uint64 + responses: + default: + description: Default + content: + application/json: + schema: + $ref: '#/components/schemas/ErrorRsp' + "200": + description: OK + content: + application/json: + schema: + $ref: '#/components/schemas/GetCommentsRsp' /v1/module: get: tags: @@ -167,6 +193,21 @@ components: properties: status: type: string + Comment: + type: object + properties: + id: + type: integer + format: uint64 + package: + type: integer + format: uint64 + text: + type: string + created: + type: string + updated: + type: string Error: type: object properties: @@ -183,6 +224,13 @@ components: properties: error: $ref: '#/components/schemas/Error' + GetCommentsRsp: + type: object + properties: + comments: + type: array + items: + $ref: '#/components/schemas/Comment' GetModuleRsp: type: object properties: diff --git a/proto/pkgdash.pb.go b/proto/pkgdash.pb.go index 0131546..8774ce6 100644 --- a/proto/pkgdash.pb.go +++ b/proto/pkgdash.pb.go @@ -1,6 +1,6 @@ // Code generated by protoc-gen-go. DO NOT EDIT. // versions: -// protoc-gen-go v1.26.0 +// protoc-gen-go v1.31.0 // protoc v4.23.4 // source: pkgdash.proto @@ -395,8 +395,8 @@ type Comment struct { Id uint64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"` Package uint64 `protobuf:"varint,2,opt,name=package,proto3" json:"package,omitempty"` Text string `protobuf:"bytes,3,opt,name=text,proto3" json:"text,omitempty"` - Created uint64 `protobuf:"varint,4,opt,name=created,proto3" json:"created,omitempty"` - Updated uint64 `protobuf:"varint,5,opt,name=updated,proto3" json:"updated,omitempty"` + Created string `protobuf:"bytes,4,opt,name=created,proto3" json:"created,omitempty"` + Updated string `protobuf:"bytes,5,opt,name=updated,proto3" json:"updated,omitempty"` } func (x *Comment) Reset() { @@ -452,18 +452,18 @@ func (x *Comment) GetText() string { return "" } -func (x *Comment) GetCreated() uint64 { +func (x *Comment) GetCreated() string { if x != nil { return x.Created } - return 0 + return "" } -func (x *Comment) GetUpdated() uint64 { +func (x *Comment) GetUpdated() string { if x != nil { return x.Updated } - return 0 + return "" } type ListPackageReq struct { @@ -1038,6 +1038,100 @@ func (x *GetModuleRsp) GetModules() []*Module { return nil } +type GetCommentsReq struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Id []uint64 `protobuf:"varint,1,rep,packed,name=id,proto3" json:"id,omitempty"` +} + +func (x *GetCommentsReq) Reset() { + *x = GetCommentsReq{} + if protoimpl.UnsafeEnabled { + mi := &file_pkgdash_proto_msgTypes[17] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *GetCommentsReq) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*GetCommentsReq) ProtoMessage() {} + +func (x *GetCommentsReq) ProtoReflect() protoreflect.Message { + mi := &file_pkgdash_proto_msgTypes[17] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use GetCommentsReq.ProtoReflect.Descriptor instead. +func (*GetCommentsReq) Descriptor() ([]byte, []int) { + return file_pkgdash_proto_rawDescGZIP(), []int{17} +} + +func (x *GetCommentsReq) GetId() []uint64 { + if x != nil { + return x.Id + } + return nil +} + +type GetCommentsRsp struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Comments []*Comment `protobuf:"bytes,1,rep,name=comments,proto3" json:"comments,omitempty"` +} + +func (x *GetCommentsRsp) Reset() { + *x = GetCommentsRsp{} + if protoimpl.UnsafeEnabled { + mi := &file_pkgdash_proto_msgTypes[18] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *GetCommentsRsp) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*GetCommentsRsp) ProtoMessage() {} + +func (x *GetCommentsRsp) ProtoReflect() protoreflect.Message { + mi := &file_pkgdash_proto_msgTypes[18] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use GetCommentsRsp.ProtoReflect.Descriptor instead. +func (*GetCommentsRsp) Descriptor() ([]byte, []int) { + return file_pkgdash_proto_rawDescGZIP(), []int{18} +} + +func (x *GetCommentsRsp) GetComments() []*Comment { + if x != nil { + return x.Comments + } + return nil +} + var File_pkgdash_proto protoreflect.FileDescriptor var file_pkgdash_proto_rawDesc = []byte{ @@ -1090,107 +1184,121 @@ var file_pkgdash_proto_rawDesc = []byte{ 0x04, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x07, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x04, 0x52, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, - 0x73, 0x22, 0x9f, 0x01, 0x0a, 0x07, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x12, 0x17, 0x0a, + 0x73, 0x22, 0x8d, 0x01, 0x0a, 0x07, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x12, 0x17, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x02, 0x69, 0x64, 0x12, 0x21, 0x0a, 0x07, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x07, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x65, 0x78, - 0x74, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x65, 0x78, 0x74, 0x12, 0x21, 0x0a, - 0x07, 0x63, 0x72, 0x65, 0x61, 0x74, 0x65, 0x64, 0x18, 0x04, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, - 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x07, 0x63, 0x72, 0x65, 0x61, 0x74, 0x65, 0x64, - 0x12, 0x21, 0x0a, 0x07, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28, - 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x07, 0x75, 0x70, 0x64, 0x61, - 0x74, 0x65, 0x64, 0x22, 0x10, 0x0a, 0x0e, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, 0x6b, 0x61, - 0x67, 0x65, 0x52, 0x65, 0x71, 0x22, 0x3e, 0x0a, 0x0e, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, - 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, 0x12, 0x2c, 0x0a, 0x08, 0x70, 0x61, 0x63, 0x6b, 0x61, - 0x67, 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x70, 0x6b, 0x67, 0x64, - 0x61, 0x73, 0x68, 0x2e, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x08, 0x70, 0x61, 0x63, - 0x6b, 0x61, 0x67, 0x65, 0x73, 0x22, 0x95, 0x01, 0x0a, 0x10, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, - 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x12, 0x17, 0x0a, 0x02, 0x69, 0x64, - 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, - 0x02, 0x69, 0x64, 0x12, 0x1b, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, - 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, - 0x12, 0x19, 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, - 0x42, 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x12, 0x18, 0x0a, 0x07, 0x6d, - 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, 0x04, 0x52, 0x07, 0x6d, 0x6f, - 0x64, 0x75, 0x6c, 0x65, 0x73, 0x12, 0x16, 0x0a, 0x06, 0x69, 0x73, 0x73, 0x75, 0x65, 0x73, 0x18, - 0x05, 0x20, 0x03, 0x28, 0x04, 0x52, 0x06, 0x69, 0x73, 0x73, 0x75, 0x65, 0x73, 0x22, 0x2b, 0x0a, - 0x10, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, - 0x70, 0x12, 0x17, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, - 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x02, 0x69, 0x64, 0x22, 0x3b, 0x0a, 0x0a, 0x43, 0x6f, - 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x52, 0x65, 0x71, 0x12, 0x19, 0x0a, 0x03, 0x70, 0x6b, 0x67, 0x18, - 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x03, - 0x70, 0x6b, 0x67, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x65, 0x78, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x04, 0x74, 0x65, 0x78, 0x74, 0x22, 0x4a, 0x0a, 0x0d, 0x41, 0x64, 0x64, 0x43, 0x6f, - 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x52, 0x65, 0x71, 0x12, 0x25, 0x0a, 0x09, 0x69, 0x64, 0x50, 0x61, - 0x63, 0x6b, 0x61, 0x67, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, - 0x32, 0x02, 0x20, 0x00, 0x52, 0x09, 0x69, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, - 0x12, 0x0a, 0x04, 0x74, 0x65, 0x78, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, - 0x65, 0x78, 0x74, 0x22, 0x28, 0x0a, 0x0d, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, - 0x74, 0x52, 0x73, 0x70, 0x12, 0x17, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, - 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x02, 0x69, 0x64, 0x22, 0x61, 0x0a, - 0x0d, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x12, 0x1b, - 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, - 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x19, 0x0a, 0x03, 0x75, - 0x72, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x10, - 0x01, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x12, 0x18, 0x0a, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, - 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x04, 0x52, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, - 0x22, 0x30, 0x0a, 0x0d, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, - 0x70, 0x12, 0x1f, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, - 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, - 0x75, 0x73, 0x22, 0x1e, 0x0a, 0x0c, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x52, - 0x65, 0x71, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x03, 0x28, 0x04, 0x52, 0x02, - 0x69, 0x64, 0x22, 0x39, 0x0a, 0x0c, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x52, - 0x73, 0x70, 0x12, 0x29, 0x0a, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x18, 0x01, 0x20, - 0x03, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x4d, 0x6f, - 0x64, 0x75, 0x6c, 0x65, 0x52, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x32, 0xa7, 0x05, - 0x0a, 0x0e, 0x50, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, - 0x12, 0x7f, 0x0a, 0x0b, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, - 0x16, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, - 0x66, 0x2e, 0x45, 0x6d, 0x70, 0x74, 0x79, 0x1a, 0x17, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, - 0x68, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, - 0x22, 0x3f, 0xaa, 0x84, 0x9e, 0x03, 0x26, 0x2a, 0x0b, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, - 0x6b, 0x61, 0x67, 0x65, 0x42, 0x17, 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, + 0x74, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x65, 0x78, 0x74, 0x12, 0x18, 0x0a, + 0x07, 0x63, 0x72, 0x65, 0x61, 0x74, 0x65, 0x64, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, + 0x63, 0x72, 0x65, 0x61, 0x74, 0x65, 0x64, 0x12, 0x18, 0x0a, 0x07, 0x75, 0x70, 0x64, 0x61, 0x74, + 0x65, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, + 0x64, 0x22, 0x10, 0x0a, 0x0e, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, + 0x52, 0x65, 0x71, 0x22, 0x3e, 0x0a, 0x0e, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, 0x6b, 0x61, + 0x67, 0x65, 0x52, 0x73, 0x70, 0x12, 0x2c, 0x0a, 0x08, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, + 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, + 0x68, 0x2e, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x08, 0x70, 0x61, 0x63, 0x6b, 0x61, + 0x67, 0x65, 0x73, 0x22, 0x95, 0x01, 0x0a, 0x10, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x50, 0x61, + 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x12, 0x17, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, + 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x02, 0x69, + 0x64, 0x12, 0x1b, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, + 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x19, + 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, + 0x72, 0x02, 0x10, 0x01, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x12, 0x18, 0x0a, 0x07, 0x6d, 0x6f, 0x64, + 0x75, 0x6c, 0x65, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, 0x04, 0x52, 0x07, 0x6d, 0x6f, 0x64, 0x75, + 0x6c, 0x65, 0x73, 0x12, 0x16, 0x0a, 0x06, 0x69, 0x73, 0x73, 0x75, 0x65, 0x73, 0x18, 0x05, 0x20, + 0x03, 0x28, 0x04, 0x52, 0x06, 0x69, 0x73, 0x73, 0x75, 0x65, 0x73, 0x22, 0x2b, 0x0a, 0x10, 0x55, + 0x70, 0x64, 0x61, 0x74, 0x65, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, 0x12, + 0x17, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, + 0x32, 0x02, 0x20, 0x00, 0x52, 0x02, 0x69, 0x64, 0x22, 0x3b, 0x0a, 0x0a, 0x43, 0x6f, 0x6d, 0x6d, + 0x65, 0x6e, 0x74, 0x52, 0x65, 0x71, 0x12, 0x19, 0x0a, 0x03, 0x70, 0x6b, 0x67, 0x18, 0x01, 0x20, + 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x03, 0x70, 0x6b, + 0x67, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x65, 0x78, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, + 0x04, 0x74, 0x65, 0x78, 0x74, 0x22, 0x4a, 0x0a, 0x0d, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, + 0x65, 0x6e, 0x74, 0x52, 0x65, 0x71, 0x12, 0x25, 0x0a, 0x09, 0x69, 0x64, 0x50, 0x61, 0x63, 0x6b, + 0x61, 0x67, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x32, 0x02, + 0x20, 0x00, 0x52, 0x09, 0x69, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, 0x12, 0x0a, + 0x04, 0x74, 0x65, 0x78, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x65, 0x78, + 0x74, 0x22, 0x28, 0x0a, 0x0d, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x52, + 0x73, 0x70, 0x12, 0x17, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x42, 0x07, + 0xfa, 0x42, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x02, 0x69, 0x64, 0x22, 0x61, 0x0a, 0x0d, 0x41, + 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x12, 0x1b, 0x0a, 0x04, + 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, + 0x02, 0x10, 0x01, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x19, 0x0a, 0x03, 0x75, 0x72, 0x6c, + 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x42, 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, + 0x03, 0x75, 0x72, 0x6c, 0x12, 0x18, 0x0a, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x18, + 0x03, 0x20, 0x03, 0x28, 0x04, 0x52, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x22, 0x30, + 0x0a, 0x0d, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, 0x12, + 0x1f, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x42, + 0x07, 0xfa, 0x42, 0x04, 0x72, 0x02, 0x10, 0x01, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, + 0x22, 0x1e, 0x0a, 0x0c, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x52, 0x65, 0x71, + 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x03, 0x28, 0x04, 0x52, 0x02, 0x69, 0x64, + 0x22, 0x39, 0x0a, 0x0c, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x52, 0x73, 0x70, + 0x12, 0x29, 0x0a, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, + 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x4d, 0x6f, 0x64, 0x75, + 0x6c, 0x65, 0x52, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x22, 0x32, 0x0a, 0x0e, 0x47, + 0x65, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x71, 0x12, 0x20, 0x0a, + 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x03, 0x28, 0x04, 0x42, 0x10, 0xfa, 0x42, 0x0d, 0x92, 0x01, + 0x0a, 0x08, 0x01, 0x18, 0x01, 0x22, 0x04, 0x32, 0x02, 0x20, 0x00, 0x52, 0x02, 0x69, 0x64, 0x22, + 0x3e, 0x0a, 0x0e, 0x47, 0x65, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x73, + 0x70, 0x12, 0x2c, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x01, 0x20, + 0x03, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x43, 0x6f, + 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x32, + 0xa8, 0x06, 0x0a, 0x0e, 0x50, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x53, 0x65, 0x72, 0x76, 0x69, + 0x63, 0x65, 0x12, 0x7f, 0x0a, 0x0b, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, + 0x65, 0x12, 0x16, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, + 0x62, 0x75, 0x66, 0x2e, 0x45, 0x6d, 0x70, 0x74, 0x79, 0x1a, 0x17, 0x2e, 0x70, 0x6b, 0x67, 0x64, + 0x61, 0x73, 0x68, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, + 0x73, 0x70, 0x22, 0x3f, 0xaa, 0x84, 0x9e, 0x03, 0x26, 0x2a, 0x0b, 0x4c, 0x69, 0x73, 0x74, 0x50, + 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x42, 0x17, 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, + 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, + 0xea, 0xff, 0xf9, 0x01, 0x0e, 0x12, 0x0c, 0x2f, 0x76, 0x31, 0x2f, 0x70, 0x61, 0x63, 0x6b, 0x61, + 0x67, 0x65, 0x73, 0x12, 0x8c, 0x01, 0x0a, 0x0d, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x50, 0x61, + 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, 0x19, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, + 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, + 0x1a, 0x19, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x55, 0x70, 0x64, 0x61, 0x74, + 0x65, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, 0x22, 0x45, 0xaa, 0x84, 0x9e, + 0x03, 0x25, 0x2a, 0x0a, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x42, 0x17, + 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, + 0x72, 0x72, 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, 0xf9, 0x01, 0x15, 0x3a, 0x01, 0x2a, + 0x22, 0x10, 0x2f, 0x76, 0x31, 0x2f, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x2f, 0x7b, 0x69, + 0x64, 0x7d, 0x12, 0x8c, 0x01, 0x0a, 0x0a, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, + 0x74, 0x12, 0x16, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x41, 0x64, 0x64, 0x43, + 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x52, 0x65, 0x71, 0x1a, 0x16, 0x2e, 0x70, 0x6b, 0x67, 0x64, + 0x61, 0x73, 0x68, 0x2e, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x52, 0x73, + 0x70, 0x22, 0x4e, 0xaa, 0x84, 0x9e, 0x03, 0x25, 0x2a, 0x0a, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, + 0x6d, 0x65, 0x6e, 0x74, 0x42, 0x17, 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, - 0xf9, 0x01, 0x0e, 0x12, 0x0c, 0x2f, 0x76, 0x31, 0x2f, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, - 0x73, 0x12, 0x8c, 0x01, 0x0a, 0x0d, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x50, 0x61, 0x63, 0x6b, - 0x61, 0x67, 0x65, 0x12, 0x19, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x55, 0x70, - 0x64, 0x61, 0x74, 0x65, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x1a, 0x19, - 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x50, - 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, 0x22, 0x45, 0xaa, 0x84, 0x9e, 0x03, 0x25, - 0x2a, 0x0a, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x42, 0x17, 0x0a, 0x15, - 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, 0x72, 0x72, - 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, 0xf9, 0x01, 0x15, 0x22, 0x10, 0x2f, 0x76, 0x31, - 0x2f, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x2f, 0x7b, 0x69, 0x64, 0x7d, 0x3a, 0x01, 0x2a, - 0x12, 0x8c, 0x01, 0x0a, 0x0a, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x12, - 0x16, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, - 0x6d, 0x65, 0x6e, 0x74, 0x52, 0x65, 0x71, 0x1a, 0x16, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, - 0x68, 0x2e, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x52, 0x73, 0x70, 0x22, - 0x4e, 0xaa, 0x84, 0x9e, 0x03, 0x25, 0x2a, 0x0a, 0x41, 0x64, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x65, - 0x6e, 0x74, 0x42, 0x17, 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, + 0xf9, 0x01, 0x1e, 0x3a, 0x01, 0x2a, 0x22, 0x19, 0x2f, 0x76, 0x31, 0x2f, 0x70, 0x61, 0x63, 0x6b, + 0x61, 0x67, 0x65, 0x2f, 0x7b, 0x70, 0x6b, 0x67, 0x7d, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, + 0x74, 0x12, 0x7e, 0x0a, 0x0a, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, + 0x16, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, + 0x6b, 0x61, 0x67, 0x65, 0x52, 0x65, 0x71, 0x1a, 0x16, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, + 0x68, 0x2e, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, 0x22, + 0x40, 0xaa, 0x84, 0x9e, 0x03, 0x25, 0x2a, 0x0a, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, + 0x67, 0x65, 0x42, 0x17, 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, 0xf9, 0x01, - 0x1e, 0x22, 0x19, 0x2f, 0x76, 0x31, 0x2f, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x2f, 0x7b, - 0x70, 0x6b, 0x67, 0x7d, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x3a, 0x01, 0x2a, 0x12, - 0x7e, 0x0a, 0x0a, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x12, 0x16, 0x2e, - 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, - 0x67, 0x65, 0x52, 0x65, 0x71, 0x1a, 0x16, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, - 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x52, 0x73, 0x70, 0x22, 0x40, 0xaa, - 0x84, 0x9e, 0x03, 0x25, 0x2a, 0x0a, 0x41, 0x64, 0x64, 0x50, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, - 0x42, 0x17, 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, - 0x2e, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, 0xf9, 0x01, 0x10, 0x22, - 0x0b, 0x2f, 0x76, 0x31, 0x2f, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, 0x65, 0x3a, 0x01, 0x2a, 0x12, - 0x76, 0x0a, 0x09, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x12, 0x15, 0x2e, 0x70, - 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, - 0x52, 0x65, 0x71, 0x1a, 0x15, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x47, 0x65, - 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x52, 0x73, 0x70, 0x22, 0x3b, 0xaa, 0x84, 0x9e, 0x03, - 0x24, 0x2a, 0x09, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x42, 0x17, 0x0a, 0x15, - 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, 0x72, 0x72, - 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, 0xf9, 0x01, 0x0c, 0x12, 0x0a, 0x2f, 0x76, 0x31, - 0x2f, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x42, 0x36, 0x5a, 0x34, 0x67, 0x6f, 0x2e, 0x75, 0x6e, - 0x69, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x75, 0x6e, 0x69, 0x73, 0x74, - 0x61, 0x63, 0x6b, 0x2d, 0x6f, 0x72, 0x67, 0x2f, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2f, - 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x3b, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x70, 0x62, 0x62, - 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x10, 0x3a, 0x01, 0x2a, 0x22, 0x0b, 0x2f, 0x76, 0x31, 0x2f, 0x70, 0x61, 0x63, 0x6b, 0x61, 0x67, + 0x65, 0x12, 0x76, 0x0a, 0x09, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x12, 0x15, + 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, + 0x6c, 0x65, 0x52, 0x65, 0x71, 0x1a, 0x15, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, + 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x52, 0x73, 0x70, 0x22, 0x3b, 0xaa, 0x84, + 0x9e, 0x03, 0x24, 0x2a, 0x09, 0x47, 0x65, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x42, 0x17, + 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, + 0x72, 0x72, 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, 0xf9, 0x01, 0x0c, 0x12, 0x0a, 0x2f, + 0x76, 0x31, 0x2f, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x12, 0x7f, 0x0a, 0x0b, 0x47, 0x65, 0x74, + 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x17, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, + 0x73, 0x68, 0x2e, 0x47, 0x65, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, + 0x71, 0x1a, 0x17, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x47, 0x65, 0x74, 0x43, + 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x73, 0x70, 0x22, 0x3e, 0xaa, 0x84, 0x9e, 0x03, + 0x26, 0x2a, 0x0b, 0x47, 0x65, 0x74, 0x43, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x42, 0x17, + 0x0a, 0x15, 0x12, 0x13, 0x0a, 0x11, 0x2e, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, 0x2e, 0x45, + 0x72, 0x72, 0x6f, 0x72, 0x52, 0x73, 0x70, 0xb2, 0xea, 0xff, 0xf9, 0x01, 0x0d, 0x12, 0x0b, 0x2f, + 0x76, 0x31, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x65, 0x6e, 0x74, 0x42, 0x36, 0x5a, 0x34, 0x67, 0x6f, + 0x2e, 0x75, 0x6e, 0x69, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x75, 0x6e, + 0x69, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x2d, 0x6f, 0x72, 0x67, 0x2f, 0x70, 0x6b, 0x67, 0x64, 0x61, + 0x73, 0x68, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x3b, 0x70, 0x6b, 0x67, 0x64, 0x61, 0x73, 0x68, + 0x70, 0x62, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, } var ( @@ -1205,7 +1313,7 @@ func file_pkgdash_proto_rawDescGZIP() []byte { return file_pkgdash_proto_rawDescData } -var file_pkgdash_proto_msgTypes = make([]protoimpl.MessageInfo, 17) +var file_pkgdash_proto_msgTypes = make([]protoimpl.MessageInfo, 19) var file_pkgdash_proto_goTypes = []interface{}{ (*ErrorRsp)(nil), // 0: pkgdash.ErrorRsp (*Error)(nil), // 1: pkgdash.Error @@ -1224,27 +1332,32 @@ var file_pkgdash_proto_goTypes = []interface{}{ (*AddPackageRsp)(nil), // 14: pkgdash.AddPackageRsp (*GetModuleReq)(nil), // 15: pkgdash.GetModuleReq (*GetModuleRsp)(nil), // 16: pkgdash.GetModuleRsp - (*emptypb.Empty)(nil), // 17: google.protobuf.Empty + (*GetCommentsReq)(nil), // 17: pkgdash.GetCommentsReq + (*GetCommentsRsp)(nil), // 18: pkgdash.GetCommentsRsp + (*emptypb.Empty)(nil), // 19: google.protobuf.Empty } var file_pkgdash_proto_depIdxs = []int32{ 1, // 0: pkgdash.ErrorRsp.error:type_name -> pkgdash.Error 2, // 1: pkgdash.ListPackageRsp.packages:type_name -> pkgdash.Package 3, // 2: pkgdash.GetModuleRsp.modules:type_name -> pkgdash.Module - 17, // 3: pkgdash.PkgdashService.ListPackage:input_type -> google.protobuf.Empty - 8, // 4: pkgdash.PkgdashService.UpdatePackage:input_type -> pkgdash.UpdatePackageReq - 11, // 5: pkgdash.PkgdashService.AddComment:input_type -> pkgdash.AddCommentReq - 13, // 6: pkgdash.PkgdashService.AddPackage:input_type -> pkgdash.AddPackageReq - 15, // 7: pkgdash.PkgdashService.GetModule:input_type -> pkgdash.GetModuleReq - 7, // 8: pkgdash.PkgdashService.ListPackage:output_type -> pkgdash.ListPackageRsp - 9, // 9: pkgdash.PkgdashService.UpdatePackage:output_type -> pkgdash.UpdatePackageRsp - 12, // 10: pkgdash.PkgdashService.AddComment:output_type -> pkgdash.AddCommentRsp - 14, // 11: pkgdash.PkgdashService.AddPackage:output_type -> pkgdash.AddPackageRsp - 16, // 12: pkgdash.PkgdashService.GetModule:output_type -> pkgdash.GetModuleRsp - 8, // [8:13] is the sub-list for method output_type - 3, // [3:8] is the sub-list for method input_type - 3, // [3:3] is the sub-list for extension type_name - 3, // [3:3] is the sub-list for extension extendee - 0, // [0:3] is the sub-list for field type_name + 5, // 3: pkgdash.GetCommentsRsp.comments:type_name -> pkgdash.Comment + 19, // 4: pkgdash.PkgdashService.ListPackage:input_type -> google.protobuf.Empty + 8, // 5: pkgdash.PkgdashService.UpdatePackage:input_type -> pkgdash.UpdatePackageReq + 11, // 6: pkgdash.PkgdashService.AddComment:input_type -> pkgdash.AddCommentReq + 13, // 7: pkgdash.PkgdashService.AddPackage:input_type -> pkgdash.AddPackageReq + 15, // 8: pkgdash.PkgdashService.GetModule:input_type -> pkgdash.GetModuleReq + 17, // 9: pkgdash.PkgdashService.GetComments:input_type -> pkgdash.GetCommentsReq + 7, // 10: pkgdash.PkgdashService.ListPackage:output_type -> pkgdash.ListPackageRsp + 9, // 11: pkgdash.PkgdashService.UpdatePackage:output_type -> pkgdash.UpdatePackageRsp + 12, // 12: pkgdash.PkgdashService.AddComment:output_type -> pkgdash.AddCommentRsp + 14, // 13: pkgdash.PkgdashService.AddPackage:output_type -> pkgdash.AddPackageRsp + 16, // 14: pkgdash.PkgdashService.GetModule:output_type -> pkgdash.GetModuleRsp + 18, // 15: pkgdash.PkgdashService.GetComments:output_type -> pkgdash.GetCommentsRsp + 10, // [10:16] is the sub-list for method output_type + 4, // [4:10] is the sub-list for method input_type + 4, // [4:4] is the sub-list for extension type_name + 4, // [4:4] is the sub-list for extension extendee + 0, // [0:4] is the sub-list for field type_name } func init() { file_pkgdash_proto_init() } @@ -1457,6 +1570,30 @@ func file_pkgdash_proto_init() { return nil } } + file_pkgdash_proto_msgTypes[17].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*GetCommentsReq); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_pkgdash_proto_msgTypes[18].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*GetCommentsRsp); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } } type x struct{} out := protoimpl.TypeBuilder{ @@ -1464,7 +1601,7 @@ func file_pkgdash_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: file_pkgdash_proto_rawDesc, NumEnums: 0, - NumMessages: 17, + NumMessages: 19, NumExtensions: 0, NumServices: 1, }, diff --git a/proto/pkgdash.pb.validate.go b/proto/pkgdash.pb.validate.go index 1345d7b..0aeea39 100644 --- a/proto/pkgdash.pb.validate.go +++ b/proto/pkgdash.pb.validate.go @@ -89,6 +89,7 @@ func (m *ErrorRsp) validate(all bool) error { if len(errors) > 0 { return ErrorRspMultiError(errors) } + return nil } @@ -194,6 +195,7 @@ func (m *Error) validate(all bool) error { if len(errors) > 0 { return ErrorMultiError(errors) } + return nil } @@ -324,6 +326,7 @@ func (m *Package) validate(all bool) error { if len(errors) > 0 { return PackageMultiError(errors) } + return nil } @@ -476,6 +479,7 @@ func (m *Module) validate(all bool) error { if len(errors) > 0 { return ModuleMultiError(errors) } + return nil } @@ -617,6 +621,7 @@ func (m *Issue) validate(all bool) error { if len(errors) > 0 { return IssueMultiError(errors) } + return nil } @@ -735,31 +740,14 @@ func (m *Comment) validate(all bool) error { // no validation rules for Text - if m.GetCreated() <= 0 { - err := CommentValidationError{ - field: "Created", - reason: "value must be greater than 0", - } - if !all { - return err - } - errors = append(errors, err) - } + // no validation rules for Created - if m.GetUpdated() <= 0 { - err := CommentValidationError{ - field: "Updated", - reason: "value must be greater than 0", - } - if !all { - return err - } - errors = append(errors, err) - } + // no validation rules for Updated if len(errors) > 0 { return CommentMultiError(errors) } + return nil } @@ -858,6 +846,7 @@ func (m *ListPackageReq) validate(all bool) error { if len(errors) > 0 { return ListPackageReqMultiError(errors) } + return nil } @@ -991,6 +980,7 @@ func (m *ListPackageRsp) validate(all bool) error { if len(errors) > 0 { return ListPackageRspMultiError(errors) } + return nil } @@ -1123,6 +1113,7 @@ func (m *UpdatePackageReq) validate(all bool) error { if len(errors) > 0 { return UpdatePackageReqMultiError(errors) } + return nil } @@ -1233,6 +1224,7 @@ func (m *UpdatePackageRsp) validate(all bool) error { if len(errors) > 0 { return UpdatePackageRspMultiError(errors) } + return nil } @@ -1345,6 +1337,7 @@ func (m *CommentReq) validate(all bool) error { if len(errors) > 0 { return CommentReqMultiError(errors) } + return nil } @@ -1456,6 +1449,7 @@ func (m *AddCommentReq) validate(all bool) error { if len(errors) > 0 { return AddCommentReqMultiError(errors) } + return nil } @@ -1566,6 +1560,7 @@ func (m *AddCommentRsp) validate(all bool) error { if len(errors) > 0 { return AddCommentRspMultiError(errors) } + return nil } @@ -1687,6 +1682,7 @@ func (m *AddPackageReq) validate(all bool) error { if len(errors) > 0 { return AddPackageReqMultiError(errors) } + return nil } @@ -1797,6 +1793,7 @@ func (m *AddPackageRsp) validate(all bool) error { if len(errors) > 0 { return AddPackageRspMultiError(errors) } + return nil } @@ -1896,6 +1893,7 @@ func (m *GetModuleReq) validate(all bool) error { if len(errors) > 0 { return GetModuleReqMultiError(errors) } + return nil } @@ -2028,6 +2026,7 @@ func (m *GetModuleRsp) validate(all bool) error { if len(errors) > 0 { return GetModuleRspMultiError(errors) } + return nil } @@ -2100,3 +2099,279 @@ var _ interface { Cause() error ErrorName() string } = GetModuleRspValidationError{} + +// Validate checks the field values on GetCommentsReq with the rules defined in +// the proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *GetCommentsReq) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on GetCommentsReq with the rules defined +// in the proto definition for this message. If any rules are violated, the +// result is a list of violation errors wrapped in GetCommentsReqMultiError, +// or nil if none found. +func (m *GetCommentsReq) ValidateAll() error { + return m.validate(true) +} + +func (m *GetCommentsReq) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + if len(m.GetId()) < 1 { + err := GetCommentsReqValidationError{ + field: "Id", + reason: "value must contain at least 1 item(s)", + } + if !all { + return err + } + errors = append(errors, err) + } + + _GetCommentsReq_Id_Unique := make(map[uint64]struct{}, len(m.GetId())) + + for idx, item := range m.GetId() { + _, _ = idx, item + + if _, exists := _GetCommentsReq_Id_Unique[item]; exists { + err := GetCommentsReqValidationError{ + field: fmt.Sprintf("Id[%v]", idx), + reason: "repeated value must contain unique items", + } + if !all { + return err + } + errors = append(errors, err) + } else { + _GetCommentsReq_Id_Unique[item] = struct{}{} + } + + if item <= 0 { + err := GetCommentsReqValidationError{ + field: fmt.Sprintf("Id[%v]", idx), + reason: "value must be greater than 0", + } + if !all { + return err + } + errors = append(errors, err) + } + + } + + if len(errors) > 0 { + return GetCommentsReqMultiError(errors) + } + + return nil +} + +// GetCommentsReqMultiError is an error wrapping multiple validation errors +// returned by GetCommentsReq.ValidateAll() if the designated constraints +// aren't met. +type GetCommentsReqMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m GetCommentsReqMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m GetCommentsReqMultiError) AllErrors() []error { return m } + +// GetCommentsReqValidationError is the validation error returned by +// GetCommentsReq.Validate if the designated constraints aren't met. +type GetCommentsReqValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e GetCommentsReqValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e GetCommentsReqValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e GetCommentsReqValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e GetCommentsReqValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e GetCommentsReqValidationError) ErrorName() string { return "GetCommentsReqValidationError" } + +// Error satisfies the builtin error interface +func (e GetCommentsReqValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sGetCommentsReq.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = GetCommentsReqValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = GetCommentsReqValidationError{} + +// Validate checks the field values on GetCommentsRsp with the rules defined in +// the proto definition for this message. If any rules are violated, the first +// error encountered is returned, or nil if there are no violations. +func (m *GetCommentsRsp) Validate() error { + return m.validate(false) +} + +// ValidateAll checks the field values on GetCommentsRsp with the rules defined +// in the proto definition for this message. If any rules are violated, the +// result is a list of violation errors wrapped in GetCommentsRspMultiError, +// or nil if none found. +func (m *GetCommentsRsp) ValidateAll() error { + return m.validate(true) +} + +func (m *GetCommentsRsp) validate(all bool) error { + if m == nil { + return nil + } + + var errors []error + + for idx, item := range m.GetComments() { + _, _ = idx, item + + if all { + switch v := interface{}(item).(type) { + case interface{ ValidateAll() error }: + if err := v.ValidateAll(); err != nil { + errors = append(errors, GetCommentsRspValidationError{ + field: fmt.Sprintf("Comments[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + case interface{ Validate() error }: + if err := v.Validate(); err != nil { + errors = append(errors, GetCommentsRspValidationError{ + field: fmt.Sprintf("Comments[%v]", idx), + reason: "embedded message failed validation", + cause: err, + }) + } + } + } else if v, ok := interface{}(item).(interface{ Validate() error }); ok { + if err := v.Validate(); err != nil { + return GetCommentsRspValidationError{ + field: fmt.Sprintf("Comments[%v]", idx), + reason: "embedded message failed validation", + cause: err, + } + } + } + + } + + if len(errors) > 0 { + return GetCommentsRspMultiError(errors) + } + + return nil +} + +// GetCommentsRspMultiError is an error wrapping multiple validation errors +// returned by GetCommentsRsp.ValidateAll() if the designated constraints +// aren't met. +type GetCommentsRspMultiError []error + +// Error returns a concatenation of all the error messages it wraps. +func (m GetCommentsRspMultiError) Error() string { + var msgs []string + for _, err := range m { + msgs = append(msgs, err.Error()) + } + return strings.Join(msgs, "; ") +} + +// AllErrors returns a list of validation violation errors. +func (m GetCommentsRspMultiError) AllErrors() []error { return m } + +// GetCommentsRspValidationError is the validation error returned by +// GetCommentsRsp.Validate if the designated constraints aren't met. +type GetCommentsRspValidationError struct { + field string + reason string + cause error + key bool +} + +// Field function returns field value. +func (e GetCommentsRspValidationError) Field() string { return e.field } + +// Reason function returns reason value. +func (e GetCommentsRspValidationError) Reason() string { return e.reason } + +// Cause function returns cause value. +func (e GetCommentsRspValidationError) Cause() error { return e.cause } + +// Key function returns key value. +func (e GetCommentsRspValidationError) Key() bool { return e.key } + +// ErrorName returns error name. +func (e GetCommentsRspValidationError) ErrorName() string { return "GetCommentsRspValidationError" } + +// Error satisfies the builtin error interface +func (e GetCommentsRspValidationError) Error() string { + cause := "" + if e.cause != nil { + cause = fmt.Sprintf(" | caused by: %v", e.cause) + } + + key := "" + if e.key { + key = "key for " + } + + return fmt.Sprintf( + "invalid %sGetCommentsRsp.%s: %s%s", + key, + e.field, + e.reason, + cause) +} + +var _ error = GetCommentsRspValidationError{} + +var _ interface { + Field() string + Reason() string + Key() bool + Cause() error + ErrorName() string +} = GetCommentsRspValidationError{} diff --git a/proto/pkgdash.proto b/proto/pkgdash.proto index 6210d82..a38d012 100644 --- a/proto/pkgdash.proto +++ b/proto/pkgdash.proto @@ -78,6 +78,19 @@ service PkgdashService { get: "/v1/module"; }; }; + rpc GetComments(GetCommentsReq) returns (GetCommentsRsp) { + option (micro.openapiv3.openapiv3_operation) = { + operation_id: "GetComments"; + responses: { + default: { + reference: {_ref: ".pkgdash.ErrorRsp"}; + }; + }; + }; + option (micro.api.http) = { + get: "/v1/comment"; + }; + } }; message ErrorRsp { @@ -120,8 +133,8 @@ message Comment { uint64 id = 1 [(validate.rules).uint64.gt = 0]; uint64 package = 2 [(validate.rules).uint64.gt = 0]; string text = 3; - uint64 created = 4 [(validate.rules).uint64.gt = 0]; - uint64 updated = 5 [(validate.rules).uint64.gt = 0]; + string created = 4 ; + string updated = 5 ; } message ListPackageReq {} @@ -169,4 +182,20 @@ message GetModuleReq { } message GetModuleRsp { repeated Module modules = 1 ; +} + +message GetCommentsReq { + repeated uint64 id = 1 [(validate.rules).repeated = { + unique: true + min_items: 1 + items: { + uint64: { + gt: 0 + } + } + }] ; +} + +message GetCommentsRsp { + repeated Comment comments = 1; } \ No newline at end of file diff --git a/proto/pkgdash_micro.pb.go b/proto/pkgdash_micro.pb.go index dcd41a1..2ac1918 100644 --- a/proto/pkgdash_micro.pb.go +++ b/proto/pkgdash_micro.pb.go @@ -23,6 +23,7 @@ type PkgdashServiceClient interface { AddComment(ctx context.Context, req *AddCommentReq, opts ...options.Option) (*AddCommentRsp, error) AddPackage(ctx context.Context, req *AddPackageReq, opts ...options.Option) (*AddPackageRsp, error) GetModule(ctx context.Context, req *GetModuleReq, opts ...options.Option) (*GetModuleRsp, error) + GetComments(ctx context.Context, req *GetCommentsReq, opts ...options.Option) (*GetCommentsRsp, error) } type PkgdashServiceServer interface { @@ -31,4 +32,5 @@ type PkgdashServiceServer interface { AddComment(ctx context.Context, req *AddCommentReq, rsp *AddCommentRsp) error AddPackage(ctx context.Context, req *AddPackageReq, rsp *AddPackageRsp) error GetModule(ctx context.Context, req *GetModuleReq, rsp *GetModuleRsp) error + GetComments(ctx context.Context, req *GetCommentsReq, rsp *GetCommentsRsp) error } diff --git a/proto/pkgdash_micro_http.pb.go b/proto/pkgdash_micro_http.pb.go index e4b2ff0..1aec5dd 100644 --- a/proto/pkgdash_micro_http.pb.go +++ b/proto/pkgdash_micro_http.pb.go @@ -52,6 +52,13 @@ var ( Body: "", Stream: false, }, + { + Name: "PkgdashService.GetComments", + Path: "/v1/comment", + Method: "GET", + Body: "", + Stream: false, + }, } ) @@ -157,6 +164,24 @@ func (c *pkgdashServiceClient) GetModule(ctx context.Context, req *GetModuleReq, return rsp, nil } +func (c *pkgdashServiceClient) GetComments(ctx context.Context, req *GetCommentsReq, opts ...options.Option) (*GetCommentsRsp, error) { + errmap := make(map[string]interface{}, 1) + errmap["default"] = &ErrorRsp{} + opts = append(opts, + v41.ErrorMap(errmap), + ) + opts = append(opts, + v41.Method(http.MethodGet), + v41.Path("/v1/comment"), + ) + rsp := &GetCommentsRsp{} + err := c.c.Call(ctx, c.c.NewRequest(c.name, "PkgdashService.GetComments", req), rsp, opts...) + if err != nil { + return nil, err + } + return rsp, nil +} + type pkgdashServiceServer struct { PkgdashServiceServer } @@ -181,6 +206,10 @@ func (h *pkgdashServiceServer) GetModule(ctx context.Context, req *GetModuleReq, return h.PkgdashServiceServer.GetModule(ctx, req, rsp) } +func (h *pkgdashServiceServer) GetComments(ctx context.Context, req *GetCommentsReq, rsp *GetCommentsRsp) error { + return h.PkgdashServiceServer.GetComments(ctx, req, rsp) +} + func RegisterPkgdashServiceServer(s server.Server, sh PkgdashServiceServer, opts ...options.Option) error { type pkgdashService interface { ListPackage(ctx context.Context, req *emptypb.Empty, rsp *ListPackageRsp) error @@ -188,6 +217,7 @@ func RegisterPkgdashServiceServer(s server.Server, sh PkgdashServiceServer, opts AddComment(ctx context.Context, req *AddCommentReq, rsp *AddCommentRsp) error AddPackage(ctx context.Context, req *AddPackageReq, rsp *AddPackageRsp) error GetModule(ctx context.Context, req *GetModuleReq, rsp *GetModuleRsp) error + GetComments(ctx context.Context, req *GetCommentsReq, rsp *GetCommentsRsp) error } type PkgdashService struct { pkgdashService diff --git a/storage/sqlite/queries.go b/storage/sqlite/queries.go index 917e23c..5efffd2 100644 --- a/storage/sqlite/queries.go +++ b/storage/sqlite/queries.go @@ -28,5 +28,10 @@ returning id; queryGetModule = ` select id, name, version, last_version from module where id in %s ; +` + + queryGetComments = ` +select id, text, created, updated from comment +where id in %s ; ` ) diff --git a/storage/sqlite/storage.go b/storage/sqlite/storage.go index ac38ee2..0d0e9d4 100644 --- a/storage/sqlite/storage.go +++ b/storage/sqlite/storage.go @@ -249,6 +249,36 @@ func (s *Sqlite) GetModule(ctx context.Context, req *pb.GetModuleReq) (result mo return result, err } +func (s *Sqlite) GetComment(ctx context.Context, req *pb.GetCommentsReq) (result models.ListComment, err error) { + query := fmt.Sprintf(queryGetComments, generateArrayIneq(len(req.Id))) + + rows, err := s.db.QueryContext(ctx, query, convertSliceUInt(req.Id...)...) + if err != nil { + return nil, err + } + defer func() { + if err = rows.Close(); err != nil { + return + } + err = rows.Err() + }() + for rows.Next() { + tmp := &models.Comment{} + if err = rows.Scan( + &tmp.ID, + &tmp.Text, + &tmp.Created, + &tmp.Updated, + ); err != nil { + return nil, err + } + + result = append(result, tmp) + } + + return result, err +} + func convertSliceUInt(arg ...uint64) []interface{} { result := make([]interface{}, 0, len(arg)) for i := range arg { diff --git a/storage/storage.go b/storage/storage.go index a79012a..5f165bd 100644 --- a/storage/storage.go +++ b/storage/storage.go @@ -42,6 +42,7 @@ type Storage interface { AddPackage(ctx context.Context, req *pb.AddPackageReq) error InsertButchModules(ctx context.Context, req []models.Module) ([]uint64, error) GetModule(ctx context.Context, req *pb.GetModuleReq) (models.ListModule, error) + GetComment(ctx context.Context, req *pb.GetCommentsReq) (models.ListComment, error) } func NewStorage(name string, db *sql.DB) (Storage, error) { diff --git a/storage/storage_test.go b/storage/storage_test.go index 65510d1..826b23a 100644 --- a/storage/storage_test.go +++ b/storage/storage_test.go @@ -38,3 +38,31 @@ func TestGetModule(t *testing.T) { fmt.Println(module) } + +func TestGetComment(t *testing.T) { + conn, err := sql.Open("sqlite3", "/Users/devstigneev_local/GolandProjects/unistack/pkgdash/identifier.sqlite") + if err != nil { + t.Fatal(err) + } + defer conn.Close() + if err = conn.Ping(); err != nil { + t.Fatal(err) + } + + st := sqlite.NewStorage() + store := st(conn, fs) + + s, ok := store.(Storage) + if !ok { + t.Fatal("dont implements interface Storage") + } + + req := &pb.GetCommentsReq{ + Id: []uint64{1, 2, 3, 15}, + } + comments, err := s.GetComment(context.Background(), req) + if err != nil { + t.Fatal(err) + } + fmt.Println(comments.Decode()) +} diff --git a/ui/src/app/api/models.ts b/ui/src/app/api/models.ts index b71b264..8ba8ba5 100644 --- a/ui/src/app/api/models.ts +++ b/ui/src/app/api/models.ts @@ -4,8 +4,10 @@ export { AddCommentReq } from './models/add-comment-req'; export { AddCommentRsp } from './models/add-comment-rsp'; export { AddPackageReq } from './models/add-package-req'; export { AddPackageRsp } from './models/add-package-rsp'; +export { Comment } from './models/comment'; export { Error } from './models/error'; export { ErrorRsp } from './models/error-rsp'; +export { GetCommentsRsp } from './models/get-comments-rsp'; export { GetModuleRsp } from './models/get-module-rsp'; export { ListPackageRsp } from './models/list-package-rsp'; export { Module } from './models/module'; diff --git a/ui/src/app/api/models/comment.ts b/ui/src/app/api/models/comment.ts new file mode 100644 index 0000000..bbf3a61 --- /dev/null +++ b/ui/src/app/api/models/comment.ts @@ -0,0 +1,9 @@ +/* tslint:disable */ +/* eslint-disable */ +export interface Comment { + created?: string; + id?: number; + package?: number; + text?: string; + updated?: string; +} diff --git a/ui/src/app/api/models/get-comments-rsp.ts b/ui/src/app/api/models/get-comments-rsp.ts new file mode 100644 index 0000000..3f54e4a --- /dev/null +++ b/ui/src/app/api/models/get-comments-rsp.ts @@ -0,0 +1,6 @@ +/* tslint:disable */ +/* eslint-disable */ +import { Comment } from './comment'; +export interface GetCommentsRsp { + comments?: Array; +} diff --git a/ui/src/app/api/services/pkgdash-service.service.ts b/ui/src/app/api/services/pkgdash-service.service.ts index b1b99c8..cd0815f 100644 --- a/ui/src/app/api/services/pkgdash-service.service.ts +++ b/ui/src/app/api/services/pkgdash-service.service.ts @@ -14,6 +14,7 @@ import { AddCommentReq } from '../models/add-comment-req'; import { AddCommentRsp } from '../models/add-comment-rsp'; import { AddPackageReq } from '../models/add-package-req'; import { AddPackageRsp } from '../models/add-package-rsp'; +import { GetCommentsRsp } from '../models/get-comments-rsp'; import { GetModuleRsp } from '../models/get-module-rsp'; import { ListPackageRsp } from '../models/list-package-rsp'; import { UpdatePackageReq } from '../models/update-package-req'; @@ -25,6 +26,53 @@ export class PkgdashServiceService extends BaseService { super(config, http); } + /** Path part for operation `getComments()` */ + static readonly GetCommentsPath = '/v1/comment'; + + /** + * This method provides access to the full `HttpResponse`, allowing access to response headers. + * To access only the response body, use `getComments()` instead. + * + * This method doesn't expect any request body. + */ + getComments$Response( + params?: { + id?: Array; + }, + context?: HttpContext + ): Observable> { + const rb = new RequestBuilder(this.rootUrl, PkgdashServiceService.GetCommentsPath, 'get'); + if (params) { + rb.query('id', params.id, {}); + } + + return this.http.request( + rb.build({ responseType: 'json', accept: 'application/json', context }) + ).pipe( + filter((r: any): r is HttpResponse => r instanceof HttpResponse), + map((r: HttpResponse) => { + return r as StrictHttpResponse; + }) + ); + } + + /** + * This method provides access only to the response body. + * To access the full response (for headers, for example), `getComments$Response()` instead. + * + * This method doesn't expect any request body. + */ + getComments( + params?: { + id?: Array; + }, + context?: HttpContext + ): Observable { + return this.getComments$Response(params, context).pipe( + map((r: StrictHttpResponse): GetCommentsRsp => r.body) + ); + } + /** Path part for operation `getModule()` */ static readonly GetModulePath = '/v1/module';