1# Copyright 2013 The Chromium Authors. All rights reserved. 2# Use of this source code is governed by a BSD-style license that can be 3# found in the LICENSE file. 4 5"""Implementation of CloudBucket using Google Cloud Storage as the backend.""" 6import os 7import sys 8 9# boto requires depot_tools/third_party be in the path. Use 10# src/tools/find_depot_tools.py to add this directory. 11sys.path.append(os.path.join(os.path.dirname(__file__), os.pardir, os.pardir, 12 os.pardir, os.pardir, 'tools')) 13import find_depot_tools 14DEPOT_TOOLS_PATH = find_depot_tools.add_depot_tools_to_path() 15sys.path.append(os.path.join(os.path.abspath(DEPOT_TOOLS_PATH), 'third_party')) 16import boto 17 18from ispy.common import cloud_bucket 19 20 21class BotoCloudBucket(cloud_bucket.BaseCloudBucket): 22 """Interfaces with GS using the boto library.""" 23 24 def __init__(self, key, secret, bucket_name): 25 """Initializes the bucket with a key, secret, and bucket_name. 26 27 Args: 28 key: the API key to access GS. 29 secret: the API secret to access GS. 30 bucket_name: the name of the bucket to connect to. 31 """ 32 uri = boto.storage_uri('', 'gs') 33 conn = uri.connect(key, secret) 34 self.bucket = conn.get_bucket(bucket_name) 35 36 def _GetKey(self, path): 37 key = boto.gs.key.Key(self.bucket) 38 key.key = path 39 return key 40 41 # override 42 def UploadFile(self, path, contents, content_type): 43 key = self._GetKey(path) 44 key.set_metadata('Content-Type', content_type) 45 key.set_contents_from_string(contents) 46 # Open permissions for the appengine account to read/write. 47 key.add_email_grant('FULL_CONTROL', 48 'ispy.google.com@appspot.gserviceaccount.com') 49 50 # override 51 def DownloadFile(self, path): 52 key = self._GetKey(path) 53 if key.exists(): 54 return key.get_contents_as_string() 55 else: 56 raise cloud_bucket.FileNotFoundError 57 58 # override 59 def UpdateFile(self, path, contents): 60 key = self._GetKey(path) 61 if key.exists(): 62 key.set_contents_from_string(contents) 63 else: 64 raise cloud_bucket.FileNotFoundError 65 66 # override 67 def RemoveFile(self, path): 68 key = self._GetKey(path) 69 key.delete() 70 71 # override 72 def FileExists(self, path): 73 key = self._GetKey(path) 74 return key.exists() 75 76 # override 77 def GetImageURL(self, path): 78 key = self._GetKey(path) 79 if key.exists(): 80 # Corrects a bug in boto that incorrectly generates a url 81 # to a resource in Google Cloud Storage. 82 return key.generate_url(3600).replace('AWSAccessKeyId', 'GoogleAccessId') 83 else: 84 raise cloud_bucket.FileNotFoundError(path) 85 86 # override 87 def GetAllPaths(self, prefix): 88 return (key.key for key in self.bucket.get_all_keys(prefix=prefix)) 89