Ejemplo n.º 1
0
    def ready(self):
        Invoice = self.get_model('Invoice')

        signals.post_save.connect(
            handlers.log_invoice_save,
            sender=Invoice,
            dispatch_uid='nodeconductor_killbill.handlers.log_invoice_save',
        )

        signals.post_delete.connect(
            handlers.log_invoice_delete,
            sender=Invoice,
            dispatch_uid='nodeconductor_killbill.handlers.log_invoice_delete',
        )

        for index, resource in enumerate(
                structure_models.PaidResource.get_all_models()):
            post_transition.connect(
                handlers.subscribe,
                sender=resource,
                dispatch_uid='nodeconductor_killbill.handlers.subscribe_{}_{}'.
                format(resource.__name__, index),
            )

            signals.post_delete.connect(
                handlers.unsubscribe,
                sender=resource,
                dispatch_uid='nodeconductor_killbill.handlers.unsubscribe_{}_{}'
                .format(resource.__name__, index),
            )

            signals.pre_save.connect(
                preserve_fields_before_update,
                sender=resource,
                dispatch_uid=
                'nodeconductor_killbill.handlers.preserve_fields_before_update_{}_{}'
                .format(resource.__name__, index),
            )

            signals.post_save.connect(
                handlers.update_resource_name,
                sender=resource,
                dispatch_uid=
                'nodeconductor_killbill.handlers.update_resource_name_{}_{}'.
                format(resource.__name__, index),
            )

        signals.post_save.connect(
            handlers.update_project_name,
            sender=structure_models.Project,
            dispatch_uid='nodeconductor_killbill.handlers.update_project_name',
        )

        signals.post_save.connect(
            handlers.update_project_group_name,
            sender=structure_models.ProjectGroup,
            dispatch_uid=
            'nodeconductor_killbill.handlers.update_project_group_name',
        )
Ejemplo n.º 2
0
    def ready(self):
        backend = import_by_path(settings.DJANGO_FSM_LOG_STORAGE_METHOD)
        StateLog = self.get_model('StateLog')

        backend.setup_model(StateLog)

        pre_transition.connect(backend.pre_transition_callback)
        post_transition.connect(backend.post_transition_callback)
Ejemplo n.º 3
0
    def ready(self):
        from django_fsm.signals import post_transition
        from shop.models.fields import JSONField
        from rest_framework.serializers import ModelSerializer
        from shop.rest.fields import JSONSerializerField
        from shop.models.notification import order_event_notification

        post_transition.connect(order_event_notification)

        # add JSONField to the map of customized serializers
        ModelSerializer.serializer_field_mapping[JSONField] = JSONSerializerField

        # perform some sanity checks
        ForeignKeyBuilder.check_for_pending_mappings()
Ejemplo n.º 4
0
    def ready(self):
        from django_fsm.signals import post_transition
        from shop.models.fields import JSONField
        from rest_framework.serializers import ModelSerializer
        from shop.deferred import ForeignKeyBuilder
        from shop.rest.fields import JSONSerializerField
        from shop.models.notification import order_event_notification

        post_transition.connect(order_event_notification)

        # add JSONField to the map of customized serializers
        ModelSerializer.serializer_field_mapping[JSONField] = JSONSerializerField

        # perform some sanity checks
        ForeignKeyBuilder.check_for_pending_mappings()
Ejemplo n.º 5
0
    def test_invoice_workflow(self):
        post_transition.disconnect(generate_invoice_pdf, sender=Invoice, dispatch_uid="generate_invoice_pdf")
        self.invoice_test1.state_open()
        post_transition.connect(generate_invoice_pdf, sender=Invoice, dispatch_uid="generate_invoice_pdf")

        # Workflow
        self.assertEqual(self.invoice_test1.state,InvoiceStatus.OPEN)
        self.invoice_test1.state_approved()
        self.assertEqual(self.invoice_test1.state,InvoiceStatus.APPROVED)
        self.invoice_test1.state_sent()
        self.assertEqual(self.invoice_test1.state,InvoiceStatus.SENT)
        self.invoice_test1.state_paid()
        self.assertEqual(self.invoice_test1.state,InvoiceStatus.PAID)
        self.invoice_test2.state_rejected()
        self.assertEqual(self.invoice_test2.state,InvoiceStatus.REJECTED)
