Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Blob] Added ContainerClient.exists() method #16315

Merged
merged 2 commits into from
Jan 29, 2021
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
Original file line number Diff line number Diff line change
Expand Up @@ -1091,10 +1091,10 @@ def exists(self, **kwargs):
Returns True if a blob exists with the defined parameters, and returns
False otherwise.

:param str version_id:
:kwarg str version_id:
The version id parameter is an opaque DateTime
value that, when present, specifies the version of the blob to check if it exists.
:param int timeout:
:kwarg int timeout:
The timeout parameter is expressed in seconds.
:returns: boolean
"""
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
import six

from azure.core import MatchConditions
from azure.core.exceptions import HttpResponseError
from azure.core.exceptions import HttpResponseError, ResourceNotFoundError
from azure.core.paging import ItemPaged
from azure.core.tracing.decorator import distributed_trace
from azure.core.pipeline import Pipeline
Expand Down Expand Up @@ -459,6 +459,25 @@ def get_container_properties(self, **kwargs):
response.name = self.container_name
return response # type: ignore

@distributed_trace
def exists(self, **kwargs):
# type: (**Any) -> bool
"""
Returns True if a container exists and returns False otherwise.

:kwarg int timeout:
The timeout parameter is expressed in seconds.
:returns: boolean
"""
try:
self._client.container.get_properties(**kwargs)
return True
except HttpResponseError as error:
try:
process_storage_error(error)
except ResourceNotFoundError:
return False

@distributed_trace
def set_container_metadata( # type: ignore
self, metadata=None, # type: Optional[Dict[str, str]]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -569,10 +569,10 @@ async def exists(self, **kwargs):
Returns True if a blob exists with the defined parameters, and returns
False otherwise.

:param str version_id:
:kwarg str version_id:
The version id parameter is an opaque DateTime
value that, when present, specifies the version of the blob to check if it exists.
:param int timeout:
:kwarg int timeout:
The timeout parameter is expressed in seconds.
:returns: boolean
"""
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
TYPE_CHECKING
)

from azure.core.exceptions import HttpResponseError
from azure.core.exceptions import HttpResponseError, ResourceNotFoundError
from azure.core.tracing.decorator import distributed_trace
from azure.core.tracing.decorator_async import distributed_trace_async
from azure.core.async_paging import AsyncItemPaged
Expand Down Expand Up @@ -335,6 +335,25 @@ async def get_container_properties(self, **kwargs):
response.name = self.container_name
return response # type: ignore

@distributed_trace_async
async def exists(self, **kwargs):
# type: (**Any) -> bool
"""
Returns True if a container exists and returns False otherwise.

:kwarg int timeout:
The timeout parameter is expressed in seconds.
:returns: boolean
"""
try:
await self._client.container.get_properties(**kwargs)
return True
except HttpResponseError as error:
try:
process_storage_error(error)
except ResourceNotFoundError:
return False

