Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 0 additions & 26 deletions gcloud/storage/blob.py
Original file line number Diff line number Diff line change
Expand Up @@ -227,32 +227,6 @@ def exists(self, client=None):
except NotFound:
return False

def rename(self, new_name, client=None):
"""Renames this blob using copy and delete operations.

Effectively, copies blob to the same bucket with a new name, then
deletes the blob.

.. warning::
This method will first duplicate the data and then delete the
old blob. This means that with very large objects renaming
could be a very (temporarily) costly or a very slow operation.

:type new_name: string
:param new_name: The new name for this blob.

:type client: :class:`gcloud.storage.client.Client` or ``NoneType``
:param client: Optional. The client to use. If not passed, falls back
to the ``client`` stored on the blob's bucket.

:rtype: :class:`Blob`
:returns: The newly-copied blob.
"""
new_blob = self.bucket.copy_blob(self, self.bucket, new_name,
client=client)
self.delete(client=client)
return new_blob

def delete(self, client=None):
"""Deletes a blob from Cloud Storage.

Expand Down
31 changes: 30 additions & 1 deletion gcloud/storage/bucket.py
Original file line number Diff line number Diff line change
Expand Up @@ -434,7 +434,7 @@ def copy_blob(self, blob, destination_bucket, new_name=None,
client=None):
"""Copy the given blob to the given bucket, optionally with a new name.

:type blob: string or :class:`gcloud.storage.blob.Blob`
:type blob: :class:`gcloud.storage.blob.Blob`
:param blob: The blob to be copied.

:type destination_bucket: :class:`gcloud.storage.bucket.Bucket`
Expand All @@ -461,6 +461,35 @@ def copy_blob(self, blob, destination_bucket, new_name=None,
new_blob._set_properties(copy_result)
return new_blob

def rename_blob(self, blob, new_name, client=None):
"""Rename the given blob using copy and delete operations.

Effectively, copies blob to the same bucket with a new name, then
deletes the blob.

.. warning::

This method will first duplicate the data and then delete the
old blob. This means that with very large objects renaming
could be a very (temporarily) costly or a very slow operation.

:type blob: :class:`gcloud.storage.blob.Blob`
:param blob: The blob to be renamed.

:type new_name: string
:param new_name: The new name for this blob.

:type client: :class:`gcloud.storage.client.Client` or ``NoneType``
:param client: Optional. The client to use. If not passed, falls back
to the ``client`` stored on the current bucket.

:rtype: :class:`Blob`
:returns: The newly-renamed blob.
"""
new_blob = self.copy_blob(blob, self, new_name, client=client)
blob.delete(client=client)
return new_blob

@property
def cors(self):
"""Retrieve CORS policies configured for this bucket.
Expand Down
20 changes: 0 additions & 20 deletions gcloud/storage/test_blob.py
Original file line number Diff line number Diff line change
Expand Up @@ -232,21 +232,6 @@ def test_exists_hit(self):
bucket._blobs[BLOB_NAME] = 1
self.assertTrue(blob.exists())

def test_rename(self):
BLOB_NAME = 'blob-name'
NEW_NAME = 'new-name'
connection = _Connection()
client = _Client(connection)
bucket = _Bucket(client=client)
blob = self._makeOne(BLOB_NAME, bucket=bucket)
bucket._blobs[BLOB_NAME] = 1
new_blob = blob.rename(NEW_NAME)
self.assertEqual(blob.name, BLOB_NAME)
self.assertEqual(new_blob.name, NEW_NAME)
self.assertFalse(BLOB_NAME in bucket._blobs)
self.assertEqual(bucket._deleted, [(BLOB_NAME, None)])
self.assertTrue(NEW_NAME in bucket._blobs)

def test_delete(self):
from six.moves.http_client import NOT_FOUND
BLOB_NAME = 'blob-name'
Expand Down Expand Up @@ -1058,11 +1043,6 @@ def __init__(self, client=None):
self._copied = []
self._deleted = []

def copy_blob(self, blob, destination_bucket, new_name, client=None):
self._copied.append((blob, destination_bucket, new_name, client))
destination_bucket._blobs[new_name] = self._blobs[blob.name]
return blob.__class__(new_name, bucket=destination_bucket)

def delete_blob(self, blob_name, client=None):
del self._blobs[blob_name]
self._deleted.append((blob_name, client))
Expand Down
26 changes: 26 additions & 0 deletions gcloud/storage/test_bucket.py
Original file line number Diff line number Diff line change
Expand Up @@ -519,6 +519,32 @@ class _Blob(object):
self.assertEqual(kw['method'], 'POST')
self.assertEqual(kw['path'], COPY_PATH)

def test_rename_blob(self):
BUCKET_NAME = 'BUCKET_NAME'
BLOB_NAME = 'blob-name'
NEW_BLOB_NAME = 'new-blob-name'

DATA = {'name': NEW_BLOB_NAME}
connection = _Connection(DATA)
client = _Client(connection)
bucket = self._makeOne(client=client, name=BUCKET_NAME)

class _Blob(object):

def __init__(self, name, bucket_name):
self.name = name
self.path = '/b/%s/o/%s' % (bucket_name, name)
self._deleted = []

def delete(self, client=None):
self._deleted.append(client)

blob = _Blob(BLOB_NAME, BUCKET_NAME)
renamed_blob = bucket.rename_blob(blob, NEW_BLOB_NAME, client=client)
self.assertTrue(renamed_blob.bucket is bucket)
self.assertEqual(renamed_blob.name, NEW_BLOB_NAME)
self.assertEqual(blob._deleted, [client])

def test_etag(self):
ETAG = 'ETAG'
properties = {'etag': ETAG}
Expand Down