Ejemplo n.º 6
0
    def ready(self):
        from django_fsm.signals import post_transition
        from jsonfield.fields import JSONField
        from rest_framework.serializers import ModelSerializer
        from shop.rest.serializers import JSONSerializerField
        from shop.models.notification import order_event_notification

        post_transition.connect(order_event_notification)

        # Monkey patches for Django-1.7
        if get_version() < (1, 8):
            from django.utils import numberformat
            from shop.patches import numberformat as patched_numberformat
            numberformat.format = patched_numberformat.format

        # add JSONField to the map of customized serializers
        ModelSerializer.serializer_field_mapping[JSONField] = JSONSerializerField
Ejemplo n.º 7
0
    def ready(self):
        from django_fsm.signals import post_transition
        from jsonfield.fields import JSONField
        from rest_framework.serializers import ModelSerializer
        from shop.rest.serializers import JSONSerializerField
        from shop.models.notification import order_event_notification

        post_transition.connect(order_event_notification)

        # Monkey patches for Django-1.8
        if get_tuple_version()[:2] < (1, 9):
            from django.utils import numberformat
            from shop.patches import numberformat as patched_numberformat
            numberformat.format = patched_numberformat.format

        # add JSONField to the map of customized serializers
        ModelSerializer.serializer_field_mapping[JSONField] = JSONSerializerField
Ejemplo n.º 8
0
    def ready(self):
        from django_fsm.signals import post_transition
        from jsonfield.fields import JSONField
        from rest_framework.serializers import ModelSerializer
        from shop.rest.fields import JSONSerializerField
        from shop.models.notification import order_event_notification

        post_transition.connect(order_event_notification)

        # Monkey patches for Django-1.8
        if get_tuple_version()[:2] < (1, 9):
            from django.utils import numberformat
            from shop.patches import numberformat as patched_numberformat
            numberformat.format = patched_numberformat.format

        # add JSONField to the map of customized serializers
        ModelSerializer.serializer_field_mapping[JSONField] = JSONSerializerField

        # perform some sanity checks
        ForeignKeyBuilder.check_for_pending_mappings()
Ejemplo n.º 9
0
        html_template="email/admin/student_registered.html",
        context={'new_profile': student, 'user': student},
    )
    action.send(student, verb='has registered')


def student_missing_information_mail(sender, instance, name, source, target, **kwargs):
    if target == StudentProfileState.MISSING_INFORMATION and not is_duplicate_transition(name, instance):
        with translation.override(instance.get_preferred_language()):
            send_templated_mail(
                subject=_("Your profile at Motius is incomplete"),
                html_template='email/student/student_missing_information.html',
                recipient_list=[instance.user.email],
                context={'profile': instance, 'user': instance.user}
            )
post_transition.connect(student_missing_information_mail, sender=StudentProfile,
                        dispatch_uid="student_missing_information_mail")


def student_accepted_mail(sender, instance, name, source, target, **kwargs):
    if target == StudentProfileState.ACCEPTED and not is_duplicate_transition(name, instance):
        with translation.override(instance.get_preferred_language()):
            mail = send_templated_mail(
                subject=_("We've accepted you for Motius"),
                html_template='email/student/student_accepted.html',
                recipient_list=[instance.user.email],
                context={'profile': instance, 'user': instance.user},
                skip_sending=True,
            )

            # Attach student guide to email
            student_guide = finders.find('pdf/student_guide_%s.pdf' % instance.get_preferred_language())
Ejemplo n.º 10
0
    signal_counter = models.IntegerField(default=0)
    state = FSMField(default="SUBMITTED_BY_USER")

    @transition(field=state, source="SUBMITTED_BY_USER", target="REVIEW_USER")
    @transition(field=state,
                source="SUBMITTED_BY_ADMIN",
                target="REVIEW_ADMIN")
    @transition(field=state,
                source="SUBMITTED_BY_ANONYMOUS",
                target="REVIEW_ANONYMOUS")
    def review(self):
        self.counter += 1

    class Meta:
        app_label = 'testapp'


def count_calls(sender, instance, name, source, target, **kwargs):
    instance.signal_counter += 1


post_transition.connect(count_calls, sender=TestModel)


class TestStateProxy(TestCase):
    def test_transition_method_called_once(self):
        model = TestModel()
        model.review()
        self.assertEqual(1, model.counter)
        # BUG self.assertEqual(1, model.signal_counter)
