From a19bca60704b4fbb674cf51d828580aa653c8210 Mon Sep 17 00:00:00 2001 From: Tulsishah <46474643+Tulsishah@users.noreply.github.com> Date: Wed, 11 Jan 2023 21:54:39 +0530 Subject: [PATCH] feat(storage): add ComponentCount as part of ObjectAttrs (#7230) * adding component count attribute in objectAttrs and related unit test and integration test * formating the file * formating the file * fixing integration test for compose method * fixing comments - rephrasing component count descriotion, adding got and want in integration test * removing extra line * fixing presubmit issues * fixing comments- ComponentCount to component_count Co-authored-by: Chris Cotter --- storage/integration_test.go | 12 ++++++++++-- storage/storage.go | 9 +++++++++ storage/storage_test.go | 4 ++++ 3 files changed, 23 insertions(+), 2 deletions(-) diff --git a/storage/integration_test.go b/storage/integration_test.go index eb5b27557d20..b851fecbcafb 100644 --- a/storage/integration_test.go +++ b/storage/integration_test.go @@ -1659,18 +1659,26 @@ func TestIntegration_Compose(t *testing.T) { // Compose should work even if the user sets no destination attributes. compDst := b.Object("composed1") c := compDst.ComposerFrom(compSrcs...) - if _, err := c.Run(ctx); err != nil { + attrs, err := c.Run(ctx) + if err != nil { t.Fatalf("ComposeFrom error: %v", err) } + if attrs.ComponentCount != int64(len(objects)) { + t.Errorf("mismatching ComponentCount: got %v, want %v", attrs.ComponentCount, int64(len(objects))) + } checkCompose(compDst, "application/octet-stream") // It should also work if we do. compDst = b.Object("composed2") c = compDst.ComposerFrom(compSrcs...) c.ContentType = "text/json" - if _, err := c.Run(ctx); err != nil { + attrs, err = c.Run(ctx) + if err != nil { t.Fatalf("ComposeFrom error: %v", err) } + if attrs.ComponentCount != int64(len(objects)) { + t.Errorf("mismatching ComponentCount: got %v, want %v", attrs.ComponentCount, int64(len(objects))) + } checkCompose(compDst, "text/json") }) } diff --git a/storage/storage.go b/storage/storage.go index c4a771593249..7fc3fc4cb9b3 100644 --- a/storage/storage.go +++ b/storage/storage.go @@ -1315,6 +1315,11 @@ type ObjectAttrs struct { // later value but not to an earlier one. For more information see // https://cloud.google.com/storage/docs/metadata#custom-time . CustomTime time.Time + + // ComponentCount is the number of objects contained within a composite object. + // For non-composite objects, the value will be zero. + // This field is read-only. + ComponentCount int64 } // convertTime converts a time in RFC3339 format to time.Time. @@ -1385,6 +1390,7 @@ func newObject(o *raw.Object) *ObjectAttrs { Updated: convertTime(o.Updated), Etag: o.Etag, CustomTime: convertTime(o.CustomTime), + ComponentCount: o.ComponentCount, } } @@ -1419,6 +1425,7 @@ func newObjectFromProto(o *storagepb.Object) *ObjectAttrs { Deleted: convertProtoTime(o.GetDeleteTime()), Updated: convertProtoTime(o.GetUpdateTime()), CustomTime: convertProtoTime(o.GetCustomTime()), + ComponentCount: int64(o.ComponentCount), } } @@ -1547,6 +1554,7 @@ var attrToFieldMap = map[string]string{ "Updated": "updated", "Etag": "etag", "CustomTime": "customTime", + "ComponentCount": "componentCount", } // attrToProtoFieldMap maps the field names of ObjectAttrs to the underlying field @@ -1578,6 +1586,7 @@ var attrToProtoFieldMap = map[string]string{ "Owner": "owner", "CustomerKeySHA256": "customer_encryption", "CustomTime": "custom_time", + "ComponentCount": "component_count", // MediaLink was explicitly excluded from the proto as it is an HTTP-ism. // "MediaLink": "mediaLink", } diff --git a/storage/storage_test.go b/storage/storage_test.go index 30cf209db50f..0414e0de0e7e 100644 --- a/storage/storage_test.go +++ b/storage/storage_test.go @@ -1747,6 +1747,7 @@ func TestRawObjectToObjectAttrs(t *testing.T) { TimeCreated: "2019-03-31T19:32:10Z", TimeDeleted: "2019-03-31T19:33:39Z", TemporaryHold: true, + ComponentCount: 2, }, want: &ObjectAttrs{ Bucket: "Test", @@ -1763,6 +1764,7 @@ func TestRawObjectToObjectAttrs(t *testing.T) { RetentionExpirationTime: time.Date(2019, 3, 31, 19, 33, 36, 0, time.UTC), Size: 1 << 20, TemporaryHold: true, + ComponentCount: 2, }, }, } @@ -1833,6 +1835,7 @@ func TestProtoObjectToObjectAttrs(t *testing.T) { CreateTime: timestamppb.New(now), DeleteTime: timestamppb.New(now), TemporaryHold: true, + ComponentCount: 2, }, want: &ObjectAttrs{ Bucket: "Test", @@ -1848,6 +1851,7 @@ func TestProtoObjectToObjectAttrs(t *testing.T) { RetentionExpirationTime: now, Size: 1 << 20, TemporaryHold: true, + ComponentCount: 2, }, }, }