Skip to content

Commit

Permalink
Ensure all values in ScheduledCall are serialized
Browse files Browse the repository at this point in the history
closes #1381
  • Loading branch information
asmacdo committed Jan 11, 2016
1 parent d169205 commit ff0b431
Show file tree
Hide file tree
Showing 4 changed files with 51 additions and 19 deletions.
3 changes: 2 additions & 1 deletion server/pulp/server/db/model/__init__.py
Expand Up @@ -21,6 +21,7 @@
from pulp.server.compat import digestmod
from pulp.server.db.fields import ISO8601StringField, UTCDateTimeField
from pulp.server.db.model.reaper_base import ReaperMixin
from pulp.server.db.model import base
from pulp.server.db.querysets import CriteriaQuerySet, RepoQuerySet
from pulp.server.util import Singleton
from pulp.server.webservices.views import serializers
Expand Down Expand Up @@ -1085,7 +1086,7 @@ def resource_tag(self):
return 'pulp:distributor:{0}:{1}'.format(self.repo_id, self.distributor_id)


class SystemUser(object):
class SystemUser(base.Model):
"""
Singleton user class that represents the "system" user (i.e. no user).
Expand Down
14 changes: 12 additions & 2 deletions server/pulp/server/db/model/dispatch.py
Expand Up @@ -201,7 +201,15 @@ def as_dict(self):
:return: dictionary of public keys and values
:rtype: dict
"""
return {

# If principal is a User object, serialize it. If it does not have a serializer, it is
# a SystemUser which is already a dict.
try:
serial_principal = self.principal.serializer(self.principal).data
except AttributeError:
serial_principal = self.principal

dict_repr = {
'_id': str(self._id),
'args': self.args,
'consecutive_failures': self.consecutive_failures,
Expand All @@ -213,14 +221,16 @@ def as_dict(self):
'last_run_at': self.last_run_at,
'last_updated': self.last_updated,
'next_run': self.calculate_next_run(),
'principal': self.principal,
'principal': serial_principal,
'remaining_runs': self.remaining_runs,
'resource': self.resource,
'schedule': self.schedule,
'task': self.task,
'total_run_count': self.total_run_count,
}

return dict_repr

def for_display(self):
"""
Represent this object as a dictionary, which is useful for serializing
Expand Down
12 changes: 6 additions & 6 deletions server/pulp/server/managers/auth/principal.py
Expand Up @@ -19,17 +19,17 @@ def get_principal(self):
"""
Get the current user of the system,
returning the default system user if there isn't one.
@return: current user of the system
@rtype: User or dict
:return: current user of the system
:rtype: pulp.server.db.model.User or pulp.server.db.model.SystemUser
"""
return getattr(_PRINCIPAL_STORAGE, 'principal', model.SystemUser())

def set_principal(self, principal=None):
"""
Set the current user of the system to the provided principal,
if no principal is provided, set the current user to the system user.
@param principal: current user
@type principal: User or None
:param principal: current user
:type principal: pulp.server.db.model.User or pulp.server.db.model.SystemUser
"""
_PRINCIPAL_STORAGE.principal = principal or model.SystemUser()

Expand All @@ -42,7 +42,7 @@ def clear_principal(self):
def is_system_principal(self):
"""
Determine if the current user is the default system user.
@return: true if the current user is the system user, false otherwise
@rtype: bool
:return: true if the current user is the system user, false otherwise
:rtype: bool
"""
return self.get_principal() is model.SystemUser()
41 changes: 31 additions & 10 deletions server/test/unit/server/db/model/test_dispatch.py
Expand Up @@ -35,12 +35,7 @@
u'kwargs': {u'overrides': {}},
u'last_run_at': u'2013-12-17T00:35:53Z',
u'last_updated': 1387218569.811224,
u'principal': u"(dp0\nV_id\np1\nccopy_reg\n_reconstructor\np2\n(cbson.objectid\nObjectId\np3\n"
u"c__builtin__\nobject\np4\nNtp5\nRp6\nS'R \\xab\\x06\\xe1\\x9a\\x00\\x10\\xe1i"
u"\\x05\\x89'\np7\nbsVname\np8\nVadmin\np9\nsVroles\np10\n(lp11\nVsuper-users\n"
u"p12\nasV_ns\np13\nVusers\np14\nsVlogin\np15\nVadmin\np16\nsVpassword\np17\n"
u"VV76Yol1XYgM=,S/G6o5UyMrn0xAwbQCqFcrXnfXTh84RWhunanCDkSCo=\np18\nsVid\np19\n"
u"V5220ab06e19a0010e1690589\np20\ns.",
u'principal': mock.MagicMock(),
u'remaining_runs': None,
u'resource': u'pulp:distributor:demo:puppet_distributor',
u'schedule': u"ccopy_reg\n_reconstructor\np0\n(ccelery.schedules\nschedule\np1\nc__builtin__\n"
Expand Down Expand Up @@ -614,6 +609,28 @@ def test_returns_dict(self):

self.assertTrue(isinstance(call.as_dict(), dict))

def test_mongoengine_objects_serialized(self):
"""
Ensure that mongoengine objects in the scheduled call were serialized.
"""
schedule = bson.SON(SCHEDULE)
call = ScheduledCall.from_db(schedule)
call['principal'] = model.User('test_user')

result = call.as_dict()
self.assertEqual(result['principal'], model.User.serializer(call['principal']).data)

def test_system_user_is_dict(self):
"""
Ensure value for principal is a dict when value is is a model.SystemUser.
"""
schedule = bson.SON(SCHEDULE)
call = ScheduledCall.from_db(schedule)
call['principal'] = model.SystemUser()

result = call.as_dict()
self.assertTrue(isinstance(result['principal'], dict))

def test_values(self):
schedule = bson.SON(SCHEDULE)
call = ScheduledCall.from_db(schedule)
Expand All @@ -622,13 +639,16 @@ def test_values(self):

self.assertEqual(result['_id'], call.id)
for k, v in SCHEDULE.items():
self.assertEqual(v, result[k])
if k == 'principal':
self.assertTrue(result[k] is SCHEDULE[k].serializer.return_value.data)
else:
self.assertEqual(v, result[k])
self.assertTrue('next_run' in result)


class TestScheduledCallForDisplay(unittest.TestCase):
def test_returns_dict(self):
call = ScheduledCall('PT1M', 'pulp.tasks.dosomething')
call = ScheduledCall('PT1M', 'pulp.tasks.dosomething', principal=mock.MagicMock())

self.assertTrue(isinstance(call.for_display(), dict))

Expand All @@ -650,7 +670,8 @@ class TestScheduledCallSave(unittest.TestCase):
def test_existing(self, mock_get_collection):
mock_update = mock_get_collection.return_value.update
fake_id = bson.ObjectId()
call = ScheduledCall('PT1M', 'pulp.tasks.dosomething', id=fake_id)
call = ScheduledCall('PT1M', 'pulp.tasks.dosomething', id=fake_id,
principal=mock.MagicMock())

call.save()

Expand All @@ -660,7 +681,7 @@ def test_existing(self, mock_get_collection):

def test_new(self, mock_get_collection):
mock_insert = mock_get_collection.return_value.insert
call = ScheduledCall('PT1M', 'pulp.tasks.dosomething')
call = ScheduledCall('PT1M', 'pulp.tasks.dosomething', principal=mock.MagicMock())

call.save()

Expand Down

0 comments on commit ff0b431

Please sign in to comment.