Ejemplo n.º 11
0
    def ready(self):
        PriceEstimate = self.get_model('PriceEstimate')
        DefaultPriceListItem = self.get_model('DefaultPriceListItem')

        signals.post_save.connect(
            handlers.
            make_autocalculate_price_estimate_invisible_on_manual_estimate_creation,
            sender=PriceEstimate,
            dispatch_uid=
            ('nodeconductor.cost_tracking.handlers.'
             'make_autocalculate_price_estimate_invisible_on_manual_estimate_creation'
             ))

        signals.post_delete.connect(
            handlers.
            make_autocalculated_price_estimate_visible_on_manual_estimate_deletion,
            sender=PriceEstimate,
            dispatch_uid=
            ('nodeconductor.cost_tracking.handlers.'
             'make_autocalculated_price_estimate_visible_on_manual_estimate_deletion'
             ))

        signals.pre_save.connect(
            handlers.
            make_autocalculate_price_estimate_invisible_if_manually_created_estimate_exists,
            sender=PriceEstimate,
            dispatch_uid=
            ('nodeconductor.cost_tracking.handlers.'
             'make_autocalculate_price_estimate_invisible_if_manually_created_estimate_exists'
             ))

        for index, service in enumerate(
                structure_models.Service.get_all_models()):
            signals.post_save.connect(
                handlers.create_price_list_items_for_service,
                sender=service,
                dispatch_uid=
                ('nodeconductor.cost_tracking.handlers.create_price_list_items_for_service_{}_{}'
                 .format(service.__name__, index)))

        for index, resource in enumerate(
                structure_models.Resource.get_all_models()):
            post_transition.connect(
                handlers.estimate_costs,
                sender=resource,
                dispatch_uid=
                'nodeconductor.cost_tracking.handlers.estimate_costs_{}_{}'.
                format(resource.__name__, index),
            )

        signals.post_save.connect(
            handlers.change_price_list_items_if_default_was_changed,
            sender=DefaultPriceListItem,
            dispatch_uid=
            'nodeconductor.cost_tracking.handlers.change_price_list_items_if_default_was_changed'
        )

        signals.post_delete.connect(
            handlers.delete_price_list_items_if_default_was_deleted,
            sender=DefaultPriceListItem,
            dispatch_uid=
            'nodeconductor.cost_tracking.handlers.delete_price_list_items_if_default_was_deleted'
        )

        for index, model in enumerate(PriceEstimate.get_estimated_models()):
            signals.pre_delete.connect(
                handlers.delete_price_estimate_on_scope_deletion,
                sender=model,
                dispatch_uid=
                ('nodeconductor.cost_tracking.handlers.delete_price_estimate_on_scope_deletion_{}_{}'
                 .format(model.__name__, index)))
Ejemplo n.º 12
0
class TestModel(models.Model):
    counter = models.IntegerField(default=0)
    signal_counter = models.IntegerField(default=0)
    state = FSMField(default="SUBMITTED_BY_USER")

    @transition(field=state, source="SUBMITTED_BY_USER", target="REVIEW_USER")
    @transition(field=state, source="SUBMITTED_BY_ADMIN", target="REVIEW_ADMIN")
    @transition(field=state, source="SUBMITTED_BY_ANONYMOUS", target="REVIEW_ANONYMOUS")
    def review(self):
        self.counter += 1

    class Meta:
        app_label = 'testapp'


def count_calls(sender, instance, name, source, target, **kwargs):
    instance.signal_counter += 1


post_transition.connect(count_calls, sender=TestModel)


class TestStateProxy(TestCase):
    def test_transition_method_called_once(self):
        model = TestModel()
        model.review()
        self.assertEqual(1, model.counter)
        # BUG self.assertEqual(1, model.signal_counter)
    
Ejemplo n.º 13
0
from django_fsm.signals import pre_transition, post_transition

from .managers import StateLogManager
from .utils import import_class_by_path


class StateLog(models.Model):
    timestamp = models.DateTimeField(default=now)
    by = models.ForeignKey(getattr(settings, 'AUTH_USER_MODEL', 'auth.User'), blank=True, null=True)
    state = models.CharField(max_length=255, db_index=True)
    transition = models.CharField(max_length=255)

    content_type = models.ForeignKey(ContentType)
    object_id = models.PositiveIntegerField(db_index=True)
    content_object = GenericForeignKey('content_type', 'object_id')

    objects = StateLogManager()

    def __unicode__(self):
        return '{} - {} - {}'.format(
            self.timestamp,
            self.content_object,
            self.transition
        )

backend = import_class_by_path(settings.DJANGO_FSM_LOG_STORAGE_METHOD)
backend.setup_model(StateLog)
pre_transition.connect(backend.pre_transition_callback)
post_transition.connect(backend.post_transition_callback)
Ejemplo n.º 14
0
Archivo: models.py Proyecto: taoy/deis
        _etcd_client.delete('/deis/domains/{}'.format(app))


