Skip to content

Commit 00b8b50

Browse files
author
Hugues Valois
committed
Merge pull request Azure#363 from hosungs/storage-connection-string-support
Storage connection string support. Fixes Azure#339
2 parents 31ce6a0 + d60f086 commit 00b8b50

File tree

5 files changed

+100
-7
lines changed

5 files changed

+100
-7
lines changed

azure/storage/__init__.py

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,10 @@
4141
_get_etree_text,
4242
ETree,
4343
_ETreeXmlToObject,
44-
)
44+
BLOB_SERVICE_HOST_BASE,
45+
TABLE_SERVICE_HOST_BASE,
46+
QUEUE_SERVICE_HOST_BASE,
47+
)
4548

4649
# x-ms-version for storage service.
4750
X_MS_VERSION = '2014-02-14'
@@ -1279,6 +1282,31 @@ def sign_request(self, request):
12791282
pass
12801283

12811284

1285+
class StorageConnectionParameters(object):
1286+
'''
1287+
Extract connection parameters from a connection string.
1288+
1289+
This is based on http://azure.microsoft.com/en-us/documentation/articles/storage-configure-connection-string/ .
1290+
1291+
NOTE "(Blob|Table|Queue|File)Endpoint" are not supported.
1292+
"SharedAccessSignature" is not supported.
1293+
dev_host, timeout, and sas_token cannot be specified with a connection string.
1294+
'''
1295+
def __init__(self, connection_string = ''):
1296+
connection_params = dict(s.split('=',1) for s in connection_string.split(';'))
1297+
1298+
self.account_name = connection_params.get('AccountName', None)
1299+
self.account_key = connection_params.get('AccountKey', None)
1300+
self.protocol = connection_params.get('DefaultEndpointsProtocol', 'https')
1301+
endpoint_suffix = connection_params.get('EndpointSuffix', None)
1302+
self.host_base_blob = BLOB_SERVICE_HOST_BASE if endpoint_suffix is None \
1303+
else ".blob.{}".format(endpoint_suffix)
1304+
self.host_base_table = TABLE_SERVICE_HOST_BASE if endpoint_suffix is None \
1305+
else ".table.{}".format(endpoint_suffix)
1306+
self.host_base_queue = QUEUE_SERVICE_HOST_BASE if endpoint_suffix is None \
1307+
else ".queue.{}".format(endpoint_suffix)
1308+
1309+
12821310
# make these available just from storage.
12831311
from azure.storage.blobservice import BlobService
12841312
from azure.storage.queueservice import QueueService

azure/storage/blobservice.py

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@
4747
StorageSASAuthentication,
4848
StorageSharedKeyAuthentication,
4949
StorageNoAuthentication,
50+
StorageConnectionParameters,
5051
X_MS_VERSION,
5152
_BlockBlobChunkUploader,
5253
_PageBlobChunkUploader,
@@ -83,7 +84,7 @@ class BlobService(_StorageClient):
8384

