github.com/GoogleCloudPlatform/testgrid@v0.0.174/util/gcs/client.go (about)

     1  /*
     2  Copyright 2020 The TestGrid Authors.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8      http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package gcs
    18  
    19  import (
    20  	"context"
    21  	"io"
    22  
    23  	"cloud.google.com/go/storage"
    24  )
    25  
    26  // Uploader adds upload capabilities to a GCS client.
    27  type Uploader interface {
    28  	Upload(ctx context.Context, path Path, buf []byte, public bool, cacheControl string) (*storage.ObjectAttrs, error)
    29  }
    30  
    31  // Downloader can list files and open them for reading.
    32  type Downloader interface {
    33  	Lister
    34  	Opener
    35  }
    36  
    37  // A Lister returns objects under a prefix.
    38  type Lister interface {
    39  	Objects(ctx context.Context, prefix Path, delimiter, start string) Iterator
    40  }
    41  
    42  // An Iterator returns the attributes of the listed objects or an iterator.Done error.
    43  type Iterator interface {
    44  	Next() (*storage.ObjectAttrs, error)
    45  }
    46  
    47  // An Opener opens a path for reading.
    48  type Opener interface {
    49  	Open(ctx context.Context, path Path) (io.ReadCloser, *storage.ReaderObjectAttrs, error)
    50  }
    51  
    52  // A Stater can stat an object and get its attributes.
    53  type Stater interface {
    54  	Stat(ctx context.Context, prefix Path) (*storage.ObjectAttrs, error)
    55  }
    56  
    57  // A Copier can cloud copy an object to a new location.
    58  type Copier interface {
    59  	// Copy an object to the specified path
    60  	Copy(ctx context.Context, from, to Path) (*storage.ObjectAttrs, error)
    61  }
    62  
    63  // A Client can upload, download and stat.
    64  type Client interface {
    65  	Uploader
    66  	Downloader
    67  	Stater
    68  	Copier
    69  }
    70  
    71  // A ConditionalClient can limit actions to those matching conditions.
    72  type ConditionalClient interface {
    73  	Client
    74  	// If specifies conditions on the object read from and/or written to.
    75  	If(read, write *storage.Conditions) ConditionalClient
    76  }
    77  
    78  type gcsClient struct {
    79  	gcs   *realGCSClient
    80  	local *localClient
    81  }
    82  
    83  // NewClient returns a flexible (local or GCS) storage client.
    84  func NewClient(client *storage.Client) ConditionalClient {
    85  	return gcsClient{
    86  		gcs:   &realGCSClient{client, nil, nil},
    87  		local: &localClient{nil, nil},
    88  	}
    89  }
    90  
    91  // If returns a flexible (local or GCS) conditional client.
    92  func (gc gcsClient) If(read, write *storage.Conditions) ConditionalClient {
    93  	return gcsClient{
    94  		gcs:   &realGCSClient{gc.gcs.client, read, write},
    95  		local: &localClient{nil, nil},
    96  	}
    97  }
    98  
    99  func (gc gcsClient) clientFromPath(path Path) ConditionalClient {
   100  	if path.URL().Scheme == "gs" {
   101  		return gc.gcs
   102  	}
   103  	return gc.local
   104  }
   105  
   106  // Copy copies the contents of 'from' into 'to'.
   107  func (gc gcsClient) Copy(ctx context.Context, from, to Path) (*storage.ObjectAttrs, error) {
   108  	client := gc.clientFromPath(from)
   109  	return client.Copy(ctx, from, to)
   110  }
   111  
   112  // Open returns a handle for a given path.
   113  func (gc gcsClient) Open(ctx context.Context, path Path) (io.ReadCloser, *storage.ReaderObjectAttrs, error) {
   114  	client := gc.clientFromPath(path)
   115  	return client.Open(ctx, path)
   116  }
   117  
   118  // Objects returns an iterator of objects under a given path.
   119  func (gc gcsClient) Objects(ctx context.Context, path Path, delimiter, startOffset string) Iterator {
   120  	client := gc.clientFromPath(path)
   121  	return client.Objects(ctx, path, delimiter, startOffset)
   122  }
   123  
   124  // Upload writes content to the given path.
   125  func (gc gcsClient) Upload(ctx context.Context, path Path, buf []byte, worldReadable bool, cacheControl string) (*storage.ObjectAttrs, error) {
   126  	client := gc.clientFromPath(path)
   127  	return client.Upload(ctx, path, buf, worldReadable, cacheControl)
   128  }
   129  
   130  // Stat returns object attributes for a given path.
   131  func (gc gcsClient) Stat(ctx context.Context, path Path) (*storage.ObjectAttrs, error) {
   132  	client := gc.clientFromPath(path)
   133  	return client.Stat(ctx, path)
   134  }