1
2
3
4
5
6
7
8
9
10
11
12
13
14
15 package storage
16
17 import (
18 "crypto/md5"
19 "hash/crc32"
20 "math/rand"
21 "testing"
22 "time"
23
24 "cloud.google.com/go/storage/internal/apiv2/storagepb"
25 "github.com/google/go-cmp/cmp"
26 "google.golang.org/protobuf/proto"
27 "google.golang.org/protobuf/testing/protocmp"
28 )
29
30 func TestBytesCodec(t *testing.T) {
31
32 content := make([]byte, 1<<10+1)
33 rand.New(rand.NewSource(0)).Read(content)
34
35
36 crc32c := crc32.Checksum(content, crc32.MakeTable(crc32.Castagnoli))
37 hasher := md5.New()
38 if _, err := hasher.Write(content); err != nil {
39 t.Errorf("hasher.Write: %v", err)
40 }
41 md5 := hasher.Sum(nil)
42
43 trueBool := true
44 metadata := &storagepb.Object{
45 Name: "object-name",
46 Bucket: "bucket-name",
47 Etag: "etag",
48 Generation: 100,
49 Metageneration: 907,
50 StorageClass: "Standard",
51 Size: 1025,
52 ContentEncoding: "none",
53 ContentDisposition: "inline",
54 CacheControl: "public, max-age=3600",
55 Acl: []*storagepb.ObjectAccessControl{{
56 Role: "role",
57 Id: "id",
58 Entity: "allUsers",
59 Etag: "tag",
60 Email: "email@foo.com",
61 }},
62 ContentLanguage: "mi, en",
63 DeleteTime: toProtoTimestamp(time.Now()),
64 ContentType: "application/octet-stream",
65 CreateTime: toProtoTimestamp(time.Now()),
66 ComponentCount: 1,
67 Checksums: &storagepb.ObjectChecksums{
68 Crc32C: &crc32c,
69 Md5Hash: md5,
70 },
71 TemporaryHold: true,
72 Metadata: map[string]string{
73 "a-key": "a-value",
74 },
75 EventBasedHold: &trueBool,
76 Owner: &storagepb.Owner{
77 Entity: "user-1",
78 EntityId: "1",
79 },
80 CustomerEncryption: &storagepb.CustomerEncryption{
81 EncryptionAlgorithm: "alg",
82 KeySha256Bytes: []byte("bytes"),
83 },
84 HardDeleteTime: toProtoTimestamp(time.Now()),
85 }
86
87 for _, test := range []struct {
88 desc string
89 resp *storagepb.ReadObjectResponse
90 }{
91 {
92 desc: "filled object response",
93 resp: &storagepb.ReadObjectResponse{
94 ChecksummedData: &storagepb.ChecksummedData{
95 Content: content,
96 Crc32C: &crc32c,
97 },
98 ObjectChecksums: &storagepb.ObjectChecksums{
99 Crc32C: &crc32c,
100 Md5Hash: md5,
101 },
102 ContentRange: &storagepb.ContentRange{
103 Start: 0,
104 End: 1025,
105 CompleteLength: 1025,
106 },
107 Metadata: metadata,
108 },
109 },
110 {
111 desc: "empty object response",
112 resp: &storagepb.ReadObjectResponse{},
113 },
114 {
115 desc: "partially empty",
116 resp: &storagepb.ReadObjectResponse{
117 ChecksummedData: &storagepb.ChecksummedData{},
118 ObjectChecksums: &storagepb.ObjectChecksums{Md5Hash: md5},
119 Metadata: &storagepb.Object{},
120 },
121 },
122 } {
123 t.Run(test.desc, func(t *testing.T) {
124
125 encodedResp, err := proto.Marshal(test.resp)
126 if err != nil {
127 t.Fatalf("proto.Marshal: %v", err)
128 }
129
130
131 encodedBytes := &[]byte{}
132 if err := bytesCodec.Unmarshal(bytesCodec{}, encodedResp, encodedBytes); err != nil {
133 t.Fatalf("unmarshal: %v", err)
134 }
135
136 got, err := readFullObjectResponse(*encodedBytes)
137 if err != nil {
138 t.Fatalf("readFullObjectResponse: %v", err)
139 }
140
141
142 if diff := cmp.Diff(got, test.resp, protocmp.Transform()); diff != "" {
143 t.Errorf("cmp.Diff got(-),want(+):\n%s", diff)
144 }
145 })
146 }
147 }
148
View as plain text