enforce personality quotas

This commit is contained in:
Mark Washenberger
2011-03-03 17:49:41 -05:00
parent 9cfe8ff2e8
commit e14f524eb9
3 changed files with 101 additions and 16 deletions

View File

@@ -80,6 +80,26 @@ class API(base.Base):
topic,
{"method": "get_network_topic", "args": {'fake': 1}})
def _check_personality_file_quota(self, context, personality_files):
limit = quota.allowed_personality_files(context)
if len(personality_files) > limit:
raise quota.QuotaError(_("Personality limit exceeded. You can "
"only have %d personalities when "
"creating an instance.") % limit,
"PersonalityLimitExceeded")
path_limit = quota.allowed_personality_path_bytes(context)
content_limit = quota.allowed_personality_content_bytes(context)
for path, content in personality_files:
if len(path) > path_limit:
raise quota.QuotaError(
_("Personality file path limit exceeded."),
"PersonalityLimitExceeded")
if len(content) > content_limit:
raise quota.QuotaError(
_("Personality file content limit exceeded."),
"PersonalityLimitExceeded")
return personality_files
def create(self, context, instance_type,
image_id, kernel_id=None, ramdisk_id=None,
min_count=1, max_count=1,
@@ -124,6 +144,10 @@ class API(base.Base):
LOG.warn(msg)
raise quota.QuotaError(msg, "MetadataLimitExceeded")
if onset_files is not None:
onset_files = \
self._check_personality_file_quota(context, onset_files)
image = self.image_service.show(context, image_id)
if kernel_id is None:
kernel_id = image.get('kernel_id', None)

View File

@@ -37,10 +37,12 @@ flags.DEFINE_integer('quota_floating_ips', 10,
'number of floating ips allowed per project')
flags.DEFINE_integer('quota_metadata_items', 128,
'number of metadata items allowed per instance')
flags.DEFINE_integer('quota_file_injection_max_files', 5,
'number of files allowed during file injection')
flags.DEFINE_integer('quota_file_injection_max_file_bytes', 10 * 1024,
'number of bytes allowed per file during file injection')
flags.DEFINE_integer('quota_personality_max_files', 5,
'number of personality files allowed')
flags.DEFINE_integer('quota_personality_max_content_bytes', 10 * 1024,
'number of bytes allowed per personality file')
flags.DEFINE_integer('quota_personality_max_path_bytes', 255,
'number of bytes allowed per personality file path')
def get_quota(context, project_id):
@@ -113,14 +115,19 @@ def allowed_metadata_items(context, num_metadata_items):
return min(num_metadata_items, num_allowed_metadata_items)
def allowed_file_injection_files(context):
"""Return the number of files allowed per file injection"""
return FLAGS.quota_file_injection_max_files
def allowed_personality_files(context):
"""Return the number of personality files allowed"""
return FLAGS.quota_personality_max_files
def allowed_file_injection_file_bytes(context):
"""Return the number of bytes allowed per file during injection"""
return FLAGS.quota_file_injection_max_file_bytes
def allowed_personality_content_bytes(context):
"""Return the number of bytes allowed per personality content"""
return FLAGS.quota_personality_max_content_bytes
def allowed_personality_path_bytes(context):
"""Return the number of bytes allowed in a personality file path"""
return FLAGS.quota_personality_max_path_bytes
class QuotaError(exception.ApiError):

View File

@@ -177,12 +177,66 @@ class QuotaTestCase(test.TestCase):
image_id='fake',
metadata=metadata)
def test_allowed_file_injection_files(self):
def test_allowed_personality_files(self):
self.assertEqual(
quota.allowed_file_injection_files(self.context),
FLAGS.quota_file_injection_max_files)
quota.allowed_personality_files(self.context),
FLAGS.quota_personality_max_files)
def test_allowed_file_injection_file_bytes(self):
def _create_with_personality(self, files):
api = compute.API()
api.create(self.context, min_count=1, max_count=1,
instance_type='m1.small', image_id='fake',
onset_files=files)
def test_no_personality_files(self):
api = compute.API()
api.create(self.context, instance_type='m1.small', image_id='fake')
def test_max_personality_files(self):
files = []
for i in xrange(FLAGS.quota_personality_max_files):
files.append(('/my/path%d' % i, 'config = test\n'))
self._create_with_personality(files) # no QuotaError
def test_too_many_personality_files(self):
files = []
for i in xrange(FLAGS.quota_personality_max_files + 1):
files.append(('/my/path%d' % i, 'my\ncontent%d\n' % i))
self.assertRaises(quota.QuotaError,
self._create_with_personality, files)
def test_allowed_personality_content_bytes(self):
self.assertEqual(
quota.allowed_file_injection_file_bytes(self.context),
FLAGS.quota_file_injection_max_file_bytes)
quota.allowed_personality_content_bytes(self.context),
FLAGS.quota_personality_max_content_bytes)
def test_max_personality_content_bytes(self):
max = FLAGS.quota_personality_max_content_bytes
content = ''.join(['a' for i in xrange(max)])
files = [('/test/path', content)]
self._create_with_personality(files) # no QuotaError
def test_too_many_personality_content_bytes(self):
max = FLAGS.quota_personality_max_content_bytes
content = ''.join(['a' for i in xrange(max + 1)])
files = [('/test/path', content)]
self.assertRaises(quota.QuotaError,
self._create_with_personality, files)
def test_allowed_personality_path_bytes(self):
self.assertEqual(
quota.allowed_personality_path_bytes(self.context),
FLAGS.quota_personality_max_path_bytes)
def test_max_personality_path_bytes(self):
max = FLAGS.quota_personality_max_path_bytes
path = ''.join(['a' for i in xrange(max)])
files = [(path, 'config = quotatest')]
self._create_with_personality(files) # no QuotaError
def test_too_many_personality_path_bytes(self):
max = FLAGS.quota_personality_max_path_bytes
path = ''.join(['a' for i in xrange(max + 1)])
files = [(path, 'config = quotatest')]
self.assertRaises(quota.QuotaError,
self._create_with_personality, files)