def tearDown(self): super(AdminRegisterInlineTest, self).tearDown() if reversion.is_registered(TestModelInline): reversion.unregister(TestModelInline) if reversion.is_registered(TestModelGenericInline): reversion.unregister(TestModelGenericInline) admin.site.unregister(TestModelParent)
def testEagerRegistration(self): # Register the model and test. reversion.register(ReversionTestModel3, eager_signals=[pre_delete]) self.assertTrue(reversion.is_registered(ReversionTestModel3)) self.assertRaises( RegistrationError, lambda: reversion.register(ReversionTestModel3, eager_signals=[pre_delete])) self.assertTrue( ReversionTestModel3 in reversion.get_registered_models()) self.assertTrue( isinstance(reversion.get_adapter(ReversionTestModel3), reversion.VersionAdapter)) self.assertEquals( [], reversion.default_revision_manager._signals[ReversionTestModel3]) self.assertEquals([pre_delete], reversion.default_revision_manager. _eager_signals[ReversionTestModel3]) # Unregister the model and text. reversion.unregister(ReversionTestModel3) self.assertFalse(reversion.is_registered(ReversionTestModel3)) self.assertRaises(RegistrationError, lambda: reversion.unregister(ReversionTestModel3)) self.assertTrue( ReversionTestModel3 not in reversion.get_registered_models()) self.assertRaises( RegistrationError, lambda: isinstance(reversion.get_adapter(ReversionTestModel3))) self.assertFalse( ReversionTestModel3 in reversion.default_revision_manager._signals) self.assertFalse(ReversionTestModel3 in reversion.default_revision_manager._eager_signals)
def test_initial_state(self): self.assertTrue(reversion.is_registered(Factory)) self.assertTrue(reversion.is_registered(Car)) self.assertEqual(Revision.objects.all().count(), 3) self.assertEqual(len(self.version_ids), 3) self.assertEqual(Version.objects.all().count(), 10)
def test_initial_state(self): self.assertTrue(reversion.is_registered(Pet)) self.assertTrue(reversion.is_registered(Person)) self.assertEqual(Pet.objects.count(), 3) self.assertEqual(reversion.get_for_object(self.pet1).count(), 2) self.assertEqual(Revision.objects.all().count(), 2)
def test_initial_state(self): self.assertTrue(is_registered(Pet)) self.assertTrue(is_registered(Person)) self.assertEqual(Pet.objects.count(), 3) self.assertEqual(Version.objects.get_for_object(self.pet1).count(), 2) self.assertEqual(Revision.objects.all().count(), 2)
def test_initial_state(self): self.assertTrue(is_registered(Factory)) self.assertTrue(is_registered(Car)) self.assertEqual(Factory.objects.all().count(), 0) self.assertEqual(Car.objects.all().count(), 0) self.assertEqual(Revision.objects.all().count(), 0) self.assertEqual(Version.objects.all().count(), 0)
def get_many_to_something(self, target_ids, related_model, is_reverse=False): # get instance of reversion.models.Revision(): # A group of related object versions. old_revision = self.version_record.revision # Get a queryset with all related objects. versions = { ver.object_id: ver for ver in old_revision.version_set.filter( content_type=ContentType.objects.get_for_model(related_model), object_id__in=target_ids).all() } missing_objects_dict = {} deleted = [] if not self.follow: # This models was not registered with follow relations # Try to fill missing related objects potentially_missing_ids = target_ids.difference( frozenset(versions)) # logger.debug( # self.field_name, # f"target: {target_ids} - actual: {versions} - missing: {potentially_missing_ids}" # ) if potentially_missing_ids: missing_objects_dict = { force_str(rel.pk): rel for rel in related_model.objects.filter( pk__in=potentially_missing_ids).iterator() if is_registered(rel.__class__) or not self.ignore_not_registered } if is_reverse: missing_objects_dict = { ver.object_id: ver for o in missing_objects_dict.values() for ver in Version.objects.get_for_object(o) if ver.revision.date_created < old_revision.date_created } if is_registered(related_model) or not self.ignore_not_registered: # shift query to database deleted = list( Version.objects.filter( revision=old_revision).get_deleted(related_model)) else: deleted = [] return versions, missing_objects_dict, deleted
def testRegistration(self): # Register the model and test. reversion.register(ReversionTestModel1) self.assertTrue(reversion.is_registered(ReversionTestModel1)) self.assertRaises(RegistrationError, lambda: reversion.register(ReversionTestModel1)) self.assertTrue(ReversionTestModel1 in reversion.get_registered_models()) self.assertTrue(isinstance(reversion.get_adapter(ReversionTestModel1), reversion.VersionAdapter)) # Unregister the model and text. reversion.unregister(ReversionTestModel1) self.assertFalse(reversion.is_registered(ReversionTestModel1)) self.assertRaises(RegistrationError, lambda: reversion.unregister(ReversionTestModel1)) self.assertTrue(ReversionTestModel1 not in reversion.get_registered_models()) self.assertRaises(RegistrationError, lambda: isinstance(reversion.get_adapter(ReversionTestModel1)))
def testInlineAdmin(self): self.assertTrue(reversion.is_registered(InlineTestParentModel)) # make sure model is following the child FK self.assertTrue('children' in reversion.get_adapter(InlineTestParentModel).follow) self.createInlineObjects() # unregister model reversion.unregister(InlineTestParentModel) self.assertFalse(reversion.is_registered(InlineTestParentModel)) # re-register without following reversion.register(InlineTestParentModel) self.assertTrue(reversion.is_registered(InlineTestParentModel)) # make sure model is NOT following the child FK self.assertFalse('children' in reversion.get_adapter(InlineTestParentModel).follow) self.createInlineObjects()
def testInlineProxyAdmin(self): self.assertTrue(reversion.is_registered(InlineTestParentModelProxy)) # make sure model is following the child FK self.assertTrue('children' in reversion.get_adapter( InlineTestParentModelProxy).follow) parent_pk = self.createInlineProxyObjects() # Check that the current version includes the inlines. versions = list( reversion.get_for_object_reference(InlineTestParentModelProxy, parent_pk)) response = self.client.get( reverse( "admin:test_app_inlinetestparentmodelproxy_revision", args=(parent_pk, versions[0].pk), )) self.assertContains(response, "parent version2") # Check parent model. self.assertContains( response, "non-generic child version 1") # Check inline child model. # Check that the first version does not include the inlines. response = self.client.get( reverse( "admin:test_app_inlinetestparentmodelproxy_revision", args=(parent_pk, versions[1].pk), )) self.assertContains(response, "parent version1") # Check parent model. self.assertNotContains( response, "non-generic child version 1") # Check inline child model.
def __new__(cls, name, bases, attrs): if name in cls.plugins_with_extrafields: ExtraFieldsMixin.media = media_property(ExtraFieldsMixin) bases = (ExtraFieldsMixin,) + bases if name in cls.plugins_with_sharables: SharableGlossaryMixin.media = media_property(SharableGlossaryMixin) bases = (SharableGlossaryMixin,) + bases attrs['fields'] += (('save_shared_glossary', 'save_as_identifier'), 'shared_glossary',) attrs['sharable_fields'] = cls.plugins_with_sharables[name] base_model = SharableCascadeElement else: base_model = CascadeElement if name in getattr(settings, 'CASCADE_PLUGINS_WITH_EXTRA_RENDER_TEMPLATES').keys(): RenderTemplateMixin.media = media_property(RenderTemplateMixin) bases = (RenderTemplateMixin,) + bases model_mixins = attrs.pop('model_mixins', ()) if name == 'SegmentPlugin': # SegmentPlugin shall additionally inherit from configured mixin classes model_mixins += tuple(import_string(mc[0]) for mc in settings.CASCADE_SEGMENTATION_MIXINS) attrs['model'] = create_proxy_model(name, model_mixins, base_model) if is_installed('reversion'): import reversion if not reversion.is_registered(base_model): reversion.register(base_model) return super(CascadePluginBaseMetaclass, cls).__new__(cls, name, bases, attrs)
def check_registration(self, test_model): # Register the model and test. reversion.register(test_model) self.assertTrue(reversion.is_registered(test_model)) self.assertRaises(RegistrationError, lambda: reversion.register(test_model)) self.assertTrue(test_model in reversion.get_registered_models()) self.assertTrue(isinstance(reversion.get_adapter(test_model), reversion.VersionAdapter))
def __init__(self, *args, **kwargs): """Initializes the VersionAdmin""" super(VersionAdmin, self).__init__(*args, **kwargs) # Automatically register models if required. if not reversion.is_registered(self.model): inline_fields = [] for inline in self.inlines: inline_model = inline.model self._autoregister(inline_model) if issubclass(inline, (admin.TabularInline, admin.StackedInline)): fk_name = inline.fk_name if not fk_name: for field in inline_model._meta.fields: if isinstance( field, (models.ForeignKey, models.OneToOneField)) and issubclass( self.model, field.rel.to): fk_name = field.name accessor = inline_model._meta.get_field( fk_name ).rel.related_name or inline_model.__name__.lower( ) + "_set" inline_fields.append(accessor) elif issubclass(inline, GenericInlineModelAdmin): ct_field = inline.ct_field ct_fk_field = inline.ct_fk_field for field in self.model._meta.many_to_many: if isinstance( field, GenericRelation ) and field.object_id_field_name == ct_fk_field and field.content_type_field_name == ct_field: inline_fields.append(field.name) self._autoregister(self.model, inline_fields)
def testDecorator(self): # Test the use of register as a decorator @reversion.register class DecoratorModel(models.Model): pass self.assertTrue(reversion.is_registered(DecoratorModel))
def register_model_and_inlines_with_reversion( self, model, inline_classes: Iterable[RelatedInline]): """ Register the model and all inline models with reversion iff they haven't been registered before. If you want full control over which models are versioned together, register them with reversion manually. """ if is_registered(model): return # we collect all inline fields so that reversion knows which inline instances to include in revisions. inline_fields = [] for inline_class in inline_classes: inline_model = inline_class.model inline_model_opts = inline_class.model._meta # do not register inlines that have their own viewset, this yields confusing # behaviour as they may not be registered on their own if (inline_model_opts.app_label in self.registry and inline_model_opts.model_name in self.registry[inline_model_opts.app_label]): continue # register the inline model self._register_model_with_parents(inline_model) # if the remote field has an accessor name that we can follow from our model (not is_hidden()) # we want reversion to follow that accessor when creating a revision for our model if not inline_model._meta.get_field( inline_class.foreign_key_field).remote_field.is_hidden(): field = inline_model._meta.get_field( inline_class.foreign_key_field) inline_fields.append(field.remote_field.get_accessor_name()) self._register_model_with_parents(model, inline_fields)
def test_initial_state(self): self.assertTrue(reversion.is_registered(VariantModel)) self.assertEqual(VariantModel.objects.count(), 1) self.assertEqual(reversion.get_for_object(self.item).count(), 1) self.assertEqual(Revision.objects.all().count(), 1)
def __init__(self, *args, **kwargs): """Initializes the VersionAdmin""" super(VersionAdmin, self).__init__(*args, **kwargs) # Automatically register models if required. if not reversion.is_registered(self.model): inline_fields = [] for inline in self.inlines: inline_model = inline.model self._autoregister(inline_model) if issubclass(inline, (admin.TabularInline, admin.StackedInline)): fk_name = inline.fk_name if not fk_name: for field in inline_model._meta.fields: if isinstance(field, (models.ForeignKey, models.OneToOneField)) and issubclass( self.model, field.rel.to ): fk_name = field.name accessor = ( inline_model._meta.get_field(fk_name).rel.related_name or inline_model.__name__.lower() + "_set" ) inline_fields.append(accessor) elif issubclass(inline, GenericInlineModelAdmin): ct_field = inline.ct_field ct_fk_field = inline.ct_fk_field for field in self.model._meta.many_to_many: if ( isinstance(field, GenericRelation) and field.object_id_field_name == ct_fk_field and field.content_type_field_name == ct_field ): inline_fields.append(field.name) self._autoregister(self.model, inline_fields)
def testDecoratorArgs(self): # Test a decorator with arguments @reversion.register(format="yaml") class DecoratorArgsModel(models.Model): pass self.assertTrue(reversion.is_registered(DecoratorArgsModel))
def setUp(self): # Register the test models. reversion.register(ReversionTestModel1) reversion.register(ReversionTestModel2) # Create some test data. self.test11 = ReversionTestModel1.objects.create( name = "model1 instance1 version1", ) self.test12 = ReversionTestModel1.objects.create( name = "model1 instance2 version1", ) self.test21 = ReversionTestModel2.objects.create( name = "model2 instance1 version1", ) self.test22 = ReversionTestModel2.objects.create( name = "model2 instance2 version1", ) self.user = User.objects.create( username = "******", ) # Since we're creating a user, we need to bias our assertions # depending on whether or not it will create versions/revisions for # self.user. self.registered_instance_offset = 0 if reversion.is_registered(User): self.registered_instance_offset = 1
def register_model(model, follow = None): if not reversion.is_registered(model) and settings.USE_REVERSION: #print "registering model with reversion: ", model if follow is None: reversion.register(model) else: reversion.register(model, follow = follow)
def check_deregistration(self, test_model): # Unregister the model and text. reversion.unregister(test_model) self.assertFalse(reversion.is_registered(test_model)) self.assertRaises(RegistrationError, lambda: reversion.unregister(test_model)) self.assertTrue(test_model not in reversion.get_registered_models()) self.assertRaises(RegistrationError, lambda: isinstance(reversion.get_adapter(test_model)))
def __new__(cls, name, bases, attrs): if name in cls.plugins_with_extra_fields: ExtraFieldsMixin.media = media_property(ExtraFieldsMixin) bases = (ExtraFieldsMixin,) + bases if name in cls.plugins_with_sharables: SharableGlossaryMixin.media = media_property(SharableGlossaryMixin) bases = (SharableGlossaryMixin,) + bases attrs['fields'] += (('save_shared_glossary', 'save_as_identifier'), 'shared_glossary',) attrs['sharable_fields'] = cls.plugins_with_sharables[name] base_model = SharableCascadeElement else: base_model = CascadeElement if name in settings.CMSPLUGIN_CASCADE['plugins_with_extra_render_templates'].keys(): RenderTemplateMixin.media = media_property(RenderTemplateMixin) bases = (RenderTemplateMixin,) + bases model_mixins = attrs.pop('model_mixins', ()) if name == 'SegmentPlugin': # SegmentPlugin shall additionally inherit from configured mixin classes model_mixins += tuple(import_string(mc[0]) for mc in settings.CMSPLUGIN_CASCADE['segmentation_mixins']) module = attrs.get('__module__') app_label = attrs.get('app_label', module.split('.')[0]) attrs['model'] = create_proxy_model(name, app_label, model_mixins, base_model, module=module) if is_installed('reversion'): import reversion if not reversion.is_registered(base_model): reversion.register(base_model) # handle ambiguous plugin names by appending a symbol if 'name' in attrs and settings.CMSPLUGIN_CASCADE['plugin_prefix']: attrs['name'] = mark_safe_lazy(string_concat( settings.CMSPLUGIN_CASCADE['plugin_prefix'], " ", attrs['name'])) return super(CascadePluginBaseMetaclass, cls).__new__(cls, name, bases, attrs)
def testDecoratorArgs(self): # Test a decorator with arguments @reversion.register(format='yaml') class DecoratorArgsModel(models.Model): pass self.assertTrue(reversion.is_registered(DecoratorArgsModel))
def testInlineAdmin(self): self.assertTrue(reversion.is_registered(InlineTestParentModel)) # make sure model is following the child FK self.assertTrue( 'children' in reversion.get_adapter(InlineTestParentModel).follow) self.createInlineObjects() # unregister model reversion.unregister(InlineTestParentModel) self.assertFalse(reversion.is_registered(InlineTestParentModel)) # re-register without following reversion.register(InlineTestParentModel) self.assertTrue(reversion.is_registered(InlineTestParentModel)) # make sure model is NOT following the child FK self.assertFalse( 'children' in reversion.get_adapter(InlineTestParentModel).follow) self.createInlineObjects()
def __new__(cls, name, bases, attrs): if name in cls.plugins_with_extrafields: ExtraFieldsMixin.media = media_property(ExtraFieldsMixin) bases = (ExtraFieldsMixin, ) + bases if name in cls.plugins_with_sharables: SharableGlossaryMixin.media = media_property(SharableGlossaryMixin) bases = (SharableGlossaryMixin, ) + bases attrs['fields'] += ( ('save_shared_glossary', 'save_as_identifier'), 'shared_glossary', ) attrs['sharable_fields'] = cls.plugins_with_sharables[name] base_model = SharableCascadeElement else: base_model = CascadeElement if name in getattr( settings, 'CASCADE_PLUGINS_WITH_EXTRA_RENDER_TEMPLATES').keys(): RenderTemplateMixin.media = media_property(RenderTemplateMixin) bases = (RenderTemplateMixin, ) + bases model_mixins = attrs.pop('model_mixins', ()) if name == 'SegmentPlugin': # SegmentPlugin shall additionally inherit from configured mixin classes model_mixins += tuple( import_string(mc[0]) for mc in settings.CASCADE_SEGMENTATION_MIXINS) attrs['model'] = create_proxy_model(name, model_mixins, base_model) if is_installed('reversion'): import reversion if not reversion.is_registered(base_model): reversion.register(base_model) return super(CascadePluginBaseMetaclass, cls).__new__(cls, name, bases, attrs)
def get_version_id(self, resource): if not reversion.is_registered(resource.__class__): return None version_id = len(Version.objects.get_for_object(resource)) if self.context['request'].method in ['POST', 'PUT', 'PATCH']: version_id += 1 return version_id
def testPKs(self): for table_type in self.table_types: self.assertTrue(reversion.is_registered(table_type)) with reversion.create_revision(): record = table_type.objects.create(name="Testing") versions = reversion.get_for_object(record) self.assertEqual(versions.count(), 1)
def testEagerRegistration(self): # Register the model and test. reversion.register(ReversionTestModel3, eager_signals=[pre_delete]) self.assertTrue(reversion.is_registered(ReversionTestModel3)) self.assertRaises(RegistrationError, lambda: reversion.register(ReversionTestModel3, eager_signals=[pre_delete])) self.assertTrue(ReversionTestModel3 in reversion.get_registered_models()) self.assertTrue(isinstance(reversion.get_adapter(ReversionTestModel3), reversion.VersionAdapter)) self.assertEquals([], reversion.default_revision_manager._signals[ReversionTestModel3]) self.assertEquals([pre_delete], reversion.default_revision_manager._eager_signals[ReversionTestModel3]) # Unregister the model and text. reversion.unregister(ReversionTestModel3) self.assertFalse(reversion.is_registered(ReversionTestModel3)) self.assertRaises(RegistrationError, lambda: reversion.unregister(ReversionTestModel3)) self.assertTrue(ReversionTestModel3 not in reversion.get_registered_models()) self.assertRaises(RegistrationError, lambda: isinstance(reversion.get_adapter(ReversionTestModel3))) self.assertFalse(ReversionTestModel3 in reversion.default_revision_manager._signals) self.assertFalse(ReversionTestModel3 in reversion.default_revision_manager._eager_signals)
def testCanUnregisterModel(self): """Tests that a model can be unregistered.""" reversion.unregister(TestModel) self.assertFalse(reversion.is_registered(TestModel)) # Check that duplicate unregistration is disallowed. self.assertRaises(RegistrationError, lambda: reversion.unregister(TestModel)) # Re-register the model. reversion.register(TestModel)
def test_initial_state(self): self.assertTrue(reversion.is_registered(SimpleModel)) self.assertEqual(SimpleModel.objects.count(), 1) self.assertEqual(SimpleModel.objects.all()[0].text, "version two") self.assertEqual(reversion.get_for_object(self.item1).count(), 2) self.assertEqual(Revision.objects.all().count(), 2) self.assertEqual(Version.objects.all().count(), 2)
def test_initial_state(self): self.assertTrue(is_registered(VariantModel)) self.assertEqual(VariantModel.objects.count(), 1) count = len(self.test_data) + 1 # incl. initial self.assertEqual(Version.objects.get_for_object(self.item).count(), count) self.assertEqual(Revision.objects.all().count(), count) self.assertEqual(len(self.version_ids), count)
def test_initial_state(self): self.assertTrue(reversion.is_registered(SimpleModel)) self.assertEqual(SimpleModel.objects.count(), 1) self.assertEqual(SimpleModel.objects.all()[0].text, "version two") self.assertEqual(reversion.get_for_object(self.item1).count(), 2) self.assertEqual(Revision.objects.all().count(), 2) self.assertEqual(len(self.version_ids), 2) self.assertEqual(Version.objects.all().count(), 2)
def check_registration(self, test_model): # Register the model and test. reversion.register(test_model) self.assertTrue(reversion.is_registered(test_model)) self.assertRaises(RegistrationError, lambda: reversion.register(test_model)) self.assertTrue(test_model in reversion.get_registered_models()) self.assertTrue( isinstance(reversion.get_adapter(test_model), reversion.VersionAdapter))
def check_deregistration(self, test_model): # Unregister the model and text. reversion.unregister(test_model) self.assertFalse(reversion.is_registered(test_model)) self.assertRaises(RegistrationError, lambda: reversion.unregister(test_model)) self.assertTrue(test_model not in reversion.get_registered_models()) self.assertRaises( RegistrationError, lambda: isinstance(reversion.get_adapter(test_model)))
def test_initial_state(self): self.assertTrue(is_registered(VariantModel)) self.assertEqual(VariantModel.objects.count(), 1) count = len(self.fixtures) + 1 # incl. initial self.assertEqual(Version.objects.get_for_object(self.item).count(), count) self.assertEqual(Revision.objects.all().count(), count) self.assertEqual(len(self.version_ids), count)
def _autoregister(self, model, follow=None): """Registers a model with reversion, if required.""" if not reversion.is_registered(model): follow = follow or [] for parent_cls, field in model._meta.parents.items(): if field: # Proxy models do not have a parent field. follow.append(field.name) self._autoregister(parent_cls) reversion.register(model, follow=follow, format=self.reversion_format)
def _register_reversion_safe(self, klass, registration): if not reversion.is_registered(klass): if klass.__name__ == 'CMSPlugin': reversion.register(klass) else: reversion.register(klass, **registration) elif klass.__name__ != 'CMSPlugin' and 'CMSPlugin' in _get_ancestor_class_names(klass): opt_dict = rev._registered_models[rev._get_registration_key(klass)]._asdict() if not 'cmsplugin_ptr' in opt_dict['follow']: opt_dict['follow'] += ('cmsplugin_ptr', ) rev._registered_models[rev._get_registration_key(klass)] = rev._VersionOptions(**opt_dict)
def test_initial_state(self): self.assertTrue(is_registered(SimpleModel)) self.assertEqual(SimpleModel.objects.count(), 2) self.assertEqual(SimpleModel.objects.all()[0].text, "version two") self.assertEqual(Version.objects.get_for_object(self.item1).count(), 2) self.assertEqual(list(self.version_ids1), [2, 1]) self.assertEqual(list(self.version_ids1), [2, 1]) self.assertEqual(list(self.version_ids2), [7, 6, 5, 4, 3])
def get_version_id(self, resource): if not reversion.is_registered(resource.__class__): return None version_id = Version.objects.get_for_object(resource).count() request = self.context['request'] if request.method in ['POST', 'PUT', 'PATCH']: if not (request.method == 'POST' and self.context.get('post_is_used_for_filter', False)): version_id += 1 return version_id
def reversion_models(model_pairs): """Given a sequence of (app_label, model_name) pairs, determine which are still Django models and registered with reversions""" for app_label, model_name in model_pairs: try: model = apps.get_model(app_label, model_name) if reversion.is_registered(model): yield model else: logger.warn("Model not registered with reversions %s %s", app_label, model_name) except LookupError: logger.warn("Couldn't find model %s %s", app_label, model_name)
def test_initial_state(self): self.assertTrue(reversion.is_registered(SimpleModel)) self.assertEqual(SimpleModel.objects.count(), 2) self.assertEqual(SimpleModel.objects.all()[0].text, "version two") self.assertEqual(reversion.get_for_object(self.item1).count(), 2) self.assertEqual(reversion.get_for_object(self.item2).count(), 5) self.assertEqual(Revision.objects.all().count(), 7) self.assertEqual(Version.objects.all().count(), 7) # query.ValuesListQuerySet() -> list(): self.assertEqual(list(self.version_ids1), [2, 1]) self.assertEqual(list(self.version_ids2), [7, 6, 5, 4, 3])
def _register_model_with_parents(self, model, follow=()): """ Register a model with reversion automatically accounting for multi table inheritance. """ if is_registered(model): return follow = tuple(follow) # recursively register parents to support multi table inheritance as per api docs # https://django-reversion.readthedocs.io/en/stable/api.html#registration-api for parent_model, field in model._meta.concrete_model._meta.parents.items(): follow += (field.name,) self._register_model_with_parents(parent_model, ()) register(model, follow=follow)
def auditlog_on_delete(sender, **kwargs): """ auditlog object deletions """ if not reversion.is_registered(sender): return if not auditlog.is_enabled(sender): return tag = auditlog.model_tag(sender) action = f"{tag}:delete" instance = kwargs.get("instance") with auditlog.Context() as ctx: ctx.log(action, log_object=instance)
def testInlineProxyAdmin(self): self.assertTrue(reversion.is_registered(InlineTestParentModelProxy)) # make sure model is following the child FK self.assertTrue('children' in reversion.get_adapter(InlineTestParentModelProxy).follow) parent_pk = self.createInlineProxyObjects() # Check that the current version includes the inlines. versions = list(reversion.get_for_object_reference(InlineTestParentModelProxy, parent_pk)) response = self.client.get(reverse( "admin:test_app_inlinetestparentmodelproxy_revision", args=(parent_pk, versions[0].pk), )) self.assertContains(response, "parent version2") # Check parent model. self.assertContains(response, "non-generic child version 1") # Check inline child model. # Check that the first version does not include the inlines. response = self.client.get(reverse( "admin:test_app_inlinetestparentmodelproxy_revision", args=(parent_pk, versions[1].pk), )) self.assertContains(response, "parent version1") # Check parent model. self.assertNotContains(response, "non-generic child version 1") # Check inline child model.
def post_delete_hook(sender, instance, **kwargs): """Custom post-delete hook. We want to know who was responsible for an object deletion. """ from reversion.models import Version if not reversion.is_registered(sender): return del_list = reversion.get_deleted(sender) try: version = del_list.get(object_id=instance.id) except Version.DoesNotExist: return logger = logging.getLogger("modoboa.admin") msg = _("%(object)s '%(name)s' %(action)s by user %(user)s") % { "object": unicode(version.content_type).capitalize(), "name": version.object_repr, "action": _("deleted"), "user": version.revision.user.username } logger.critical(msg)
def testCanRegisterModel(self): """Tests that a model can be registered.""" self.assertTrue(reversion.is_registered(TestModel)) # Check that duplicate registration is disallowed. self.assertRaises(RegistrationError, lambda: reversion.register(TestModel))
image_off = "img/community-off.png" default_logo_url = "img/logo-community.png" # TODO: order communities from the database def closest_communities(self, max=3, radius=Distance(km=25)): center = self.geometry.centroid unordered = Community.objects.filter(polys__distance_lte=(center, radius)) closest = sorted(unordered, key=lambda c: c.geometry.distance(center)) return closest[1 : (max + 1)] # url aliases @property def view_url(self): return reverse("view_community", kwargs={"id": self.id}) @property def edit_url(self): return reverse("edit_community", kwargs={"id": self.id}) @property def admin_url(self): return reverse("admin:{}_{}_change".format(self._meta.app_label, self._meta.module_name), args=[self.id]) @property def perm_id(self): return "c%d" % self.id if not reversion.is_registered(Community): reversion.register(Community)
def testUnregister(self): reversion.unregister(TestModel) self.assertFalse(reversion.is_registered(TestModel))
def testRegisterDecorator(self): @reversion.register() class TestModelDecorater(models.Model): pass self.assertTrue(reversion.is_registered(TestModelDecorater))