# Log significant app-related events
post_save.connect(_log_build_created, sender=Build, dispatch_uid='api.models.log')
post_save.connect(_log_release_created, sender=Release, dispatch_uid='api.models.log')
post_save.connect(_log_config_updated, sender=Config, dispatch_uid='api.models.log')
post_save.connect(_log_domain_added, sender=Domain, dispatch_uid='api.models.log')
post_delete.connect(_log_domain_removed, sender=Domain, dispatch_uid='api.models.log')


# save FSM transitions as they happen
def _save_transition(**kwargs):
    kwargs['instance'].save()

post_transition.connect(_save_transition)

# wire up etcd publishing if we can connect
try:
    _etcd_client = etcd.Client(host=settings.ETCD_HOST, port=int(settings.ETCD_PORT))
    _etcd_client.get('/deis')
except etcd.EtcdException:
    logger.log(logging.WARNING, 'Cannot synchronize with etcd cluster')
    _etcd_client = None

if _etcd_client:
    post_save.connect(_etcd_publish_key, sender=Key, dispatch_uid='api.models')
    post_delete.connect(_etcd_purge_key, sender=Key, dispatch_uid='api.models')
    post_delete.connect(_etcd_purge_user, sender=User, dispatch_uid='api.models')
    post_save.connect(_etcd_publish_domains, sender=Domain, dispatch_uid='api.models')
    post_delete.connect(_etcd_publish_domains, sender=Domain, dispatch_uid='api.models')
Ejemplo n.º 15
0
# -*- coding: utf-8 -*-
from __future__ import unicode_literals

from django_fsm.signals import post_transition

from edw.tasks import send_notification


def transition_event_notification(sender, instance, name, source, target, **kwargs):
    if hasattr(instance, 'send_notification'):
        send_notification.apply_async(
            kwargs={
                'model_name': instance.__class__.__name__,
                'instance_id': instance.id,
                'source': source,
                'target': target,
            }
        )
    return


post_transition.connect(transition_event_notification)
Ejemplo n.º 16
0
 def setUp(self):
     self.pre_transition_called = False
     self.post_transition_called = False
     pre_transition.connect(self.on_pre_transition, sender=MultiResultTest)
     post_transition.connect(self.on_post_transition, sender=MultiResultTest)
 def setUp(self):
     self.model = ExceptionalBlogPost()
     post_transition.connect(self.on_post_transition, sender=ExceptionalBlogPost)
     self.post_transition_data = None
Ejemplo n.º 18
0
 def setUp(self):
     self.model = ExceptionalBlogPost()
     post_transition.connect(self.on_post_transition,
                             sender=ExceptionalBlogPost)
     self.post_transition_data = None
Ejemplo n.º 19
0
    @classmethod
    def remove(cls, callback):
        scheduler = cls.get_scheduler()
        if scheduler.get_job(callback.__name__) is not None:
            scheduler.remove_job(callback.__name__)

    @classmethod
    def get_list(cls):
        job_list = []
        scheduler = cls.get_scheduler()
        for job in scheduler.get_jobs():
            if hasattr(job, 'next_run_time'):
                status = job.next_run_time
            else:
                status = 'pending'
            job_list.append((job.name, job.func.__doc__, job.trigger, status))
        return job_list


PrintFieldsPlugIn.add_plugin(GeneralPrintPlugin)


def post_after_transition(sender, **kwargs):
    if 'exception' not in kwargs:
        instance = kwargs['instance']
        instance.save()


post_transition.connect(post_after_transition)
Ejemplo n.º 20
0
 def ready(self):
     from django_fsm.signals import post_transition
     post_transition.connect(order_event_notification)
Ejemplo n.º 21
0
 def setUp(self):
     self.model = BlogPost()
     self.pre_transition_called = False
     self.post_transition_called = False
     pre_transition.connect(self.on_pre_transition, sender=BlogPost)
     post_transition.connect(self.on_post_transition, sender=BlogPost)
Ejemplo n.º 22
0
    object_id = models.PositiveIntegerField(db_index=True)
    content_object = GenericForeignKey('content_type', 'object_id')

    objects = StateLogManager()
    
    class Meta:
        get_latest_by = 'timestamp'

    def __str__(self):
        return '{} - {} - {}'.format(
            self.timestamp,
            self.content_object,
            self.transition
        )

    def get_state_display(self):
        fsm_obj = self.content_object
        for field in fsm_obj._meta.fields:
            if isinstance(field, FSMFieldMixin):
                state_display = dict(field.flatchoices).get(self.state, self.state)
                return force_text(state_display, strings_only=True)