@distributed_trace_async
async def set_container_metadata( # type: ignore
self, metadata=None, # type: Optional[Dict[str, str]]
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,130 @@
interactions:
- request:
body: null
headers:
Accept:
- application/xml
Accept-Encoding:
- gzip, deflate
Connection:
- keep-alive
Content-Length:
- '0'
User-Agent:
- azsdk-python-storage-blob/12.7.2 Python/3.8.5 (Windows-10-10.0.19041-SP0)
x-ms-date:
- Sun, 24 Jan 2021 23:07:30 GMT
x-ms-version:
- '2020-04-08'
method: PUT
uri: https://storagename.blob.core.windows.net/container112fe0ef2?restype=container
response:
body:
string: "\uFEFF<?xml version=\"1.0\" encoding=\"utf-8\"?><Error><Code>ContainerAlreadyExists</Code><Message>The
specified container already exists.\nRequestId:34e48888-401e-009f-08a5-f21ff6000000\nTime:2021-01-24T23:07:30.9942715Z</Message></Error>"
headers:
content-length:
- '230'
content-type:
- application/xml
date:
- Sun, 24 Jan 2021 23:07:30 GMT
server:
- Windows-Azure-Blob/1.0 Microsoft-HTTPAPI/2.0
x-ms-error-code:
- ContainerAlreadyExists
x-ms-version:
- '2020-04-08'
status:
code: 409
message: The specified container already exists.
- request:
body: null
headers:
Accept:
- application/xml
Accept-Encoding:
- gzip, deflate
Connection:
- keep-alive
User-Agent:
- azsdk-python-storage-blob/12.7.2 Python/3.8.5 (Windows-10-10.0.19041-SP0)
x-ms-date:
- Sun, 24 Jan 2021 23:07:31 GMT
x-ms-version:
- '2020-04-08'
method: GET
uri: https://storagename.blob.core.windows.net/container112fe0ef2?restype=container
response:
body:
string: ''
headers:
content-length:
- '0'
date:
- Sun, 24 Jan 2021 23:07:31 GMT
etag:
- '"0x8D8C0BA190EF0A2"'
last-modified:
- Sun, 24 Jan 2021 22:47:58 GMT
server:
- Windows-Azure-Blob/1.0 Microsoft-HTTPAPI/2.0
vary:
- Origin
x-ms-default-encryption-scope:
- $account-encryption-key
x-ms-deny-encryption-scope-override:
- 'false'
x-ms-has-immutability-policy:
- 'false'
x-ms-has-legal-hold:
- 'false'
x-ms-lease-state:
- available
x-ms-lease-status:
- unlocked
x-ms-version:
- '2020-04-08'
status:
code: 200
message: OK
- request:
body: null
headers:
Accept:
- application/xml
Accept-Encoding:
- gzip, deflate
Connection:
- keep-alive
User-Agent:
- azsdk-python-storage-blob/12.7.2 Python/3.8.5 (Windows-10-10.0.19041-SP0)
x-ms-date:
- Sun, 24 Jan 2021 23:07:31 GMT
x-ms-version:
- '2020-04-08'
method: GET
uri: https://storagename.blob.core.windows.net/container212fe0ef2?restype=container
response:
body:
string: "\uFEFF<?xml version=\"1.0\" encoding=\"utf-8\"?><Error><Code>ContainerNotFound</Code><Message>The
specified container does not exist.\nRequestId:34e488e9-401e-009f-63a5-f21ff6000000\nTime:2021-01-24T23:07:31.1273672Z</Message></Error>"
headers:
content-length:
- '225'
content-type:
- application/xml
date:
- Sun, 24 Jan 2021 23:07:31 GMT
server:
- Windows-Azure-Blob/1.0 Microsoft-HTTPAPI/2.0
vary:
- Origin
x-ms-error-code:
- ContainerNotFound
x-ms-version:
- '2020-04-08'
status:
code: 404
message: The specified container does not exist.
version: 1
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
interactions:
- request:
body: null
headers:
Accept:
- application/xml
User-Agent:
- azsdk-python-storage-blob/12.7.2 Python/3.8.5 (Windows-10-10.0.19041-SP0)
x-ms-date:
- Sun, 24 Jan 2021 23:08:38 GMT
x-ms-version:
- '2020-04-08'
method: PUT
uri: https://storagename.blob.core.windows.net/container175a3116f?restype=container
response:
body:
string: ''
headers:
content-length: '0'
date: Sun, 24 Jan 2021 23:08:37 GMT
etag: '"0x8D8C0BCFBA744BA"'
last-modified: Sun, 24 Jan 2021 23:08:38 GMT
server: Windows-Azure-Blob/1.0 Microsoft-HTTPAPI/2.0
x-ms-version: '2020-04-08'
status:
code: 201
message: Created
url: https://emilydevtest.blob.core.windows.net/container175a3116f?restype=container
- request:
body: null
headers:
Accept:
- application/xml
User-Agent:
- azsdk-python-storage-blob/12.7.2 Python/3.8.5 (Windows-10-10.0.19041-SP0)
x-ms-date:
- Sun, 24 Jan 2021 23:08:38 GMT
x-ms-version:
- '2020-04-08'
method: GET
uri: https://storagename.blob.core.windows.net/container175a3116f?restype=container
response:
body:
string: ''
headers:
content-length: '0'
date: Sun, 24 Jan 2021 23:08:37 GMT
etag: '"0x8D8C0BCFBA744BA"'
last-modified: Sun, 24 Jan 2021 23:08:38 GMT
server: Windows-Azure-Blob/1.0 Microsoft-HTTPAPI/2.0
vary: Origin
x-ms-default-encryption-scope: $account-encryption-key
x-ms-deny-encryption-scope-override: 'false'
x-ms-has-immutability-policy: 'false'
x-ms-has-legal-hold: 'false'
x-ms-lease-state: available
x-ms-lease-status: unlocked
x-ms-version: '2020-04-08'
status:
code: 200
message: OK
url: https://emilydevtest.blob.core.windows.net/container175a3116f?restype=container
- request:
body: null
headers:
Accept:
- application/xml
User-Agent:
- azsdk-python-storage-blob/12.7.2 Python/3.8.5 (Windows-10-10.0.19041-SP0)
x-ms-date:
- Sun, 24 Jan 2021 23:08:38 GMT
x-ms-version:
- '2020-04-08'
method: GET
uri: https://storagename.blob.core.windows.net/container275a3116f?restype=container
response:
body:
string: "\uFEFF<?xml version=\"1.0\" encoding=\"utf-8\"?><Error><Code>ContainerNotFound</Code><Message>The
specified container does not exist.\nRequestId:f0e7bd23-001e-00b1-54a5-f24de1000000\nTime:2021-01-24T23:08:38.1833494Z</Message></Error>"
headers:
content-length: '225'
content-type: application/xml
date: Sun, 24 Jan 2021 23:08:37 GMT
server: Windows-Azure-Blob/1.0 Microsoft-HTTPAPI/2.0
vary: Origin
x-ms-error-code: ContainerNotFound
x-ms-version: '2020-04-08'
status:
code: 404
message: The specified container does not exist.
url: https://emilydevtest.blob.core.windows.net/container275a3116f?restype=container
version: 1
11 changes: 11 additions & 0 deletions sdk/storage/azure-storage-blob/tests/test_container.py
Original file line number Diff line number Diff line change
Expand Up @@ -311,6 +311,17 @@ def test_get_container_metadata_with_lease_id(self, resource_group, location, st
# Assert
self.assertDictEqual(md, metadata)

@GlobalStorageAccountPreparer()
def test_container_exists(self, resource_group, location, storage_account, storage_account_key):
bsc = BlobServiceClient(self.account_url(storage_account, "blob"), storage_account_key)

container1 = self._create_container(bsc, prefix="container1")
container2_name = self._get_container_reference(prefix="container2")
container2 = bsc.get_container_client(container2_name)

self.assertTrue(container1.exists())
self.assertFalse(container2.exists())

@GlobalStorageAccountPreparer()
def test_get_container_properties(self, resource_group, location, storage_account, storage_account_key):
bsc = BlobServiceClient(self.account_url(storage_account, "blob"), storage_account_key)
Expand Down
16 changes: 15 additions & 1 deletion sdk/storage/azure-storage-blob/tests/test_container_async.py
Original file line number Diff line number Diff line change
Expand Up @@ -379,10 +379,24 @@ async def test_get_container_metadata_with_lease_id(self, resource_group, locati
# Assert
self.assertDictEqual(md, metadata)

@GlobalStorageAccountPreparer()
@AsyncStorageTestCase.await_prepared_test
async def test_container_exists(self, resource_group, location, storage_account, storage_account_key):
bsc = BlobServiceClient(self.account_url(
storage_account, "blob"), storage_account_key, transport=AiohttpTestTransport())

container1 = await self._create_container(bsc, prefix="container1")
container2_name = self._get_container_reference(prefix="container2")
container2 = bsc.get_container_client(container2_name)

self.assertTrue(await container1.exists())
self.assertFalse(await container2.exists())

@GlobalStorageAccountPreparer()
@AsyncStorageTestCase.await_prepared_test
async def test_get_container_properties(self, resource_group, location, storage_account, storage_account_key):
bsc = BlobServiceClient(self.account_url(storage_account, "blob"), storage_account_key, transport=AiohttpTestTransport())
bsc = BlobServiceClient(
self.account_url(storage_account, "blob"), storage_account_key, transport=AiohttpTestTransport())
metadata = {'hello': 'world', 'number': '42'}
container = await self._create_container(bsc)
await container.set_container_metadata(metadata)
Expand Down