Skip to content

Commit 50f55fc

Browse files
committed
Add support for gcs object generations
1 parent bcfc71c commit 50f55fc

File tree

1 file changed

+23
-8
lines changed

1 file changed

+23
-8
lines changed

get_gcs.go

Lines changed: 23 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@ import (
66
"net/url"
77
"os"
88
"path/filepath"
9+
"regexp"
10+
"strconv"
911
"strings"
1012

1113
"cloud.google.com/go/storage"
@@ -22,7 +24,7 @@ func (g *GCSGetter) ClientMode(u *url.URL) (ClientMode, error) {
2224
ctx := g.Context()
2325

2426
// Parse URL
25-
bucket, object, err := g.parseURL(u)
27+
bucket, object, _, err := g.parseURL(u)
2628
if err != nil {
2729
return 0, err
2830
}
@@ -59,7 +61,7 @@ func (g *GCSGetter) Get(dst string, u *url.URL) error {
5961
ctx := g.Context()
6062

6163
// Parse URL
62-
bucket, object, err := g.parseURL(u)
64+
bucket, object, _, err := g.parseURL(u)
6365
if err != nil {
6466
return err
6567
}
@@ -105,7 +107,7 @@ func (g *GCSGetter) Get(dst string, u *url.URL) error {
105107
}
106108
objDst = filepath.Join(dst, objDst)
107109
// Download the matching object.
108-
err = g.getObject(ctx, client, objDst, bucket, obj.Name)
110+
err = g.getObject(ctx, client, objDst, bucket, obj.Name, "")
109111
if err != nil {
110112
return err
111113
}
@@ -118,20 +120,32 @@ func (g *GCSGetter) GetFile(dst string, u *url.URL) error {
118120
ctx := g.Context()
119121

120122
// Parse URL
121-
bucket, object, err := g.parseURL(u)
123+
bucket, object, fragment, err := g.parseURL(u)
122124
if err != nil {
123125
return err
124126
}
127+
fmt.Println(object)
125128

126129
client, err := storage.NewClient(ctx)
127130
if err != nil {
128131
return err
129132
}
130-
return g.getObject(ctx, client, dst, bucket, object)
133+
return g.getObject(ctx, client, dst, bucket, object, fragment)
131134
}
132135

133-
func (g *GCSGetter) getObject(ctx context.Context, client *storage.Client, dst, bucket, object string) error {
134-
rc, err := client.Bucket(bucket).Object(object).NewReader(ctx)
136+
func (g *GCSGetter) getObject(ctx context.Context, client *storage.Client, dst, bucket, object, fragment string) error {
137+
var rc *storage.Reader
138+
var err error
139+
fragmentHasGeneration := regexp.MustCompile("^\\d+$").MatchString(fragment)
140+
if fragmentHasGeneration {
141+
generation, err := strconv.ParseInt(fragment, 10, 64)
142+
if err != nil {
143+
return err
144+
}
145+
rc, err = client.Bucket(bucket).Object(object).Generation(generation).NewReader(ctx)
146+
} else {
147+
rc, err = client.Bucket(bucket).Object(object).NewReader(ctx)
148+
}
135149
if err != nil {
136150
return err
137151
}
@@ -145,7 +159,7 @@ func (g *GCSGetter) getObject(ctx context.Context, client *storage.Client, dst,
145159
return copyReader(dst, rc, 0666, g.client.umask())
146160
}
147161

148-
func (g *GCSGetter) parseURL(u *url.URL) (bucket, path string, err error) {
162+
func (g *GCSGetter) parseURL(u *url.URL) (bucket, path, fragment string, err error) {
149163
if strings.Contains(u.Host, "googleapis.com") {
150164
hostParts := strings.Split(u.Host, ".")
151165
if len(hostParts) != 3 {
@@ -160,6 +174,7 @@ func (g *GCSGetter) parseURL(u *url.URL) (bucket, path string, err error) {
160174
}
161175
bucket = pathParts[3]
162176
path = pathParts[4]
177+
fragment = u.Fragment
163178
}
164179
return
165180
}

0 commit comments

Comments
 (0)