async def test_create_service_with_custom_account_endpoint_path_async(self, resource_group, location, storage_account, storage_account_key): custom_account_url = "http://local-machine:11002/custom/account/path/" + self.sas_token for service_type in SERVICES.items(): conn_string = 'DefaultEndpointsProtocol=http;AccountName={};AccountKey={};TableEndpoint={};'.format( storage_account.name, storage_account_key, custom_account_url) # Act service = service_type[0].from_connection_string(conn_string, table_name="foo") # Assert self.assertEqual(service.account_name, storage_account.name) self.assertEqual(service.credential.account_name, storage_account.name) self.assertEqual(service.credential.account_key, storage_account_key) self.assertEqual(service._primary_hostname, 'local-machine:11002/custom/account/path') service = TableServiceClient(account_url=custom_account_url) self.assertEqual(service.account_name, None) self.assertEqual(service.credential, None) self.assertEqual(service._primary_hostname, 'local-machine:11002/custom/account/path') self.assertTrue(service.url.startswith('http://local-machine:11002/custom/account/path')) service = TableClient(account_url=custom_account_url, table_name="foo") self.assertEqual(service.account_name, None) self.assertEqual(service.table_name, "foo") self.assertEqual(service.credential, None) self.assertEqual(service._primary_hostname, 'local-machine:11002/custom/account/path') self.assertTrue(service.url.startswith('http://local-machine:11002/custom/account/path')) service = TableClient.from_table_url("http://local-machine:11002/custom/account/path/foo" + self.sas_token) self.assertEqual(service.account_name, None) self.assertEqual(service.table_name, "foo") self.assertEqual(service.credential, None) self.assertEqual(service._primary_hostname, 'local-machine:11002/custom/account/path') self.assertTrue(service.url.startswith('http://local-machine:11002/custom/account/path'))
async def test_create_service_with_custom_account_endpoint_path_async(self): token = self.generate_sas_token() custom_account_url = "http://local-machine:11002/custom/account/path/" + token for service_type in SERVICES.items(): conn_string = 'DefaultEndpointsProtocol=http;AccountName={};AccountKey={};TableEndpoint={};'.format( self.tables_storage_account_name, self.tables_primary_storage_account_key, custom_account_url) # Act service = service_type[0].from_connection_string(conn_string, table_name="foo") # Assert assert service.account_name == self.tables_storage_account_name assert service.credential.account_name == self.tables_storage_account_name assert service.credential.account_key == self.tables_primary_storage_account_key assert service._primary_hostname == 'local-machine:11002/custom/account/path' service = TableServiceClient(account_url=custom_account_url) assert service.account_name == "custom" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' assert service.url.startswith('http://local-machine:11002/custom/account/path') service = TableClient(account_url=custom_account_url, table_name="foo") assert service.account_name == "custom" assert service.table_name == "foo" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' assert service.url.startswith('http://local-machine:11002/custom/account/path') service = TableClient.from_table_url("http://local-machine:11002/custom/account/path/foo" + token) assert service.account_name == "custom" assert service.table_name == "foo" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' assert service.url.startswith('http://local-machine:11002/custom/account/path')
async def test_create_service_with_custom_account_endpoint_path_async(self, resource_group, location, cosmos_account, cosmos_account_key): custom_account_url = "http://local-machine:11002/custom/account/path/" + self.sas_token for service_type in SERVICES.items(): conn_string = 'DefaultEndpointsProtocol=http;AccountName={};AccountKey={};TableEndpoint={};'.format( cosmos_account.name, cosmos_account_key, custom_account_url) # Act service = service_type[0].from_connection_string(conn_string, table_name="foo") # Assert assert service.account_name == cosmos_account.name assert service.credential.account_name == cosmos_account.name assert service.credential.account_key == cosmos_account_key assert service._primary_hostname == 'local-machine:11002/custom/account/path' service = TableServiceClient(account_url=custom_account_url) assert service.account_name == None assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' # mine doesnt have a question mark at the end assert service.url.startswith('http://local-machine:11002/custom/account/path') service = TableClient(account_url=custom_account_url, table_name="foo") assert service.account_name == None assert service.table_name == "foo" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' assert service.url.startswith('http://local-machine:11002/custom/account/path') service = TableClient.from_table_url("http://local-machine:11002/custom/account/path/foo" + self.sas_token) assert service.account_name == None assert service.table_name == "foo" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' assert service.url.startswith('http://local-machine:11002/custom/account/path')
def test_create_client_for_cosmos_emulator(self): emulator_credential = AzureNamedKeyCredential( 'localhost', self.tables_primary_cosmos_account_key) emulator_connstr = "DefaultEndpointsProtocol=http;AccountName=localhost;AccountKey={};TableEndpoint=http://localhost:8902/;".format( self.tables_primary_cosmos_account_key) client = TableServiceClient.from_connection_string(emulator_connstr) assert client.url == "http://localhost:8902" assert client.account_name == 'localhost' assert client.credential.named_key.name == 'localhost' assert client.credential.named_key.key == self.tables_primary_cosmos_account_key assert client._cosmos_endpoint client = TableServiceClient("http://localhost:8902/", credential=emulator_credential) assert client.url == "http://localhost:8902" assert client.account_name == 'localhost' assert client.credential.named_key.name == 'localhost' assert client.credential.named_key.key == self.tables_primary_cosmos_account_key assert client._cosmos_endpoint table = TableClient.from_connection_string(emulator_connstr, 'tablename') assert table.url == "http://localhost:8902" assert table.account_name == 'localhost' assert table.table_name == 'tablename' assert table.credential.named_key.name == 'localhost' assert table.credential.named_key.key == self.tables_primary_cosmos_account_key assert table._cosmos_endpoint table = TableClient("http://localhost:8902/", "tablename", credential=emulator_credential) assert table.url == "http://localhost:8902" assert table.account_name == 'localhost' assert table.table_name == 'tablename' assert table.credential.named_key.name == 'localhost' assert table.credential.named_key.key == self.tables_primary_cosmos_account_key assert table._cosmos_endpoint table = TableClient.from_table_url( "http://localhost:8902/Tables('tablename')", credential=emulator_credential) assert table.url == "http://localhost:8902" assert table.account_name == 'localhost' assert table.table_name == 'tablename' assert table.credential.named_key.name == 'localhost' assert table.credential.named_key.key == self.tables_primary_cosmos_account_key assert table._cosmos_endpoint
async def sample_batching(self): # Instantiate a TableServiceClient using a connection string # [START batching] from azure.data.tables.aio import TableClient from azure.data.tables import UpdateMode, BatchErrorException from azure.core.exceptions import ResourceExistsError self.table_client = TableClient.from_connection_string( conn_str=self.connection_string, table_name=self.table_name) try: await self.table_client.create_table() print("Created table") except ResourceExistsError: print("Table already exists") await self._create_entities() batch = self.table_client.create_batch() batch.create_entity(self.entity1) batch.delete_entity(partition_key=self.entity2['PartitionKey'], row_key=self.entity2['RowKey']) batch.upsert_entity(self.entity3) batch.update_entity(self.entity4, mode=UpdateMode.REPLACE) try: await self.table_client.send_batch(batch) except BatchErrorException as e: print("There was an error with the batch operation") print("Error: {}".format(e))
async def create_and_get_entities(self): # Instantiate a table service client from azure.data.tables.aio import TableClient table = TableClient.from_connection_string(self.connection_string, table_name=self.table_base + "create") async with table: await table.create_table() my_entity = { "PartitionKey": "color", "RowKey": "crayola", "text": "Marker", "color": "Purple", "price": "5", } try: created_entity = await table.create_entity(entity=my_entity) print("Created entity: {}".format(created_entity)) # [START get_entity] # Get Entity by partition and row key got_entity = await table.get_entity( partition_key=my_entity["PartitionKey"], row_key=my_entity["RowKey"]) print("Received entity: {}".format(got_entity)) # [END get_entity] finally: await table.delete_table()
async def insert_random_entities(self): from azure.data.tables.aio import TableClient from azure.core.exceptions import ResourceExistsError brands = ["Crayola", "Sharpie", "Chameleon"] colors = ["red", "blue", "orange", "yellow"] names = ["marker", "pencil", "pen"] entity_template = { "PartitionKey": "pk", "RowKey": "row", } table_client = TableClient.from_connection_string(self.connection_string, self.table_name) async with table_client: try: await table_client.create_table() except ResourceExistsError: print("Table already exists") for i in range(25): e = copy.deepcopy(entity_template) e["RowKey"] += str(i) e["Name"] = random.choice(names) e["Brand"] = random.choice(brands) e["Color"] = random.choice(colors) e["Value"] = random.randint(0, 100) await table_client.create_entity(entity=e)
async def create_table_client(self): # Instantiate a TableServiceClient using a connection string # [START create_table_client] from azure.data.tables.aio import TableClient table_client = TableClient.from_connection_string( conn_str=self.connection_string, table_name="tableName") print("Table name: {}".format(table_client.table_name))
async def delete_entity(self): from azure.data.tables.aio import TableClient from azure.core.exceptions import ResourceNotFoundError, ResourceExistsError from azure.core.credentials import AzureNamedKeyCredential credential = AzureNamedKeyCredential(self.account_name, self.access_key) table_client = TableClient(account_url=self.account_url, credential=credential, table_name=self.table_name) # [START delete_entity] async with table_client: try: resp = await table_client.create_entity(entity=self.entity) except ResourceExistsError: print("Entity already exists!") try: await table_client.delete_entity( row_key=self.entity["RowKey"], partition_key=self.entity["PartitionKey"]) print("Successfully deleted!") except ResourceNotFoundError: print("Entity does not exists")
async def test_table_name_errors(self, tables_storage_account_name, tables_primary_storage_account_key): endpoint = self.account_url(tables_storage_account_name, "table") # storage table names must be alphanumeric, cannot begin with a number, and must be between 3 and 63 chars long. invalid_table_names = ["1table", "a"*2, "a"*64, "a//", "my_table"] for invalid_name in invalid_table_names: client = TableClient( endpoint=endpoint, credential=tables_primary_storage_account_key, table_name=invalid_name) async with client: with pytest.raises(ValueError) as error: await client.create_table() assert 'Storage table names must be alphanumeric' in str(error.value) with pytest.raises(ValueError) as error: await client.create_entity({'PartitionKey': 'foo', 'RowKey': 'bar'}) assert 'Storage table names must be alphanumeric' in str(error.value) with pytest.raises(ValueError) as error: await client.upsert_entity({'PartitionKey': 'foo', 'RowKey': 'foo'}) assert 'Storage table names must be alphanumeric' in str(error.value) with pytest.raises(ValueError) as error: await client.delete_entity("PK", "RK") assert 'Storage table names must be alphanumeric' in str(error.value) with pytest.raises(ValueError) as error: await client.get_table_access_policy() assert 'Storage table names must be alphanumeric' in str(error.value) with pytest.raises(ValueError) as error: batch = [] batch.append(('upsert', {'PartitionKey': 'A', 'RowKey': 'B'})) await client.submit_transaction(batch) assert 'Storage table names must be alphanumeric' in str(error.value)
async def list_all_entities(self): # Instantiate a table service client from azure.data.tables.aio import TableClient table = TableClient.from_connection_string( self.connection_string, table_name=self.table_base + "list") # Create the table async with table: await table.create_table() entity = {'PartitionKey': 'color2', 'RowKey': 'sharpie', 'text': 'Marker', 'color': 'Purple', 'price': '5'} entity1 = {'PartitionKey': 'color2', 'RowKey': 'crayola', 'text': 'Marker', 'color': 'Red', 'price': '3'} try: # Create entities await table.create_entity(entity=entity) await table.create_entity(entity=entity1) # [START list_entities] # Query the entities in the table entities = [] async for e in table.list_entities(): entities.append(e) for i, entity in enumerate(entities): print("Entity #{}: {}".format(entity, i)) # [END list_entities] finally: await table.delete_table()
async def sample_transaction(self): # Instantiate a TableServiceClient using a connection string # [START batching] from azure.data.tables.aio import TableClient from azure.data.tables import TableTransactionError from azure.core.exceptions import ResourceExistsError self.table_client = TableClient.from_connection_string( conn_str=self.connection_string, table_name=self.table_name) try: await self.table_client.create_table() print("Created table") except ResourceExistsError: print("Table already exists") await self._create_entities() operations = [('create', self.entity1), ('delete', self.entity2), ('upsert', self.entity3), ('update', self.entity4, { 'mode': 'replace' })] try: await self.table_client.submit_transaction(operations) except TableTransactionError as e: print("There was an error with the transaction operation") print("Error: {}".format(e))
async def test_table_name_errors_bad_chars(self, tables_cosmos_account_name, tables_primary_cosmos_account_key): endpoint = self.account_url(tables_cosmos_account_name, "cosmos") # cosmos table names must be a non-empty string without chars '\', '/', '#', '?', and less than 255 chars. invalid_table_names = ["\\", "//", "#", "?", "- "] for invalid_name in invalid_table_names: client = TableClient( endpoint=endpoint, credential=tables_primary_cosmos_account_key, table_name=invalid_name) async with client: with pytest.raises(ValueError) as error: await client.create_table() assert "Cosmos table names must contain from 1-255 characters" in str(error.value) try: with pytest.raises(ValueError) as error: await client.delete_table() assert "Cosmos table names must contain from 1-255 characters" in str(error.value) except HttpResponseError as error: # Delete table returns a MethodNotAllowed for tablename == "\" if error.error_code != 'MethodNotAllowed': raise with pytest.raises(ValueError) as error: await client.create_entity({'PartitionKey': 'foo', 'RowKey': 'foo'}) assert "Cosmos table names must contain from 1-255 characters" in str(error.value) with pytest.raises(ValueError) as error: await client.upsert_entity({'PartitionKey': 'foo', 'RowKey': 'foo'}) assert "Cosmos table names must contain from 1-255 characters" in str(error.value) with pytest.raises(ValueError) as error: await client.delete_entity("PK", "RK") assert "Cosmos table names must contain from 1-255 characters" in str(error.value) with pytest.raises(ValueError) as error: batch = [] batch.append(('upsert', {'PartitionKey': 'A', 'RowKey': 'B'})) await client.submit_transaction(batch) assert "Cosmos table names must contain from 1-255 characters" in str(error.value)
async def create_and_get_entities(self): # Instantiate a table service client from azure.data.tables.aio import TableClient table = TableClient.from_connection_string( self.connection_string, table_name=self.table_base + "create") async with table: await table.create_table() my_entity = { 'PartitionKey': 'color', 'RowKey': 'crayola', 'text': 'Marker', 'color': 'Purple', 'price': '5' } try: created_entity = await table.create_entity(entity=my_entity) print("Created entity: {}".format(created_entity)) # [START get_entity] # Get Entity by partition and row key got_entity = await table.get_entity( partition_key=my_entity['PartitionKey'], row_key=my_entity['RowKey'] ) print("Received entity: {}".format(got_entity)) # [END get_entity] finally: await table.delete_table()
async def test_create_service_with_custom_account_endpoint_path_async( self): self.sas_token = self.generate_sas_token() self.sas_token = AzureSasCredential(self.sas_token) custom_account_url = "http://local-machine:11002/custom/account/path/" + self.sas_token.signature for service_type in SERVICES.items(): conn_string = 'DefaultEndpointsProtocol=http;AccountName={};AccountKey={};TableEndpoint={};'.format( self.tables_cosmos_account_name, self.tables_primary_cosmos_account_key, custom_account_url) # Act service = service_type[0].from_connection_string(conn_string, table_name="foo") # Assert assert service.account_name == self.tables_cosmos_account_name assert service.credential.named_key.name == self.tables_cosmos_account_name assert service.credential.named_key.key == self.tables_primary_cosmos_account_key assert service._primary_hostname == 'local-machine:11002/custom/account/path' service = TableServiceClient(endpoint=custom_account_url) assert service.account_name == "custom" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' # mine doesnt have a question mark at the end assert service.url.startswith( 'http://local-machine:11002/custom/account/path') service = TableClient(endpoint=custom_account_url, table_name="foo") assert service.account_name == "custom" assert service.table_name == "foo" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' assert service.url.startswith( 'http://local-machine:11002/custom/account/path') service = TableClient.from_table_url( "http://local-machine:11002/custom/account/path/foo" + self.sas_token.signature) assert service.account_name == "custom" assert service.table_name == "foo" assert service.credential == None assert service._primary_hostname == 'local-machine:11002/custom/account/path' assert service.url.startswith( 'http://local-machine:11002/custom/account/path')
async def test_create_table_client_with_complete_url_async(self): # Arrange table_url = "https://{}.table.core.windows.net:443/foo".format(self.tables_storage_account_name) service = TableClient(endpoint=table_url, table_name='bar', credential=self.credential) # Assert assert service.scheme == 'https' assert service.table_name == 'bar' assert service.account_name == self.tables_storage_account_name
async def test_create_table_client_with_complete_url_async(self, resource_group, location, storage_account, storage_account_key): # Arrange table_url = "https://{}.table.core.windows.net:443/foo".format(storage_account.name) service = TableClient(account_url=table_url, table_name='bar', credential=storage_account_key) # Assert self.assertEqual(service.scheme, 'https') self.assertEqual(service.table_name, 'bar') self.assertEqual(service.account_name, storage_account.name)
async def test_create_table_client_with_complete_table_url_async(self, resource_group, location, storage_account, storage_account_key): # Arrange table_url = self.account_url(storage_account, "table") + "/foo" service = TableClient(table_url, table_name='bar', credential=storage_account_key) # Assert self.assertEqual(service.scheme, 'https') self.assertEqual(service.table_name, 'bar') self.assertEqual(service.account_name, storage_account.name)
async def test_create_table_client_with_complete_url_async(self): # Arrange table_url = "https://{}.table.cosmos.azure.com:443/foo".format(self.tables_cosmos_account_name) service = TableClient(table_url, table_name='bar', credential=self.credential) # Assert assert service.scheme == 'https' assert service.table_name == 'bar' assert service.account_name == self.tables_cosmos_account_name
async def test_create_table_client_with_complete_table_url_async(self, resource_group, location, cosmos_account, cosmos_account_key): # Arrange table_url = self.account_url(cosmos_account, "cosmos") + "/foo" service = TableClient(table_url, table_name='bar', credential=cosmos_account_key) # Assert assert service.scheme == 'https' assert service.table_name == 'bar' assert service.account_name == cosmos_account.name
async def test_create_table_client_with_complete_url_async(self, resource_group, location, cosmos_account, cosmos_account_key): # Arrange table_url = "https://{}.table.cosmos.azure.com:443/foo".format(cosmos_account.name) service = TableClient(table_url, table_name='bar', credential=cosmos_account_key) # Assert assert service.scheme == 'https' assert service.table_name == 'bar' assert service.account_name == cosmos_account.name
async def test_create_table_client_with_complete_table_url_async(self): # Arrange table_url = self.account_url(self.tables_storage_account_name, "table") + "/foo" service = TableClient(table_url, table_name='bar', credential=self.credential) # Assert assert service.scheme == 'https' assert service.table_name == 'bar' assert service.account_name == self.tables_storage_account_name
async def test_create_table_client_with_invalid_name_async(self): # Arrange table_url = "https://{}.table.core.windows.net:443/foo".format("storage_account_name") invalid_table_name = "my_table" # Assert with pytest.raises(ValueError) as excinfo: service = TableClient(endpoint=table_url, table_name=invalid_table_name, credential="self.tables_primary_storage_account_key") assert "Table names must be alphanumeric, cannot begin with a number, and must be between 3-63 characters long."in str(excinfo)
async def delete_from_table_client(self): from azure.data.tables.aio import TableClient from azure.core.exceptions import HttpResponseError # [START delete_from_table_client] async with TableClient.from_connection_string( conn_str=self.connection_string, table_name=self.table_name) as table_client: await table_client.delete_table() print("Deleted table {}!".format(self.table_name))
async def test_create_table_client_with_invalid_name_async(self): # Arrange table_url = "https://{}.table.cosmos.azure.com:443/foo".format("cosmos_account_name") invalid_table_name = "my_table" # Assert with pytest.raises(ValueError) as excinfo: service = TableClient(account_url=table_url, table_name=invalid_table_name, credential="cosmos_account_key") assert "Table names must be alphanumeric, cannot begin with a number, and must be between 3-63 characters long.""" in str(excinfo)
async def create_from_table_client(self): from azure.data.tables.aio import TableClient # [START create_from_table_client] async with TableClient.from_connection_string(conn_str=self.connection_string, table_name=self.table_name) as table_client: try: table_item = await table_client.create_table() print("Created table {}!".format(table_item.table_name)) except ResourceExistsError: print("Table already exists")
async def delete_from_table_client(self): from azure.data.tables.aio import TableClient from azure.core.exceptions import ResourceNotFoundError # [START delete_from_table_client] async with TableClient.from_connection_string(conn_str=self.connection_string, table_name=self.table_name) as table_client: try: await table_client.delete_table() print("Deleted table {}!".format(self.table_name)) except ResourceNotFoundError: print("Table could not be found")
async def test_aad_access_policy_error(self, tables_storage_account_name): account_url = self.account_url(tables_storage_account_name, "table") table_name = self._get_table_reference() table_client = TableClient(credential=self.get_token_credential(), endpoint=account_url, table_name=table_name) with pytest.raises(HttpResponseError): await table_client.get_table_access_policy() with pytest.raises(HttpResponseError): await table_client.set_table_access_policy(signed_identifiers={})
async def update_entities(self): # Instantiate a table service client from azure.data.tables.aio import TableClient from azure.data.tables import UpdateMode table = TableClient.from_connection_string( self.connection_string, table_name=self.table_base + "update") # Create the table and Table Client async with table: await table.create_table() entity = {'PartitionKey': 'color', 'RowKey': 'sharpie', 'text': 'Marker', 'color': 'Purple', 'price': '5'} entity1 = {'PartitionKey': 'color2', 'RowKey': 'crayola', 'text': 'Marker', 'color': 'Red', 'price': '3'} try: # Create entities await table.create_entity(entity=entity) created = await table.get_entity(partition_key=entity["PartitionKey"], row_key=entity["RowKey"]) # [START upsert_entity] # Try Replace and then Insert on Fail insert_entity = await table.upsert_entity(mode=UpdateMode.REPLACE, entity=entity1) print("Inserted entity: {}".format(insert_entity)) # Try merge, and merge since already in table created['text'] = "NewMarker" merged_entity = await table.upsert_entity(mode=UpdateMode.MERGE, entity=entity) print("Merged entity: {}".format(merged_entity)) # [END upsert_entity] # [START update_entity] # Update the entity created['text'] = "NewMarker" await table.update_entity(mode=UpdateMode.REPLACE, entity=created) # Get the replaced entity replaced = await table.get_entity( partition_key=created['PartitionKey'], row_key=created['RowKey']) print("Replaced entity: {}".format(replaced)) # Merge the entity replaced['color'] = "Blue" await table.update_entity(mode=UpdateMode.MERGE, entity=replaced) # Get the merged entity merged = await table.get_entity( partition_key=replaced['PartitionKey'], row_key=replaced['RowKey']) print("Merged entity: {}".format(merged)) # [END update_entity] finally: await table.delete_table()
async def test_create_table_client_with_complete_table_url_async(self): # Arrange table_url = self.account_url(self.tables_cosmos_account_name, "cosmos") + "/foo" service = TableClient( table_url, table_name='bar', credential=self.tables_primary_cosmos_account_key) # Assert assert service.scheme == 'https' assert service.table_name == 'bar' assert service.account_name == self.tables_cosmos_account_name