try:
    import django.apps
except: # django < 1.7
    backend = import_by_path(settings.DJANGO_FSM_LOG_STORAGE_METHOD)
    backend.setup_model(StateLog)

    pre_transition.connect(backend.pre_transition_callback)
    post_transition.connect(backend.post_transition_callback)
Ejemplo n.º 23
0
post_save.connect(_log_build_created, sender=Build, dispatch_uid='api.models.log')
post_save.connect(_log_release_created, sender=Release, dispatch_uid='api.models.log')
post_save.connect(_log_config_updated, sender=Config, dispatch_uid='api.models.log')
post_save.connect(_log_domain_added, sender=Domain, dispatch_uid='api.models.log')
post_delete.connect(_log_domain_removed, sender=Domain, dispatch_uid='api.models.log')


# save FSM transitions as they happen
def _save_transition(**kwargs):
    kwargs['instance'].save()
    # close database connections after transition
    # to avoid leaking connections inside threads
    from django.db import connection
    connection.close()

post_transition.connect(_save_transition)

# wire up etcd publishing if we can connect
try:
    _etcd_client = etcd.Client(host=settings.ETCD_HOST, port=int(settings.ETCD_PORT))
    _etcd_client.get('/deis')
except etcd.EtcdException:
    logger.log(logging.WARNING, 'Cannot synchronize with etcd cluster')
    _etcd_client = None

if _etcd_client:
    post_save.connect(_etcd_publish_key, sender=Key, dispatch_uid='api.models')
    post_delete.connect(_etcd_purge_key, sender=Key, dispatch_uid='api.models')
    post_delete.connect(_etcd_purge_user, sender=User, dispatch_uid='api.models')
    post_save.connect(_etcd_publish_domains, sender=Domain, dispatch_uid='api.models')
    post_delete.connect(_etcd_purge_domains, sender=Domain, dispatch_uid='api.models')
Ejemplo n.º 24
0
def create_standard_obm(sender, instance, created, **kwargs):
    if created and instance.client.outstanding_balance != 0:
        try:
            mod = OutstandingBalanceModifierTag.objects.get(name='Standard')
        except OutstandingBalanceModifierTag.DoesNotExist:
            pass
        else:
            OutstandingBalanceModifier.objects.create(
                                                    invoice=instance,
                                                    memo='Outstanding Balance',
                                                    amount=mod.amount,
                                                    percentage=mod.percentage,
                                                    charge_type=mod
                                                    )
post_save.connect(create_standard_obm, sender=ClientInvoice)
post_transition.connect(create_pdf, sender=ClientInvoice)

class TutorInvoice(Invoice):
    tutor = models.ForeignKey('Tutor.Tutor')

    def close_invoice(self):
        self.save()
        memo = unicode(self.tutor) + ' ' + unicode(self.start_date) + \
                ' through ' + unicode(self.end_date)
        Transaction.objects.create(memo=memo, 
                                    date=timezone.now(), 
                                    payment=self.amount,
                                    payee_object=self.tutor)

    def open_invoice(self):
        self.save()
 def setUp(self):
     self.model = BlogPost()
     self.pre_transition_called = False
     self.post_transition_called = False
     pre_transition.connect(self.on_pre_transition, sender=BlogPost)
     post_transition.connect(self.on_post_transition, sender=BlogPost)
Ejemplo n.º 26
0
from motius_user.models import StudentProfile
from .enums import InvoiceStatus
from .models import Invoice, IbanBankAccount


def generate_invoice_pdf(sender, instance, name, source, target, **kwargs):
    if target == InvoiceStatus.OPEN and not is_duplicate_transition(name, instance):
        with tempfile.NamedTemporaryFile() as fh:
            motius_pdf.from_url(
                settings.SITE_URL + reverse('payment_invoice_html', args=[instance.pk]),
                fh.name,
            )
            instance.pdf = File(fh)
            instance.save()
        action.send(instance, verb='new invoice generated for', target=instance.recipient)
post_transition.connect(generate_invoice_pdf, sender=Invoice, dispatch_uid="generate_invoice_pdf")


def update_default_iban(sender, instance, created, raw, **kwargs):
    """
    Unsets any other defaults if the saved instance is default
    """
    if instance.default:
        instance.student.bank_accounts\
            .filter(default=True)\
            .exclude(pk=instance.pk)\
            .update(default=False)
post_save.connect(update_default_iban, sender=IbanBankAccount, dispatch_uid="update_default_iban")


def delete_default_iban(sender, instance, using, **kwargs):