Skip to content

Commit

Permalink
chore(storage): add proto converters for metadata
Browse files Browse the repository at this point in the history
  • Loading branch information
noahdietz committed Aug 19, 2021
1 parent f3b8217 commit b83994e
Show file tree
Hide file tree
Showing 2 changed files with 128 additions and 0 deletions.
50 changes: 50 additions & 0 deletions storage/acl.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import (
"cloud.google.com/go/internal/trace"
"google.golang.org/api/googleapi"
raw "google.golang.org/api/storage/v1"
storagepb "google.golang.org/genproto/googleapis/storage/v2"
)

// ACLRole is the level of access to grant.
Expand Down Expand Up @@ -244,6 +245,14 @@ func toObjectACLRules(items []*raw.ObjectAccessControl) []ACLRule {
return rs
}

func fromProtoToObjectACLRules(items []*storagepb.ObjectAccessControl) []ACLRule {
var rs []ACLRule
for _, item := range items {
rs = append(rs, fromProtoToObjectACLRule(item))
}
return rs
}

func toBucketACLRules(items []*raw.BucketAccessControl) []ACLRule {
var rs []ACLRule
for _, item := range items {
Expand All @@ -263,6 +272,17 @@ func toObjectACLRule(a *raw.ObjectAccessControl) ACLRule {
}
}

func fromProtoToObjectACLRule(a *storagepb.ObjectAccessControl) ACLRule {
return ACLRule{
Entity: ACLEntity(a.GetEntity()),
EntityID: a.GetEntityId(),
Role: ACLRole(a.GetRole()),
Domain: a.GetDomain(),
Email: a.GetEmail(),
ProjectTeam: fromProtoToObjectProjectTeam(a.GetProjectTeam()),
}
}

func toBucketACLRule(a *raw.BucketAccessControl) ACLRule {
return ACLRule{
Entity: ACLEntity(a.Entity),
Expand All @@ -285,6 +305,17 @@ func toRawObjectACL(rules []ACLRule) []*raw.ObjectAccessControl {
return r
}

func toProtoObjectACL(rules []ACLRule) []*storagepb.ObjectAccessControl {
if len(rules) == 0 {
return nil
}
r := make([]*storagepb.ObjectAccessControl, 0, len(rules))
for _, rule := range rules {
r = append(r, rule.toProtoObjectAccessControl("")) // bucket name unnecessary
}
return r
}

func toRawBucketACL(rules []ACLRule) []*raw.BucketAccessControl {
if len(rules) == 0 {
return nil
Expand Down Expand Up @@ -314,6 +345,15 @@ func (r ACLRule) toRawObjectAccessControl(bucket string) *raw.ObjectAccessContro
}
}

func (r ACLRule) toProtoObjectAccessControl(bucket string) *storagepb.ObjectAccessControl {
return &storagepb.ObjectAccessControl{
Entity: string(r.Entity),
Role: string(r.Role),
// The other fields are not settable.
// TODO: Is that the case for gRPC?
}
}

func toBucketProjectTeam(p *raw.BucketAccessControlProjectTeam) *ProjectTeam {
if p == nil {
return nil
Expand All @@ -333,3 +373,13 @@ func toObjectProjectTeam(p *raw.ObjectAccessControlProjectTeam) *ProjectTeam {
Team: p.Team,
}
}

func fromProtoToObjectProjectTeam(p *storagepb.ProjectTeam) *ProjectTeam {
if p == nil {
return nil
}
return &ProjectTeam{
ProjectNumber: p.GetProjectNumber(),
Team: p.GetTeam(),
}
}
78 changes: 78 additions & 0 deletions storage/storage.go
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,9 @@ import (
"google.golang.org/api/option/internaloption"
raw "google.golang.org/api/storage/v1"
htransport "google.golang.org/api/transport/http"
storagepb "google.golang.org/genproto/googleapis/storage/v2"
"google.golang.org/protobuf/proto"
"google.golang.org/protobuf/types/known/timestamppb"
)

// Methods which can be used in signed URLs.
Expand Down Expand Up @@ -1132,6 +1135,39 @@ func (o *ObjectAttrs) toRawObject(bucket string) *raw.Object {
}
}

// toProtoObject copies the editable attributes from o to the proto library's Object type.
func (o *ObjectAttrs) toProtoObject(b string) *storagepb.Object {
var ret *timestamppb.Timestamp
if !o.RetentionExpirationTime.IsZero() {
ret = timestamppb.New(o.RetentionExpirationTime)
}
var ct *timestamppb.Timestamp
if !o.CustomTime.IsZero() {
ct = timestamppb.New(o.CustomTime)
}
// For now, there are only globally unique buckets, and "_" is the alias
// project ID for such buckets.
b = bucket("_", b)

return &storagepb.Object{
Bucket: b,
Name: o.Name,
EventBasedHold: proto.Bool(o.EventBasedHold),
TemporaryHold: o.TemporaryHold,
RetentionExpireTime: ret,
ContentType: o.ContentType,
ContentEncoding: o.ContentEncoding,
ContentLanguage: o.ContentLanguage,
CacheControl: o.CacheControl,
ContentDisposition: o.ContentDisposition,
StorageClass: o.StorageClass,
Acl: toProtoObjectACL(o.ACL),
Metadata: o.Metadata,
CustomTime: ct,
KmsKey: o.KMSKeyName,
}
}

// ObjectAttrs represents the metadata for a Google Cloud Storage (GCS) object.
type ObjectAttrs struct {
// Bucket is the name of the bucket containing this GCS object.
Expand Down Expand Up @@ -1288,6 +1324,14 @@ func convertTime(t string) time.Time {
return r
}

func convertProtoTime(t *timestamppb.Timestamp) time.Time {
var r time.Time
if t != nil {
r = t.AsTime()
}
return r
}

func newObject(o *raw.Object) *ObjectAttrs {
if o == nil {
return nil
Expand Down Expand Up @@ -1333,6 +1377,40 @@ func newObject(o *raw.Object) *ObjectAttrs {
}
}

func newObjectFromProto(r *storagepb.WriteObjectResponse) *ObjectAttrs {
o := r.GetResource()
if r == nil || o == nil {
return nil
}
return &ObjectAttrs{
Bucket: o.Bucket,
Name: o.Name,
ContentType: o.ContentType,
ContentLanguage: o.ContentLanguage,
CacheControl: o.CacheControl,
EventBasedHold: o.GetEventBasedHold(),
TemporaryHold: o.TemporaryHold,
RetentionExpirationTime: convertProtoTime(o.GetRetentionExpireTime()),
ACL: fromProtoToObjectACLRules(o.GetAcl()),
Owner: o.GetOwner().GetEntity(),
ContentEncoding: o.ContentEncoding,
ContentDisposition: o.ContentDisposition,
Size: int64(o.Size),
MD5: o.GetChecksums().GetMd5Hash(),
CRC32C: o.GetChecksums().GetCrc32C(),
Metadata: o.Metadata,
Generation: o.Generation,
Metageneration: o.Metageneration,
StorageClass: o.StorageClass,
CustomerKeySHA256: o.GetCustomerEncryption().GetKeySha256(),
KMSKeyName: o.GetKmsKey(),
Created: convertProtoTime(o.GetCreateTime()),
Deleted: convertProtoTime(o.GetDeleteTime()),
Updated: convertProtoTime(o.GetUpdateTime()),
CustomTime: convertProtoTime(o.GetCustomTime()),
}
}

// Decode a uint32 encoded in Base64 in big-endian byte order.
func decodeUint32(b64 string) (uint32, error) {
d, err := base64.StdEncoding.DecodeString(b64)
Expand Down

0 comments on commit b83994e

Please sign in to comment.