github.com/bpfs/defs@v0.0.15/afero/gcsfs/gcs.go (about) 1 // Copyright © 2021 Vasily Ovchinnikov <vasily@remerge.io>. 2 // 3 // The code in this file is derived from afero fork github.com/Zatte/afero by Mikael Rapp 4 // licensed under Apache License 2.0. 5 // 6 // Licensed under the Apache License, Version 2.0 (the "License"); 7 // you may not use this file except in compliance with the License. 8 // You may obtain a copy of the License at 9 // http://www.apache.org/licenses/LICENSE-2.0 10 // 11 // Unless required by applicable law or agreed to in writing, software 12 // distributed under the License is distributed on an "AS IS" BASIS, 13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 // See the License for the specific language governing permissions and 15 // limitations under the License. 16 17 package gcsfs 18 19 import ( 20 "context" 21 "os" 22 "time" 23 24 "cloud.google.com/go/storage" 25 "github.com/bpfs/defs/afero" 26 "github.com/googleapis/google-cloud-go-testing/storage/stiface" 27 28 "google.golang.org/api/option" 29 ) 30 31 type GcsFs struct { 32 source *Fs 33 } 34 35 // NewGcsFS creates a GCS file system, automatically instantiating and decorating the storage client. 36 // You can provide additional options to be passed to the client creation, as per 37 // cloud.google.com/go/storage documentation 38 func NewGcsFS(ctx context.Context, opts ...option.ClientOption) (afero.Fs, error) { 39 if json := os.Getenv("GOOGLE_APPLICATION_CREDENTIALS_JSON"); json != "" { 40 opts = append(opts, option.WithCredentialsJSON([]byte(json))) 41 } 42 client, err := storage.NewClient(ctx, opts...) 43 if err != nil { 44 return nil, err 45 } 46 47 return NewGcsFSFromClient(ctx, client) 48 } 49 50 // NewGcsFSWithSeparator is the same as NewGcsFS, but the files system will use the provided folder separator. 51 func NewGcsFSWithSeparator(ctx context.Context, folderSeparator string, opts ...option.ClientOption) (afero.Fs, error) { 52 client, err := storage.NewClient(ctx, opts...) 53 if err != nil { 54 return nil, err 55 } 56 57 return NewGcsFSFromClientWithSeparator(ctx, client, folderSeparator) 58 } 59 60 // NewGcsFSFromClient creates a GCS file system from a given storage client 61 func NewGcsFSFromClient(ctx context.Context, client *storage.Client) (afero.Fs, error) { 62 c := stiface.AdaptClient(client) 63 64 return &GcsFs{NewGcsFs(ctx, c)}, nil 65 } 66 67 // NewGcsFSFromClientWithSeparator is the same as NewGcsFSFromClient, but the file system will use the provided folder separator. 68 func NewGcsFSFromClientWithSeparator(ctx context.Context, client *storage.Client, folderSeparator string) (afero.Fs, error) { 69 c := stiface.AdaptClient(client) 70 71 return &GcsFs{NewGcsFsWithSeparator(ctx, c, folderSeparator)}, nil 72 } 73 74 // Wraps gcs.GcsFs and convert some return types to afero interfaces. 75 76 func (fs *GcsFs) Name() string { 77 return fs.source.Name() 78 } 79 80 func (fs *GcsFs) Create(name string) (afero.File, error) { 81 return fs.source.Create(name) 82 } 83 84 func (fs *GcsFs) Mkdir(name string, perm os.FileMode) error { 85 return fs.source.Mkdir(name, perm) 86 } 87 88 func (fs *GcsFs) MkdirAll(path string, perm os.FileMode) error { 89 return fs.source.MkdirAll(path, perm) 90 } 91 92 func (fs *GcsFs) Open(name string) (afero.File, error) { 93 return fs.source.Open(name) 94 } 95 96 func (fs *GcsFs) OpenFile(name string, flag int, perm os.FileMode) (afero.File, error) { 97 return fs.source.OpenFile(name, flag, perm) 98 } 99 100 func (fs *GcsFs) Remove(name string) error { 101 return fs.source.Remove(name) 102 } 103 104 func (fs *GcsFs) RemoveAll(path string) error { 105 return fs.source.RemoveAll(path) 106 } 107 108 func (fs *GcsFs) Rename(oldname, newname string) error { 109 return fs.source.Rename(oldname, newname) 110 } 111 112 func (fs *GcsFs) Stat(name string) (os.FileInfo, error) { 113 return fs.source.Stat(name) 114 } 115 116 func (fs *GcsFs) Chmod(name string, mode os.FileMode) error { 117 return fs.source.Chmod(name, mode) 118 } 119 120 func (fs *GcsFs) Chtimes(name string, atime time.Time, mtime time.Time) error { 121 return fs.source.Chtimes(name, atime, mtime) 122 } 123 124 func (fs *GcsFs) Chown(name string, uid, gid int) error { 125 return fs.source.Chown(name, uid, gid) 126 }