From 28742e53a4ce600b8aefc65e2b968bcc04d56cbe Mon Sep 17 00:00:00 2001 From: Alfredo Deza Date: Wed, 19 Nov 2014 15:08:42 -0500 Subject: [PATCH] tests for sync_object in worker.py Signed-off-by: Alfredo Deza --- radosgw_agent/tests/test_worker.py | 115 +++++++++++++++++++++++++++++ 1 file changed, 115 insertions(+) create mode 100644 radosgw_agent/tests/test_worker.py diff --git a/radosgw_agent/tests/test_worker.py b/radosgw_agent/tests/test_worker.py new file mode 100644 index 0000000..da5372d --- /dev/null +++ b/radosgw_agent/tests/test_worker.py @@ -0,0 +1,115 @@ +from mock import Mock, patch +import py.test + +from radosgw_agent import worker, client + + +class TestSyncObject(object): + + def setup(self): + # setup the fake client, but get the exceptions back into place + self.client = Mock() + self.client.HttpError = client.HttpError + self.client.NotFound = client.NotFound + + self.src = Mock() + self.src.zone.name = 'Zone Name' + self.src.host = 'example.com' + + def test_syncs_correctly(self): + with patch('radosgw_agent.worker.client'): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + assert w.sync_object('mah-bucket', 'mah-object') is True + + def test_syncs_not_found_on_master_deleting_from_secondary(self): + self.client.sync_object_intra_region = Mock(side_effect=client.NotFound(404, '')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + w.wait_for_object = lambda *a: None + assert w.sync_object('mah-bucket', 'mah-object') is True + + def test_syncs_deletes_from_secondary(self): + self.client.sync_object_intra_region = Mock(side_effect=client.NotFound(404, '')) + self.client.delete_object = Mock(side_effect=client.NotFound(404, '')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + w.wait_for_object = lambda *a: None + assert w.sync_object('mah-bucket', 'mah-object') is False + + def test_syncs_could_not_delete_from_secondary(self): + self.client.sync_object_intra_region = Mock(side_effect=client.NotFound(404, '')) + self.client.delete_object = Mock(side_effect=ValueError('unexpected error')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + w.wait_for_object = lambda *a: None + + with py.test.raises(worker.SyncFailed): + w.sync_object('mah-bucket', 'mah-object') + + def test_syncs_encounters_a_transient_http_error(self): + self.client.sync_object_intra_region = Mock(side_effect=client.HttpError(400, '')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + w.wait_for_object = lambda *a: None + + with py.test.raises(worker.SyncFailed) as exc: + w.sync_object('mah-bucket', 'mah-object') + + exc_message = exc.value[0] + assert 'HTTP error with status: 400' in exc_message + + def test_sync_client_raises_sync_failed(self): + self.client.sync_object_intra_region = Mock(side_effect=worker.SyncFailed('failed intra region')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + + with py.test.raises(worker.SyncFailed) as exc: + w.sync_object('mah-bucket', 'mah-object') + + exc_message = exc.value[0] + assert 'failed intra region' in exc_message + + def test_syncs_encounters_a_critical_http_error(self): + self.client.sync_object_intra_region = Mock(side_effect=client.HttpError(500, 'Internal Server Error')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + w.wait_for_object = lambda *a: None + + with py.test.raises(client.HttpError) as exc: + w.sync_object('mah-bucket', 'mah-object') + + exc_message = exc.exconly() + assert 'error code 500 content Internal Server Error' in exc_message + + def test_fails_to_remove_op_state(self, capsys): + # really tricky to test this one, we are forced to just use `capsys` from py.test + # which will allow us to check into the stderr logging output and see if the agent + # was spitting what we are expecting. + self.client.remove_op_state = Mock(side_effect=ValueError('could not remove op')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + w.wait_for_object = lambda *a: None + assert w.sync_object('mah-bucket', 'mah-object') is True + # logging does not play nice and so we are forced to comment this out. + # this test does test the right thing, but we are unable to have a nice + # assertion, the fix here is not the test it is the code that needs to + # improve. For now, this just + # gives us the coverage. + # out, err = capsys.readouterr() + # assert 'could not remove op state' in out + # assert 'could not remove op state' in err + + def test_fails_to_do_anything_fallsback_to_wait_for_object(self): + self.client.sync_object_intra_region = Mock(side_effect=ValueError('severe error')) + + with patch('radosgw_agent.worker.client', self.client): + w = worker.DataWorker(None, None, None, self.src, None, daemon_id=1) + w.wait_for_object = lambda *a: None + assert w.sync_object('mah-bucket', 'mah-object') is True -- 2.47.3