def test_long_running_delete(self): # Test polling from azure-asyncoperation header response = TestArmPolling.mock_send( 'DELETE', 202, {'azure-asyncoperation': ASYNC_URL}, body="") poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) poll.wait() assert poll.result() is None assert poll._polling_method._response.randomFieldFromPollAsyncOpHeader is None
def wait_poller(service_client, operation_config, response): def get_long_running_output(response): return response poller = LROPoller(service_client, ClientRawResponse(None, response), get_long_running_output, ARMPolling(30, **operation_config)) try: poller.wait(timeout=600) response = poller.result() except Exception as exc: raise return response
def test_lro_happy_paths(self, special_client): client = special_client product = Product(location="West US") process = self.lro_result(client.lr_os.put201_creating_succeeded200, product) assert "Succeeded" == process.provisioning_state # Test manual poller raw_process = client.lr_os.put201_creating_succeeded200( product, raw=True, polling=False).result() poller = LROPoller(client, raw_process, Product, ARMPolling(timeout=0)) process = poller.result() assert "Succeeded" == process.provisioning_state self.assertRaisesWithMessage( "Operation failed with status: 200. Details: Resource state Failed", client.lr_os.put201_creating_failed200, product) process = self.lro_result(client.lr_os.put200_updating_succeeded204, product) assert "Succeeded" == process.provisioning_state self.assertRaisesWithMessage( "Operation failed with status: 200. Details: Resource state Canceled", client.lr_os.put200_acceptedcanceled200, product) # Testing nopolling process = self.lro_result(client.lr_os.put201_creating_succeeded200, product, polling=False) assert "Creating" == process.provisioning_state process = self.lro_result(client.lr_os.put201_creating_failed200, product, polling=False) assert "Created" == process.provisioning_state process = self.lro_result(client.lr_os.put200_updating_succeeded204, product, polling=False) assert "Updating" == process.provisioning_state process = self.lro_result(client.lr_os.put200_acceptedcanceled200, product, polling=False) assert "Accepted" == process.provisioning_state # Testing nopolling and raw at the same time process = self.lro_result(client.lr_os.put201_creating_succeeded200, product, raw=True, polling=False) assert "Creating" == process.output.provisioning_state process = self.lro_result(client.lr_os.put201_creating_failed200, product, raw=True, polling=False) assert "Created" == process.output.provisioning_state process = self.lro_result(client.lr_os.put200_updating_succeeded204, product, raw=True, polling=False) assert "Updating" == process.output.provisioning_state process = self.lro_result(client.lr_os.put200_acceptedcanceled200, product, raw=True, polling=False) assert "Accepted" == process.output.provisioning_state process = self.lro_result(client.lr_os.put_no_header_in_retry, product) assert "Succeeded" == process.provisioning_state process = self.lro_result(client.lr_os.put_async_no_header_in_retry, product) assert "Succeeded" == process.provisioning_state process = self.lro_result(client.lr_os.put_sub_resource, SubProduct()) assert "Succeeded" == process.provisioning_state process = self.lro_result(client.lr_os.put_async_sub_resource, SubProduct()) assert "Succeeded" == process.provisioning_state process = self.lro_result(client.lr_os.put_non_resource, Sku()) assert "100" == process.id process = self.lro_result(client.lr_os.put_async_non_resource, Sku()) assert "100" == process.id process = self.lro_result(client.lr_os.post202_retry200, product) assert process is None process = self.lro_result(client.lr_os.put200_succeeded, product) assert "Succeeded" == process.provisioning_state process = self.lro_result(client.lr_os.put200_succeeded_no_state, product) assert "100" == process.id process = self.lro_result(client.lr_os.put202_retry200, product) assert "100" == process.id process = self.lro_result(client.lr_os.put_async_retry_succeeded, product) assert "Succeeded" == process.provisioning_state process = self.lro_result(client.lr_os.put_async_no_retry_succeeded, product) assert "Succeeded" == process.provisioning_state self.assertRaisesWithMessage( "Operation failed with status: 200. Details: Resource state Failed", client.lr_os.put_async_retry_failed, product) self.assertRaisesWithMessage( "Operation failed with status: 200. Details: Resource state Canceled", client.lr_os.put_async_no_retrycanceled, product) assert self.lro_result(client.lr_os.delete204_succeeded) is None assert self.lro_result(client.lr_os.delete202_retry200) is None assert self.lro_result(client.lr_os.delete202_no_retry204) is None assert self.lro_result( client.lr_os.delete_async_no_retry_succeeded) is None assert self.lro_result(client.lr_os.delete_no_header_in_retry) is None assert self.lro_result( client.lr_os.delete_async_no_header_in_retry) is None self.assertRaisesWithMessage( "Operation failed with status: 200. Details: Resource state Canceled", client.lr_os.delete_async_retrycanceled) self.assertRaisesWithMessage( "Operation failed with status: 200. Details: Resource state Failed", client.lr_os.delete_async_retry_failed) assert self.lro_result( client.lr_os.delete_async_retry_succeeded) is None process = self.lro_result( client.lr_os.delete_provisioning202_accepted200_succeeded) assert "Succeeded" == process.provisioning_state result = self.lro_result( client.lr_os.delete_provisioning202_deletingcanceled200) assert result.provisioning_state == 'Canceled' result = self.lro_result( client.lr_os.delete_provisioning202_deleting_failed200) assert result.provisioning_state == 'Failed' assert self.lro_result(client.lr_os.post202_no_retry204, product) is None self.assertRaisesWithMessage("Internal Server Error", client.lr_os.post_async_retry_failed) self.assertRaisesWithMessage( "Operation failed with status: 200. Details: Resource state Canceled", client.lr_os.post_async_retrycanceled) prod = self.lro_result(client.lr_os.post_async_retry_succeeded) assert prod.id == "100" prod = self.lro_result(client.lr_os.post_async_no_retry_succeeded) assert prod.id == "100" sku = self.lro_result(client.lr_os.post200_with_payload) assert sku.id == '1' process = self.lro_result( client.lro_retrys.put201_creating_succeeded200, product) assert 'Succeeded' == process.provisioning_state process = self.lro_result( client.lro_retrys.put_async_relative_retry_succeeded, product) assert 'Succeeded' == process.provisioning_state process = self.lro_result( client.lro_retrys.delete_provisioning202_accepted200_succeeded) assert 'Succeeded' == process.provisioning_state assert self.lro_result(client.lro_retrys.delete202_retry200) is None assert self.lro_result( client.lro_retrys.delete_async_relative_retry_succeeded) is None assert self.lro_result(client.lro_retrys.post202_retry200, product) is None assert self.lro_result( client.lro_retrys.post_async_relative_retry_succeeded, product) is None custom_headers = { "x-ms-client-request-id": '9C4D50EE-2D56-4CD3-8152-34347DC9F2B0' } process = self.lro_result( client.lr_os_custom_header.put_async_retry_succeeded, product, custom_headers) assert process is not None process = self.lro_result( client.lr_os_custom_header.post_async_retry_succeeded, product, custom_headers) assert process is None process = self.lro_result( client.lr_os_custom_header.put201_creating_succeeded200, product, custom_headers) assert process is not None process = self.lro_result(client.lr_os_custom_header.post202_retry200, product, custom_headers) assert process is None
def test_long_running_post(self): # Test POST LRO with both Location and Azure-AsyncOperation # The initial response contains both Location and Azure-AsyncOperation, a 202 and no Body response = TestArmPolling.mock_send( 'POST', 202, { 'location': 'http://example.org/location', 'azure-asyncoperation': 'http://example.org/async_monitor', }, '') class TestServiceClient(ServiceClient): def __init__(self): ServiceClient.__init__(self, None, Configuration("http://example.org")) def send(self, request, headers=None, content=None, **config): assert request.method == 'GET' if request.url == 'http://example.org/location': return TestArmPolling.mock_send( 'GET', 200, body={'location_result': True}) elif request.url == 'http://example.org/async_monitor': return TestArmPolling.mock_send( 'GET', 200, body={'status': 'Succeeded'}) else: pytest.fail("No other query allowed") def deserialization_cb(response): return response.json() # Test 1, LRO options with Location final state poll = LROPoller( TestServiceClient(), response, deserialization_cb, ARMPolling(0, lro_options={"final-state-via": "location"})) result = poll.result() assert result['location_result'] == True # Test 2, LRO options with Azure-AsyncOperation final state poll = LROPoller( TestServiceClient(), response, deserialization_cb, ARMPolling( 0, lro_options={"final-state-via": "azure-async-operation"})) result = poll.result() assert result['status'] == 'Succeeded' # Test 3, backward compat (no options, means "azure-async-operation") poll = LROPoller(TestServiceClient(), response, deserialization_cb, ARMPolling(0)) result = poll.result() assert result['status'] == 'Succeeded' # Test 4, location has no body class TestServiceClientNoBody(ServiceClient): def __init__(self): ServiceClient.__init__(self, None, Configuration("http://example.org")) def send(self, request, headers=None, content=None, **config): assert request.method == 'GET' if request.url == 'http://example.org/location': return TestArmPolling.mock_send('GET', 200, body="") elif request.url == 'http://example.org/async_monitor': return TestArmPolling.mock_send( 'GET', 200, body={'status': 'Succeeded'}) else: pytest.fail("No other query allowed") poll = LROPoller( TestServiceClientNoBody(), response, deserialization_cb, ARMPolling(0, lro_options={"final-state-via": "location"})) result = poll.result() assert result is None # Former oooooold tests to refactor one day to something more readble # Test throw on non LRO related status code response = TestArmPolling.mock_send('POST', 201, {}) op = LongRunningOperation(response, lambda x: None) with pytest.raises(BadStatus): op.set_initial_status(response) with pytest.raises(CloudError): LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result() # Test polling from azure-asyncoperation header response = TestArmPolling.mock_send( 'POST', 202, {'azure-asyncoperation': ASYNC_URL}, body={'properties': { 'provisioningState': 'Succeeded' }}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) poll.wait() #self.assertIsNone(poll.result()) assert poll._polling_method._response.randomFieldFromPollAsyncOpHeader is None # Test polling from location header response = TestArmPolling.mock_send( 'POST', 202, {'location': LOCATION_URL}, body={'properties': { 'provisioningState': 'Succeeded' }}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert poll._polling_method._response.randomFieldFromPollLocationHeader is None # Test fail to poll from azure-asyncoperation header response = TestArmPolling.mock_send('POST', 202, {'azure-asyncoperation': ERROR}) with pytest.raises(BadEndpointError): poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result() # Test fail to poll from location header response = TestArmPolling.mock_send('POST', 202, {'location': ERROR}) with pytest.raises(BadEndpointError): poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result()
def test_long_running_patch(self): # Test polling from location header response = TestArmPolling.mock_send( 'PATCH', 202, {'location': LOCATION_URL}, body={'properties': { 'provisioningState': 'Succeeded' }}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert poll._polling_method._response.randomFieldFromPollLocationHeader is None # Test polling from azure-asyncoperation header response = TestArmPolling.mock_send( 'PATCH', 202, {'azure-asyncoperation': ASYNC_URL}, body={'properties': { 'provisioningState': 'Succeeded' }}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert not hasattr(poll._polling_method._response, 'randomFieldFromPollAsyncOpHeader') # Test polling from location header response = TestArmPolling.mock_send( 'PATCH', 200, {'location': LOCATION_URL}, body={'properties': { 'provisioningState': 'Succeeded' }}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert poll._polling_method._response.randomFieldFromPollLocationHeader is None # Test polling from azure-asyncoperation header response = TestArmPolling.mock_send( 'PATCH', 200, {'azure-asyncoperation': ASYNC_URL}, body={'properties': { 'provisioningState': 'Succeeded' }}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert not hasattr(poll._polling_method._response, 'randomFieldFromPollAsyncOpHeader') # Test fail to poll from azure-asyncoperation header response = TestArmPolling.mock_send('PATCH', 202, {'azure-asyncoperation': ERROR}) with pytest.raises(BadEndpointError): poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result() # Test fail to poll from location header response = TestArmPolling.mock_send('PATCH', 202, {'location': ERROR}) with pytest.raises(BadEndpointError): poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result()
def test_long_running_put(self): #TODO: Test custom header field # Test throw on non LRO related status code response = TestArmPolling.mock_send('PUT', 1000, {}) op = LongRunningOperation(response, lambda x: None) with pytest.raises(BadStatus): op.set_initial_status(response) with pytest.raises(CloudError): LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result() # Test with no polling necessary response_body = { 'properties': { 'provisioningState': 'Succeeded' }, 'name': TEST_NAME } response = TestArmPolling.mock_send('PUT', 201, {}, response_body) def no_update_allowed(url, headers=None): raise ValueError("Should not try to update") poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert not hasattr(poll._polling_method._response, 'randomFieldFromPollAsyncOpHeader') # Test polling from azure-asyncoperation header response = TestArmPolling.mock_send( 'PUT', 201, {'azure-asyncoperation': ASYNC_URL}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert not hasattr(poll._polling_method._response, 'randomFieldFromPollAsyncOpHeader') # Test polling location header response = TestArmPolling.mock_send('PUT', 201, {'location': LOCATION_URL}) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert poll._polling_method._response.randomFieldFromPollLocationHeader is None # Test polling initial payload invalid (SQLDb) response_body = {} # Empty will raise response = TestArmPolling.mock_send('PUT', 201, {'location': LOCATION_URL}, response_body) poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)) assert poll.result().name == TEST_NAME assert poll._polling_method._response.randomFieldFromPollLocationHeader is None # Test fail to poll from azure-asyncoperation header response = TestArmPolling.mock_send('PUT', 201, {'azure-asyncoperation': ERROR}) with pytest.raises(BadEndpointError): poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result() # Test fail to poll from location header response = TestArmPolling.mock_send('PUT', 201, {'location': ERROR}) with pytest.raises(BadEndpointError): poll = LROPoller(CLIENT, response, TestArmPolling.mock_outputs, ARMPolling(0)).result()