From 0007a403fae32eae778f295d6d81ba6c811c2177 Mon Sep 17 00:00:00 2001 From: Michael Street <5597260+MStreet3@users.noreply.github.com> Date: Fri, 20 Sep 2024 12:11:53 -0400 Subject: [PATCH] feat(values): adds support for time.Time as value --- pkg/values/pb/values.go | 13 ++ pkg/values/pb/values.pb.go | 329 +++++++++++++++++++++++-------------- pkg/values/pb/values.proto | 17 +- pkg/values/time.go | 41 +++++ pkg/values/time_test.go | 88 ++++++++++ pkg/values/value.go | 2 + pkg/values/value_test.go | 16 ++ 7 files changed, 377 insertions(+), 129 deletions(-) create mode 100644 pkg/values/time.go create mode 100644 pkg/values/time_test.go diff --git a/pkg/values/pb/values.go b/pkg/values/pb/values.go index 59755cfa8e..fe3f2d642d 100644 --- a/pkg/values/pb/values.go +++ b/pkg/values/pb/values.go @@ -1,7 +1,10 @@ package pb import ( + "time" + "github.com/shopspring/decimal" + "google.golang.org/protobuf/types/known/timestamppb" ) func NewBoolValue(b bool) *Value { @@ -80,3 +83,13 @@ func NewBigIntValue(sign int, bib []byte) *Value { }, } } + +func NewTime(t time.Time) *Value { + return &Value{ + Value: &Value_TimeValue{ + TimeValue: &Time{ + Time: timestamppb.New(t), + }, + }, + } +} diff --git a/pkg/values/pb/values.pb.go b/pkg/values/pb/values.pb.go index 5db8a5a263..10eb6bf68f 100644 --- a/pkg/values/pb/values.pb.go +++ b/pkg/values/pb/values.pb.go @@ -1,14 +1,15 @@ // Code generated by protoc-gen-go. DO NOT EDIT. // versions: // protoc-gen-go v1.31.0 -// protoc v4.25.1 -// source: values/pb/values.proto +// protoc v5.27.3 +// source: values.proto package pb import ( protoreflect "google.golang.org/protobuf/reflect/protoreflect" protoimpl "google.golang.org/protobuf/runtime/protoimpl" + timestamppb "google.golang.org/protobuf/types/known/timestamppb" reflect "reflect" sync "sync" ) @@ -35,13 +36,14 @@ type Value struct { // *Value_DecimalValue // *Value_Int64Value // *Value_BigintValue + // *Value_TimeValue Value isValue_Value `protobuf_oneof:"value"` } func (x *Value) Reset() { *x = Value{} if protoimpl.UnsafeEnabled { - mi := &file_values_pb_values_proto_msgTypes[0] + mi := &file_values_proto_msgTypes[0] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -54,7 +56,7 @@ func (x *Value) String() string { func (*Value) ProtoMessage() {} func (x *Value) ProtoReflect() protoreflect.Message { - mi := &file_values_pb_values_proto_msgTypes[0] + mi := &file_values_proto_msgTypes[0] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -67,7 +69,7 @@ func (x *Value) ProtoReflect() protoreflect.Message { // Deprecated: Use Value.ProtoReflect.Descriptor instead. func (*Value) Descriptor() ([]byte, []int) { - return file_values_pb_values_proto_rawDescGZIP(), []int{0} + return file_values_proto_rawDescGZIP(), []int{0} } func (m *Value) GetValue() isValue_Value { @@ -133,6 +135,13 @@ func (x *Value) GetBigintValue() *BigInt { return nil } +func (x *Value) GetTimeValue() *Time { + if x, ok := x.GetValue().(*Value_TimeValue); ok { + return x.TimeValue + } + return nil +} + type isValue_Value interface { isValue_Value() } @@ -169,6 +178,10 @@ type Value_BigintValue struct { BigintValue *BigInt `protobuf:"bytes,9,opt,name=bigint_value,json=bigintValue,proto3,oneof"` } +type Value_TimeValue struct { + TimeValue *Time `protobuf:"bytes,10,opt,name=time_value,json=timeValue,proto3,oneof"` +} + func (*Value_StringValue) isValue_Value() {} func (*Value_BoolValue) isValue_Value() {} @@ -185,6 +198,8 @@ func (*Value_Int64Value) isValue_Value() {} func (*Value_BigintValue) isValue_Value() {} +func (*Value_TimeValue) isValue_Value() {} + type BigInt struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache @@ -197,7 +212,7 @@ type BigInt struct { func (x *BigInt) Reset() { *x = BigInt{} if protoimpl.UnsafeEnabled { - mi := &file_values_pb_values_proto_msgTypes[1] + mi := &file_values_proto_msgTypes[1] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -210,7 +225,7 @@ func (x *BigInt) String() string { func (*BigInt) ProtoMessage() {} func (x *BigInt) ProtoReflect() protoreflect.Message { - mi := &file_values_pb_values_proto_msgTypes[1] + mi := &file_values_proto_msgTypes[1] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -223,7 +238,7 @@ func (x *BigInt) ProtoReflect() protoreflect.Message { // Deprecated: Use BigInt.ProtoReflect.Descriptor instead. func (*BigInt) Descriptor() ([]byte, []int) { - return file_values_pb_values_proto_rawDescGZIP(), []int{1} + return file_values_proto_rawDescGZIP(), []int{1} } func (x *BigInt) GetAbsVal() []byte { @@ -251,7 +266,7 @@ type Map struct { func (x *Map) Reset() { *x = Map{} if protoimpl.UnsafeEnabled { - mi := &file_values_pb_values_proto_msgTypes[2] + mi := &file_values_proto_msgTypes[2] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -264,7 +279,7 @@ func (x *Map) String() string { func (*Map) ProtoMessage() {} func (x *Map) ProtoReflect() protoreflect.Message { - mi := &file_values_pb_values_proto_msgTypes[2] + mi := &file_values_proto_msgTypes[2] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -277,7 +292,7 @@ func (x *Map) ProtoReflect() protoreflect.Message { // Deprecated: Use Map.ProtoReflect.Descriptor instead. func (*Map) Descriptor() ([]byte, []int) { - return file_values_pb_values_proto_rawDescGZIP(), []int{2} + return file_values_proto_rawDescGZIP(), []int{2} } func (x *Map) GetFields() map[string]*Value { @@ -298,7 +313,7 @@ type List struct { func (x *List) Reset() { *x = List{} if protoimpl.UnsafeEnabled { - mi := &file_values_pb_values_proto_msgTypes[3] + mi := &file_values_proto_msgTypes[3] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -311,7 +326,7 @@ func (x *List) String() string { func (*List) ProtoMessage() {} func (x *List) ProtoReflect() protoreflect.Message { - mi := &file_values_pb_values_proto_msgTypes[3] + mi := &file_values_proto_msgTypes[3] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -324,7 +339,7 @@ func (x *List) ProtoReflect() protoreflect.Message { // Deprecated: Use List.ProtoReflect.Descriptor instead. func (*List) Descriptor() ([]byte, []int) { - return file_values_pb_values_proto_rawDescGZIP(), []int{3} + return file_values_proto_rawDescGZIP(), []int{3} } func (x *List) GetFields() []*Value { @@ -346,7 +361,7 @@ type Decimal struct { func (x *Decimal) Reset() { *x = Decimal{} if protoimpl.UnsafeEnabled { - mi := &file_values_pb_values_proto_msgTypes[4] + mi := &file_values_proto_msgTypes[4] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -359,7 +374,7 @@ func (x *Decimal) String() string { func (*Decimal) ProtoMessage() {} func (x *Decimal) ProtoReflect() protoreflect.Message { - mi := &file_values_pb_values_proto_msgTypes[4] + mi := &file_values_proto_msgTypes[4] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -372,7 +387,7 @@ func (x *Decimal) ProtoReflect() protoreflect.Message { // Deprecated: Use Decimal.ProtoReflect.Descriptor instead. func (*Decimal) Descriptor() ([]byte, []int) { - return file_values_pb_values_proto_rawDescGZIP(), []int{4} + return file_values_proto_rawDescGZIP(), []int{4} } func (x *Decimal) GetCoefficient() *BigInt { @@ -389,105 +404,164 @@ func (x *Decimal) GetExponent() int32 { return 0 } -var File_values_pb_values_proto protoreflect.FileDescriptor - -var file_values_pb_values_proto_rawDesc = []byte{ - 0x0a, 0x16, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2f, 0x70, 0x62, 0x2f, 0x76, 0x61, 0x6c, 0x75, - 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x06, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, - 0x22, 0xea, 0x02, 0x0a, 0x05, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x73, 0x74, - 0x72, 0x69, 0x6e, 0x67, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, - 0x48, 0x00, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, - 0x1f, 0x0a, 0x0a, 0x62, 0x6f, 0x6f, 0x6c, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, - 0x01, 0x28, 0x08, 0x48, 0x00, 0x52, 0x09, 0x62, 0x6f, 0x6f, 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, - 0x12, 0x21, 0x0a, 0x0b, 0x62, 0x79, 0x74, 0x65, 0x73, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, - 0x03, 0x20, 0x01, 0x28, 0x0c, 0x48, 0x00, 0x52, 0x0a, 0x62, 0x79, 0x74, 0x65, 0x73, 0x56, 0x61, - 0x6c, 0x75, 0x65, 0x12, 0x2a, 0x0a, 0x09, 0x6d, 0x61, 0x70, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, - 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0b, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, - 0x4d, 0x61, 0x70, 0x48, 0x00, 0x52, 0x08, 0x6d, 0x61, 0x70, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, - 0x2d, 0x0a, 0x0a, 0x6c, 0x69, 0x73, 0x74, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x05, 0x20, - 0x01, 0x28, 0x0b, 0x32, 0x0c, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x4c, 0x69, 0x73, - 0x74, 0x48, 0x00, 0x52, 0x09, 0x6c, 0x69, 0x73, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x36, - 0x0a, 0x0d, 0x64, 0x65, 0x63, 0x69, 0x6d, 0x61, 0x6c, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, - 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x44, - 0x65, 0x63, 0x69, 0x6d, 0x61, 0x6c, 0x48, 0x00, 0x52, 0x0c, 0x64, 0x65, 0x63, 0x69, 0x6d, 0x61, - 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x21, 0x0a, 0x0b, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x5f, - 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x07, 0x20, 0x01, 0x28, 0x03, 0x48, 0x00, 0x52, 0x0a, 0x69, - 0x6e, 0x74, 0x36, 0x34, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x33, 0x0a, 0x0c, 0x62, 0x69, 0x67, - 0x69, 0x6e, 0x74, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x09, 0x20, 0x01, 0x28, 0x0b, 0x32, - 0x0e, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x42, 0x69, 0x67, 0x49, 0x6e, 0x74, 0x48, - 0x00, 0x52, 0x0b, 0x62, 0x69, 0x67, 0x69, 0x6e, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x42, 0x07, - 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x4a, 0x04, 0x08, 0x08, 0x10, 0x09, 0x22, 0x35, 0x0a, - 0x06, 0x42, 0x69, 0x67, 0x49, 0x6e, 0x74, 0x12, 0x17, 0x0a, 0x07, 0x61, 0x62, 0x73, 0x5f, 0x76, - 0x61, 0x6c, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x06, 0x61, 0x62, 0x73, 0x56, 0x61, 0x6c, - 0x12, 0x12, 0x0a, 0x04, 0x73, 0x69, 0x67, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x03, 0x52, 0x04, - 0x73, 0x69, 0x67, 0x6e, 0x22, 0x80, 0x01, 0x0a, 0x03, 0x4d, 0x61, 0x70, 0x12, 0x2f, 0x0a, 0x06, - 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x76, - 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x4d, 0x61, 0x70, 0x2e, 0x46, 0x69, 0x65, 0x6c, 0x64, 0x73, - 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x06, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x1a, 0x48, 0x0a, - 0x0b, 0x46, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, - 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x23, - 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0d, 0x2e, - 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52, 0x05, 0x76, 0x61, - 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x2d, 0x0a, 0x04, 0x4c, 0x69, 0x73, 0x74, 0x12, - 0x25, 0x0a, 0x06, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, - 0x0d, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52, 0x06, - 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x22, 0x57, 0x0a, 0x07, 0x44, 0x65, 0x63, 0x69, 0x6d, 0x61, - 0x6c, 0x12, 0x30, 0x0a, 0x0b, 0x63, 0x6f, 0x65, 0x66, 0x66, 0x69, 0x63, 0x69, 0x65, 0x6e, 0x74, - 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, - 0x42, 0x69, 0x67, 0x49, 0x6e, 0x74, 0x52, 0x0b, 0x63, 0x6f, 0x65, 0x66, 0x66, 0x69, 0x63, 0x69, - 0x65, 0x6e, 0x74, 0x12, 0x1a, 0x0a, 0x08, 0x65, 0x78, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x18, - 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x65, 0x78, 0x70, 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x42, - 0x3c, 0x5a, 0x3a, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x73, 0x6d, - 0x61, 0x72, 0x74, 0x63, 0x6f, 0x6e, 0x74, 0x72, 0x61, 0x63, 0x74, 0x6b, 0x69, 0x74, 0x2f, 0x63, - 0x68, 0x61, 0x69, 0x6e, 0x6c, 0x69, 0x6e, 0x6b, 0x2d, 0x63, 0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2f, - 0x70, 0x6b, 0x67, 0x2f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2f, 0x70, 0x62, 0x62, 0x06, 0x70, - 0x72, 0x6f, 0x74, 0x6f, 0x33, +type Time struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Time *timestamppb.Timestamp `protobuf:"bytes,1,opt,name=time,proto3" json:"time,omitempty"` +} + +func (x *Time) Reset() { + *x = Time{} + if protoimpl.UnsafeEnabled { + mi := &file_values_proto_msgTypes[5] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *Time) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*Time) ProtoMessage() {} + +func (x *Time) ProtoReflect() protoreflect.Message { + mi := &file_values_proto_msgTypes[5] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use Time.ProtoReflect.Descriptor instead. +func (*Time) Descriptor() ([]byte, []int) { + return file_values_proto_rawDescGZIP(), []int{5} +} + +func (x *Time) GetTime() *timestamppb.Timestamp { + if x != nil { + return x.Time + } + return nil +} + +var File_values_proto protoreflect.FileDescriptor + +var file_values_proto_rawDesc = []byte{ + 0x0a, 0x0c, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x06, + 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 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, 0x99, 0x03, 0x0a, 0x05, 0x56, 0x61, 0x6c, 0x75, + 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x5f, 0x76, 0x61, 0x6c, 0x75, + 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x69, 0x6e, + 0x67, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x1f, 0x0a, 0x0a, 0x62, 0x6f, 0x6f, 0x6c, 0x5f, 0x76, + 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x08, 0x48, 0x00, 0x52, 0x09, 0x62, 0x6f, + 0x6f, 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x21, 0x0a, 0x0b, 0x62, 0x79, 0x74, 0x65, 0x73, + 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0c, 0x48, 0x00, 0x52, 0x0a, + 0x62, 0x79, 0x74, 0x65, 0x73, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x2a, 0x0a, 0x09, 0x6d, 0x61, + 0x70, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0b, 0x2e, + 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x4d, 0x61, 0x70, 0x48, 0x00, 0x52, 0x08, 0x6d, 0x61, + 0x70, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x2d, 0x0a, 0x0a, 0x6c, 0x69, 0x73, 0x74, 0x5f, 0x76, + 0x61, 0x6c, 0x75, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0c, 0x2e, 0x76, 0x61, 0x6c, + 0x75, 0x65, 0x73, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x48, 0x00, 0x52, 0x09, 0x6c, 0x69, 0x73, 0x74, + 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x36, 0x0a, 0x0d, 0x64, 0x65, 0x63, 0x69, 0x6d, 0x61, 0x6c, + 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x76, + 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x44, 0x65, 0x63, 0x69, 0x6d, 0x61, 0x6c, 0x48, 0x00, 0x52, + 0x0c, 0x64, 0x65, 0x63, 0x69, 0x6d, 0x61, 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x21, 0x0a, + 0x0b, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x07, 0x20, 0x01, + 0x28, 0x03, 0x48, 0x00, 0x52, 0x0a, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x56, 0x61, 0x6c, 0x75, 0x65, + 0x12, 0x33, 0x0a, 0x0c, 0x62, 0x69, 0x67, 0x69, 0x6e, 0x74, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, + 0x18, 0x09, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, + 0x42, 0x69, 0x67, 0x49, 0x6e, 0x74, 0x48, 0x00, 0x52, 0x0b, 0x62, 0x69, 0x67, 0x69, 0x6e, 0x74, + 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x2d, 0x0a, 0x0a, 0x74, 0x69, 0x6d, 0x65, 0x5f, 0x76, 0x61, + 0x6c, 0x75, 0x65, 0x18, 0x0a, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0c, 0x2e, 0x76, 0x61, 0x6c, 0x75, + 0x65, 0x73, 0x2e, 0x54, 0x69, 0x6d, 0x65, 0x48, 0x00, 0x52, 0x09, 0x74, 0x69, 0x6d, 0x65, 0x56, + 0x61, 0x6c, 0x75, 0x65, 0x42, 0x07, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x4a, 0x04, 0x08, + 0x08, 0x10, 0x09, 0x22, 0x35, 0x0a, 0x06, 0x42, 0x69, 0x67, 0x49, 0x6e, 0x74, 0x12, 0x17, 0x0a, + 0x07, 0x61, 0x62, 0x73, 0x5f, 0x76, 0x61, 0x6c, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x06, + 0x61, 0x62, 0x73, 0x56, 0x61, 0x6c, 0x12, 0x12, 0x0a, 0x04, 0x73, 0x69, 0x67, 0x6e, 0x18, 0x02, + 0x20, 0x01, 0x28, 0x03, 0x52, 0x04, 0x73, 0x69, 0x67, 0x6e, 0x22, 0x80, 0x01, 0x0a, 0x03, 0x4d, + 0x61, 0x70, 0x12, 0x2f, 0x0a, 0x06, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x18, 0x01, 0x20, 0x03, + 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x4d, 0x61, 0x70, 0x2e, + 0x46, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x06, 0x66, 0x69, 0x65, + 0x6c, 0x64, 0x73, 0x1a, 0x48, 0x0a, 0x0b, 0x46, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x45, 0x6e, 0x74, + 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, + 0x03, 0x6b, 0x65, 0x79, 0x12, 0x23, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, + 0x01, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x56, 0x61, 0x6c, + 0x75, 0x65, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x2d, 0x0a, + 0x04, 0x4c, 0x69, 0x73, 0x74, 0x12, 0x25, 0x0a, 0x06, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x18, + 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x56, + 0x61, 0x6c, 0x75, 0x65, 0x52, 0x06, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x22, 0x57, 0x0a, 0x07, + 0x44, 0x65, 0x63, 0x69, 0x6d, 0x61, 0x6c, 0x12, 0x30, 0x0a, 0x0b, 0x63, 0x6f, 0x65, 0x66, 0x66, + 0x69, 0x63, 0x69, 0x65, 0x6e, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0e, 0x2e, 0x76, + 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2e, 0x42, 0x69, 0x67, 0x49, 0x6e, 0x74, 0x52, 0x0b, 0x63, 0x6f, + 0x65, 0x66, 0x66, 0x69, 0x63, 0x69, 0x65, 0x6e, 0x74, 0x12, 0x1a, 0x0a, 0x08, 0x65, 0x78, 0x70, + 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x65, 0x78, 0x70, + 0x6f, 0x6e, 0x65, 0x6e, 0x74, 0x22, 0x36, 0x0a, 0x04, 0x54, 0x69, 0x6d, 0x65, 0x12, 0x2e, 0x0a, + 0x04, 0x74, 0x69, 0x6d, 0x65, 0x18, 0x01, 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, 0x04, 0x74, 0x69, 0x6d, 0x65, 0x42, 0x3c, 0x5a, + 0x3a, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x73, 0x6d, 0x61, 0x72, + 0x74, 0x63, 0x6f, 0x6e, 0x74, 0x72, 0x61, 0x63, 0x74, 0x6b, 0x69, 0x74, 0x2f, 0x63, 0x68, 0x61, + 0x69, 0x6e, 0x6c, 0x69, 0x6e, 0x6b, 0x2d, 0x63, 0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2f, 0x70, 0x6b, + 0x67, 0x2f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2f, 0x70, 0x62, 0x62, 0x06, 0x70, 0x72, 0x6f, + 0x74, 0x6f, 0x33, } var ( - file_values_pb_values_proto_rawDescOnce sync.Once - file_values_pb_values_proto_rawDescData = file_values_pb_values_proto_rawDesc + file_values_proto_rawDescOnce sync.Once + file_values_proto_rawDescData = file_values_proto_rawDesc ) -func file_values_pb_values_proto_rawDescGZIP() []byte { - file_values_pb_values_proto_rawDescOnce.Do(func() { - file_values_pb_values_proto_rawDescData = protoimpl.X.CompressGZIP(file_values_pb_values_proto_rawDescData) +func file_values_proto_rawDescGZIP() []byte { + file_values_proto_rawDescOnce.Do(func() { + file_values_proto_rawDescData = protoimpl.X.CompressGZIP(file_values_proto_rawDescData) }) - return file_values_pb_values_proto_rawDescData -} - -var file_values_pb_values_proto_msgTypes = make([]protoimpl.MessageInfo, 6) -var file_values_pb_values_proto_goTypes = []interface{}{ - (*Value)(nil), // 0: values.Value - (*BigInt)(nil), // 1: values.BigInt - (*Map)(nil), // 2: values.Map - (*List)(nil), // 3: values.List - (*Decimal)(nil), // 4: values.Decimal - nil, // 5: values.Map.FieldsEntry -} -var file_values_pb_values_proto_depIdxs = []int32{ - 2, // 0: values.Value.map_value:type_name -> values.Map - 3, // 1: values.Value.list_value:type_name -> values.List - 4, // 2: values.Value.decimal_value:type_name -> values.Decimal - 1, // 3: values.Value.bigint_value:type_name -> values.BigInt - 5, // 4: values.Map.fields:type_name -> values.Map.FieldsEntry - 0, // 5: values.List.fields:type_name -> values.Value - 1, // 6: values.Decimal.coefficient:type_name -> values.BigInt - 0, // 7: values.Map.FieldsEntry.value:type_name -> values.Value - 8, // [8:8] is the sub-list for method output_type - 8, // [8:8] is the sub-list for method input_type - 8, // [8:8] is the sub-list for extension type_name - 8, // [8:8] is the sub-list for extension extendee - 0, // [0:8] is the sub-list for field type_name -} - -func init() { file_values_pb_values_proto_init() } -func file_values_pb_values_proto_init() { - if File_values_pb_values_proto != nil { + return file_values_proto_rawDescData +} + +var file_values_proto_msgTypes = make([]protoimpl.MessageInfo, 7) +var file_values_proto_goTypes = []interface{}{ + (*Value)(nil), // 0: values.Value + (*BigInt)(nil), // 1: values.BigInt + (*Map)(nil), // 2: values.Map + (*List)(nil), // 3: values.List + (*Decimal)(nil), // 4: values.Decimal + (*Time)(nil), // 5: values.Time + nil, // 6: values.Map.FieldsEntry + (*timestamppb.Timestamp)(nil), // 7: google.protobuf.Timestamp +} +var file_values_proto_depIdxs = []int32{ + 2, // 0: values.Value.map_value:type_name -> values.Map + 3, // 1: values.Value.list_value:type_name -> values.List + 4, // 2: values.Value.decimal_value:type_name -> values.Decimal + 1, // 3: values.Value.bigint_value:type_name -> values.BigInt + 5, // 4: values.Value.time_value:type_name -> values.Time + 6, // 5: values.Map.fields:type_name -> values.Map.FieldsEntry + 0, // 6: values.List.fields:type_name -> values.Value + 1, // 7: values.Decimal.coefficient:type_name -> values.BigInt + 7, // 8: values.Time.time:type_name -> google.protobuf.Timestamp + 0, // 9: values.Map.FieldsEntry.value:type_name -> values.Value + 10, // [10:10] is the sub-list for method output_type + 10, // [10:10] is the sub-list for method input_type + 10, // [10:10] is the sub-list for extension type_name + 10, // [10:10] is the sub-list for extension extendee + 0, // [0:10] is the sub-list for field type_name +} + +func init() { file_values_proto_init() } +func file_values_proto_init() { + if File_values_proto != nil { return } if !protoimpl.UnsafeEnabled { - file_values_pb_values_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} { + file_values_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} { switch v := v.(*Value); i { case 0: return &v.state @@ -499,7 +573,7 @@ func file_values_pb_values_proto_init() { return nil } } - file_values_pb_values_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} { + file_values_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} { switch v := v.(*BigInt); i { case 0: return &v.state @@ -511,7 +585,7 @@ func file_values_pb_values_proto_init() { return nil } } - file_values_pb_values_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} { + file_values_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} { switch v := v.(*Map); i { case 0: return &v.state @@ -523,7 +597,7 @@ func file_values_pb_values_proto_init() { return nil } } - file_values_pb_values_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} { + file_values_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} { switch v := v.(*List); i { case 0: return &v.state @@ -535,7 +609,7 @@ func file_values_pb_values_proto_init() { return nil } } - file_values_pb_values_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} { + file_values_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} { switch v := v.(*Decimal); i { case 0: return &v.state @@ -547,8 +621,20 @@ func file_values_pb_values_proto_init() { return nil } } + file_values_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} { + switch v := v.(*Time); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } } - file_values_pb_values_proto_msgTypes[0].OneofWrappers = []interface{}{ + file_values_proto_msgTypes[0].OneofWrappers = []interface{}{ (*Value_StringValue)(nil), (*Value_BoolValue)(nil), (*Value_BytesValue)(nil), @@ -557,23 +643,24 @@ func file_values_pb_values_proto_init() { (*Value_DecimalValue)(nil), (*Value_Int64Value)(nil), (*Value_BigintValue)(nil), + (*Value_TimeValue)(nil), } type x struct{} out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_values_pb_values_proto_rawDesc, + RawDescriptor: file_values_proto_rawDesc, NumEnums: 0, - NumMessages: 6, + NumMessages: 7, NumExtensions: 0, NumServices: 0, }, - GoTypes: file_values_pb_values_proto_goTypes, - DependencyIndexes: file_values_pb_values_proto_depIdxs, - MessageInfos: file_values_pb_values_proto_msgTypes, + GoTypes: file_values_proto_goTypes, + DependencyIndexes: file_values_proto_depIdxs, + MessageInfos: file_values_proto_msgTypes, }.Build() - File_values_pb_values_proto = out.File - file_values_pb_values_proto_rawDesc = nil - file_values_pb_values_proto_goTypes = nil - file_values_pb_values_proto_depIdxs = nil + File_values_proto = out.File + file_values_proto_rawDesc = nil + file_values_proto_goTypes = nil + file_values_proto_depIdxs = nil } diff --git a/pkg/values/pb/values.proto b/pkg/values/pb/values.proto index 7eb3e65a47..b21372f09b 100644 --- a/pkg/values/pb/values.proto +++ b/pkg/values/pb/values.proto @@ -1,5 +1,7 @@ syntax = "proto3"; +import "google/protobuf/timestamp.proto"; + option go_package = "github.com/smartcontractkit/chainlink-common/pkg/values/pb"; package values; @@ -15,23 +17,22 @@ message Value { Decimal decimal_value = 6; int64 int64_value = 7; BigInt bigint_value = 9; + Time time_value = 10; } } message BigInt { - bytes abs_val = 1; - int64 sign = 2; + bytes abs_val = 1; + int64 sign = 2; } -message Map { - map fields = 1; -} +message Map { map fields = 1; } -message List { - repeated Value fields = 2; -} +message List { repeated Value fields = 2; } message Decimal { BigInt coefficient = 1; int32 exponent = 2; } + +message Time { google.protobuf.Timestamp time = 1; } diff --git a/pkg/values/time.go b/pkg/values/time.go new file mode 100644 index 0000000000..7280021a8f --- /dev/null +++ b/pkg/values/time.go @@ -0,0 +1,41 @@ +package values + +import ( + "errors" + "time" + + "github.com/smartcontractkit/chainlink-common/pkg/values/pb" +) + +type Time struct { + Underlying time.Time +} + +func NewTime(t time.Time) *Time { + return &Time{Underlying: t} +} + +func (t *Time) UnwrapTo(to any) error { + if t == nil { + return errors.New("could not unwrap nil values.Time") + } + + return unwrapTo(t.Underlying, to) +} + +func (t *Time) Unwrap() (any, error) { + tt := new(time.Time) + return *tt, t.UnwrapTo(tt) +} + +func (t *Time) copy() Value { + if t == nil { + return nil + } + + return NewTime(t.Underlying) +} + +func (t *Time) proto() *pb.Value { + return pb.NewTime(t.Underlying) +} diff --git a/pkg/values/time_test.go b/pkg/values/time_test.go new file mode 100644 index 0000000000..0c642c165c --- /dev/null +++ b/pkg/values/time_test.go @@ -0,0 +1,88 @@ +package values + +import ( + "testing" + "time" + + "github.com/stretchr/testify/assert" +) + +func Test_TimeUnwrapTo(t *testing.T) { + expected, err := time.Parse(time.RFC3339, "2006-01-02T15:04:05Z") + assert.NoError(t, err) + + // Unwraps to a time.Time pointer + v := NewTime(expected) + got := new(time.Time) + err = v.UnwrapTo(got) + assert.NoError(t, err) + assert.Equal(t, expected, *got) + + // Fails to unwrap to nil time.Time pointer + gotTime := (*time.Time)(nil) + err = v.UnwrapTo(gotTime) + assert.Error(t, err) + assert.ErrorContains(t, err, "cannot unwrap to nil pointer") + + // Unwraps to an any pointer + var varAny any + err = v.UnwrapTo(&varAny) + assert.NoError(t, err) + assert.Equal(t, expected, varAny) + + // Fails to unwrap to a string pointer + var varStr string + err = v.UnwrapTo(&varStr) + assert.Error(t, err) + assert.ErrorContains(t, err, "cannot unwrap to value of type: *string") + + // Fails to unwrap nil value of Time + nilVal := (*Time)(nil) + _, err = nilVal.Unwrap() + assert.Error(t, err) + assert.ErrorContains(t, err, "could not unwrap nil") + + // Unwraps zero value of Time + zeroTime := &Time{} + unwrapped, err := zeroTime.Unwrap() + assert.NoError(t, err) + assert.Equal(t, time.Time{}, unwrapped) + + // Unwraps an alias + type aliasTime time.Time + alias := aliasTime(time.Time{}) + err = v.UnwrapTo(&alias) + assert.NoError(t, err) +} + +// Test_Time tests that Time values can be converted to and from protobuf representations. +func Test_Time(t *testing.T) { + testCases := []struct { + name string + t time.Time + }{ + { + name: "zero", + t: time.Time{}, + }, + { + name: "some time", + t: func() time.Time { + someTime, err := time.Parse(time.RFC3339, "2006-01-02T15:04:05Z") + assert.NoError(t, err) + return someTime + }(), + }, + } + + for _, tc := range testCases { + t.Run(tc.name, func(t *testing.T) { + v := NewTime(tc.t) + + vp := Proto(v) + got, err := FromProto(vp) + assert.NoError(t, err) + assert.Equal(t, tc.t, got.(*Time).Underlying) + }) + } +} diff --git a/pkg/values/value.go b/pkg/values/value.go index a4a23cc3bd..7b27665b64 100644 --- a/pkg/values/value.go +++ b/pkg/values/value.go @@ -184,6 +184,8 @@ func FromProto(val *pb.Value) (Value, error) { return FromMapValueProto(val.GetMapValue()) case *pb.Value_BigintValue: return fromBigIntValueProto(val.GetBigintValue()), nil + case *pb.Value_TimeValue: + return NewTime(val.GetTimeValue().Time.AsTime()), nil } return nil, fmt.Errorf("unsupported type %T: %+v", val, val) diff --git a/pkg/values/value_test.go b/pkg/values/value_test.go index affd34406a..a6774274a2 100644 --- a/pkg/values/value_test.go +++ b/pkg/values/value_test.go @@ -4,6 +4,7 @@ import ( "math" "math/big" "testing" + "time" "github.com/go-viper/mapstructure/v2" "github.com/shopspring/decimal" @@ -100,6 +101,14 @@ func Test_Value(t *testing.T) { return b, bv, nil }, }, + { + name: "time", + newValue: func() (any, Value, error) { + t, err := time.Parse(time.RFC3339, "2006-01-02T15:04:05Z") + tv := NewTime(t) + return t, tv, err + }, + }, { name: "recursive map", newValue: func() (any, Value, error) { @@ -343,6 +352,9 @@ func Test_Copy(t *testing.T) { { value: mp, }, + { + value: NewTime(time.Time{}), + }, { value: (*String)(nil), isNil: true, @@ -371,6 +383,10 @@ func Test_Copy(t *testing.T) { value: (*Map)(nil), isNil: true, }, + { + value: (*Time)(nil), + isNil: true, + }, } for _, tc := range tcs {