Add functional test for OverQuota

Since we now have checks for OverLimit on both volume and snapshot
creation, we need to check and make sure OverQuota is raised properly
for both volumes and snapshots. Because snapshot create was not checking
for OverQuota, that needed to be caught in the API so it could be
re-raised properly.

Helper methods for snapshot operations in the functional test API client
were missing, so this also added those in so we can use them in the
functional test.

Change-Id: Iea16a6cb7d3448e0bdd8491826b0780fa8e1a9b1
Closes-Bug: #1554631
This commit is contained in:
Ryan Rossiter 2016-03-11 21:09:41 +00:00
parent 99de5fd3d9
commit 5546df0f41
3 changed files with 85 additions and 4 deletions

View File

@ -549,7 +549,7 @@ class SnapshotController(wsgi.Controller):
res = [entity_maker(context, snapshot) for snapshot in limited_list]
return {'snapshots': res}
@extensions.expected_errors(400)
@extensions.expected_errors((400, 403))
@validation.schema(volumes_schema.snapshot_create)
def create(self, req, body):
"""Creates a new snapshot."""
@ -566,9 +566,12 @@ class SnapshotController(wsgi.Controller):
else:
create_func = self.volume_api.create_snapshot
new_snapshot = create_func(context, volume_id,
snapshot.get('display_name'),
snapshot.get('display_description'))
try:
new_snapshot = create_func(context, volume_id,
snapshot.get('display_name'),
snapshot.get('display_description'))
except exception.OverQuota as e:
raise exc.HTTPForbidden(explanation=e.format_message())
retval = _translate_snapshot_detail_view(context, new_snapshot)
return {'snapshot': retval}

View File

@ -317,6 +317,19 @@ class TestOpenStackClient(object):
def delete_volume(self, volume_id):
return self.api_delete('/os-volumes/%s' % volume_id)
def get_snapshot(self, snap_id):
return self.api_get('/os-snapshots/%s' % snap_id).body['snapshot']
def get_snapshots(self, detail=True):
rel_url = '/os-snapshots/detail' if detail else '/os-snapshots'
return self.api_get(rel_url).body['snapshots']
def post_snapshot(self, snapshot):
return self.api_post('/os-snapshots', snapshot).body['snapshot']
def delete_snapshot(self, snap_id):
return self.api_delete('/os-snapshots/%s' % snap_id)
def get_server_volume(self, server_id, attachment_id):
return self.api_get('/servers/%s/os-volume_attachments/%s' %
(server_id, attachment_id)

View File

@ -45,3 +45,68 @@ class TestCinderForbidden(test.TestCase):
e = self.assertRaises(client.OpenStackApiException,
self.api.post_volume, {'volume': volume})
self.assertEqual(403, e.response.status_code)
class TestCinderOverLimit(test.TestCase):
def setUp(self):
super(TestCinderOverLimit, self).setUp()
self.useFixture(policy_fixture.RealPolicyFixture())
api_fixture = self.useFixture(nova_fixtures.OSAPIFixture(
api_version='v2.1'))
self.api = api_fixture.api
@mock.patch('nova.volume.cinder.cinderclient')
def test_over_limit_volumes(self, mock_cinder):
"""Regression test for bug #1554631.
When the Cinder client returns OverLimit when trying to create
a volume, an OverQuota exception should be raised with the value being
volumes.
"""
cinder_client = mock.Mock()
mock_cinder.return_value = cinder_client
exc = cinder_exceptions.OverLimit('')
cinder_client.volumes.create.side_effect = exc
volume = {'display_name': 'vol1', 'size': 3}
e = self.assertRaises(client.OpenStackApiException,
self.api.post_volume, {'volume': volume})
self.assertEqual(403, e.response.status_code)
# Make sure we went over on volumes
self.assertIn('volumes', e.response.content)
@mock.patch('nova.volume.cinder.cinderclient')
def test_over_limit_snapshots(self, mock_cinder):
"""Regression test for bug #1554631.
When the Cinder client returns OverLimit when trying to create a
snapshot, an OverQuota exception should be raised with the value being
snapshots.
"""
self._do_snapshot_over_test(mock_cinder)
@mock.patch('nova.volume.cinder.cinderclient')
def test_over_limit_snapshots_force(self, mock_cinder):
"""Regression test for bug #1554631.
When the Cinder client returns OverLimit when trying to create a
snapshot, an OverQuota exception should be raised with the value being
snapshots. (create_snapshot_force version)
"""
self._do_snapshot_over_test(mock_cinder, force=True)
def _do_snapshot_over_test(self, mock_cinder, force=False):
cinder_client = mock.Mock()
mock_cinder.return_value = cinder_client
exc = cinder_exceptions.OverLimit('')
cinder_client.volume_snapshots.create.side_effect = exc
snap = {'display_name': 'snap1',
'volume_id': '521752a6-acf6-4b2d-bc7a-119f9148cd8c',
'force': force}
e = self.assertRaises(client.OpenStackApiException,
self.api.post_snapshot, {'snapshot': snap})
self.assertEqual(403, e.response.status_code)
# Make sure we went over on snapshots
self.assertIn('snapshots', e.response.content)