8485
def __init__(self, account_name=None, account_key=None, protocol='https',
8586
host_base=BLOB_SERVICE_HOST_BASE, dev_host=DEV_BLOB_HOST,
86-
timeout=DEFAULT_HTTP_TIMEOUT, sas_token=None):
87+
timeout=DEFAULT_HTTP_TIMEOUT, sas_token=None, connection_string=None):
8788
'''
8889
account_name:
8990
your storage account name, required for all operations.
@@ -100,7 +101,22 @@ def __init__(self, account_name=None, account_key=None, protocol='https',
100101
Optional. Timeout for the http request, in seconds.
101102
sas_token:
102103
Optional. Token to use to authenticate with shared access signature.
103-
'''
104+
connection_string:
105+
Optional. If specified, the first four parameters (account_name,
106+
account_key, protocol, host_base) may be overridden
107+
by values specified in the connection_string. The next three parameters
108+
(dev_host, timeout, sas_token) cannot be specified with a
109+
connection_string. See
110+
http://azure.microsoft.com/en-us/documentation/articles/storage-configure-connection-string/
111+
for the connection string format.
112+
'''
113+
if connection_string is not None:
114+
connection_params = StorageConnectionParameters(connection_string)
115+
account_name = connection_params.account_name
116+
account_key = connection_params.account_key
117+
protocol = connection_params.protocol
118+
host_base = connection_params.host_base_blob
119+
104120
self._BLOB_MAX_DATA_SIZE = 64 * 1024 * 1024
105121
self._BLOB_MAX_CHUNK_DATA_SIZE = 4 * 1024 * 1024
106122
super(BlobService, self).__init__(

azure/storage/queueservice.py

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@
4646
StorageServiceProperties,
4747
StorageSASAuthentication,
4848
StorageSharedKeyAuthentication,
49+
StorageConnectionParameters,
4950
_convert_signed_identifiers_to_xml,
5051
_update_storage_queue_header,
5152
X_MS_VERSION,
@@ -64,7 +65,7 @@ class QueueService(_StorageClient):
6465

6566
def __init__(self, account_name=None, account_key=None, protocol='https',
6667
host_base=QUEUE_SERVICE_HOST_BASE, dev_host=DEV_QUEUE_HOST,
67-
timeout=DEFAULT_HTTP_TIMEOUT, sas_token=None):
68+
timeout=DEFAULT_HTTP_TIMEOUT, sas_token=None, connection_string=None):
6869
'''
6970
account_name:
7071
your storage account name, required for all operations.
@@ -81,7 +82,22 @@ def __init__(self, account_name=None, account_key=None, protocol='https',
8182
Optional. Timeout for the http request, in seconds.
8283
sas_token:
8384
Optional. Token to use to authenticate with shared access signature.
84-
'''
85+
connection_string:
86+
Optional. If specified, the first four parameters (account_name,
87+
account_key, protocol, host_base) may be overridden
88+
by values specified in the connection_string. The next three parameters
89+
(dev_host, timeout, sas_token) cannot be specified with a
90+
connection_string. See
91+
http://azure.microsoft.com/en-us/documentation/articles/storage-configure-connection-string/
92+
for the connection string format.
93+
'''
94+
if connection_string is not None:
95+
connection_params = StorageConnectionParameters(connection_string)
96+
account_name = connection_params.account_name
97+
account_key = connection_params.account_key
98+
protocol = connection_params.protocol
99+
host_base = connection_params.host_base_queue
100+
85101
super(QueueService, self).__init__(
86102
account_name, account_key, protocol, host_base, dev_host, timeout, sas_token)
87103

azure/storage/tableservice.py

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@
3939
StorageSASAuthentication,
4040
StorageTableSharedKeyAuthentication,
4141
TableSharedAccessPermissions,
42+
StorageConnectionParameters,
4243
_convert_entity_to_xml,
4344
_convert_etree_element_to_entity,
4445
_convert_etree_element_to_table,
@@ -62,7 +63,7 @@ class TableService(_StorageClient):
6263

6364
def __init__(self, account_name=None, account_key=None, protocol='https',
6465
host_base=TABLE_SERVICE_HOST_BASE, dev_host=DEV_TABLE_HOST,
65-
timeout=DEFAULT_HTTP_TIMEOUT, sas_token=None):
66+
timeout=DEFAULT_HTTP_TIMEOUT, sas_token=None, connection_string=None):
6667
'''
6768
account_name:
6869
your storage account name, required for all operations.
@@ -79,7 +80,22 @@ def __init__(self, account_name=None, account_key=None, protocol='https',
7980
Optional. Timeout for the http request, in seconds.
8081
sas_token:
8182
Optional. Token to use to authenticate with shared access signature.
82-
'''
83+
connection_string:
84+
Optional. If specified, the first four parameters (account_name,
85+
account_key, protocol, host_base) may be overridden
86+
by values specified in the connection_string. The next three parameters
87+
(dev_host, timeout, sas_token) cannot be specified with a
88+
connection_string. See
89+
http://azure.microsoft.com/en-us/documentation/articles/storage-configure-connection-string/
90+
for the connection string format.
91+
'''
92+
if connection_string is not None:
93+
connection_params = StorageConnectionParameters(connection_string)
94+
account_name = connection_params.account_name
95+
account_key = connection_params.account_key
96+
protocol = connection_params.protocol
97+
host_base = connection_params.host_base_table
98+
8399
super(TableService, self).__init__(
84100
account_name, account_key, protocol, host_base, dev_host, timeout, sas_token)
85101

tests/test_blobservice.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -354,6 +354,23 @@ def test_create_blob_service_emulated_false_env_variables(self):
354354
self.assertEqual(bs.account_key, credentials.getStorageServicesKey())
355355
self.assertEqual(bs.is_emulated, False)
356356

357+
def test_create_blob_service_connection_string(self):
358+
# Arrange
359+
connection_string = 'DefaultEndpointsProtocol={};AccountName={};AccountKey={}'.format(
360+
'http', credentials.getStorageServicesName(),
361+
credentials.getStorageServicesKey())
362+
363+
# Act
364+
bs = BlobService(connection_string = connection_string)
365+
366+
# Assert
367+
self.assertIsNotNone(bs)
368+
self.assertEqual(bs.account_name, credentials.getStorageServicesName())
369+
self.assertEqual(bs.account_key, credentials.getStorageServicesKey())
370+
self.assertEqual(bs.protocol, 'http')
371+
self.assertEqual(bs.host_base, BLOB_SERVICE_HOST_BASE)
372+
self.assertFalse(bs.is_emulated)
373+
357374
#--Test cases for containers -----------------------------------------
358375
def test_create_container_no_options(self):
359376
# Arrange

0 commit comments

Comments
 (0)