Example #1
0
    def test_next_wakeup(self):
        "Minimum of the future generations."
        now_value = now()
        create_gen = partial(
            RecurrentGenerator.objects.create,
            user=self.user,
            ct=self.ct,
            template=self._create_ticket_template(),
        )
        create_gen(
            name='Gen1',
            periodicity=self._get_weekly(),
            first_generation=now_value - timedelta(days=8),
            last_generation=now_value - timedelta(days=1),
        )  # In 6 days
        create_gen(
            name='Gen2',
            periodicity=date_period_registry.get_period('days', 1),
            first_generation=now_value - timedelta(hours=34),
            last_generation=now_value - timedelta(hours=10),
        )  # In 14 hours ==> that's the one !
        create_gen(
            name='Gen3',
            periodicity=date_period_registry.get_period('months', 1),
            first_generation=now_value - timedelta(weeks=5),
            last_generation=now_value - timedelta(weeks=1),
        )  # In ~3 weeks

        job = self._get_job()
        wakeup = job.type.next_wakeup(job, now_value)
        self.assertIsNotNone(wakeup)
        self.assertDatetimesAlmostEqual(now_value + timedelta(hours=14),
                                        wakeup)
Example #2
0
    def populate(self):
        SettingValue.objects.get_or_create(key_id=sandbox_key.id,
                                           defaults={'value': False})

        # CremeUser = get_user_model()
        #
        # try:
        #     user = CremeUser.objects.get(pk=settings.CREME_GET_EMAIL_JOB_USER_ID)
        # except (CremeUser.DoesNotExist, AttributeError):
        #     user = CremeUser.objects.get_admin()
        user = get_user_model().objects.get_admin()

        Job.objects.get_or_create(type_id=crudity_synchronize_type.id,
                                  defaults={
                                      'language':
                                      settings.LANGUAGE_CODE,
                                      'periodicity':
                                      date_period_registry.get_period(
                                          'minutes', 30),
                                      'status':
                                      Job.STATUS_OK,
                                      'data': {
                                          'user': user.id
                                      },
                                  })
Example #3
0
    def test_editview02(self):
        "last_generation has been filled => cannot edit first_generation"
        user = self.user

        now_value = now().replace(
            microsecond=0)  # MySQL does not record microseconds...
        gen = RecurrentGenerator.objects.create(
            name='Gen1',
            user=user,
            first_generation=now_value,
            last_generation=now_value,
            periodicity=date_period_registry.get_period('months', 1),
            ct=self.ct,
            template=self._create_ticket_template(title='TicketTemplate #1'),
        )

        name = gen.name.upper()
        response = self.client.post(
            gen.get_edit_absolute_url(),
            follow=True,
            data={
                'user': user.id,
                'name': name,

                # Should not be used
                'first_generation': '12-06-2014 10:00',
                'periodicity_0': 'months',
                'periodicity_1': '3',
            },
        )
        self.assertNoFormError(response)

        gen = self.refresh(gen)
        self.assertEqual(now_value, gen.first_generation)
Example #4
0
 def _oldify_temp_file(self, temp_file, days):
     "Make the instance older"
     FileRef.objects \
            .filter(id=temp_file.id) \
            .update(created=temp_file.created
                            - date_period_registry.get_period('days', days).as_timedelta()
                            - timedelta(hours=1)
                   )
Example #5
0
    def _get_job(self, days=1):
        job = self.get_object_or_fail(Job, type_id=temp_files_cleaner_type.id)
        job.data = {
            'delay': date_period_registry.get_period('days', days).as_dict()
        }
        job.save()

        return job
Example #6
0
    def test_editview01(self):
        user = self.user

        tpl1 = self._create_ticket_template(title='TicketTemplate #1')
        tpl2 = self._create_ticket_template(title='TicketTemplate #2')

        gen = RecurrentGenerator.objects.create(
            name='Gen1',
            user=user,
            first_generation=now(),
            last_generation=None,
            periodicity=date_period_registry.get_period('weeks', 2),
            ct=self.ct,
            template=tpl1,
        )

        url = gen.get_edit_absolute_url()
        self.assertGET200(url)

        queue = JobSchedulerQueue.get_main_queue()
        queue.clear()

        name = gen.name.upper()
        response = self.client.post(
            url,
            follow=True,
            data={
                'user': user.id,
                'name': name,
                'first_generation': '12-06-2014 10:00',
                'periodicity_0': 'months',
                'periodicity_1': '1',

                # should not be used
                'ct': ContentType.objects.get_for_model(Priority).id,
                'template': tpl2.id,
            },
        )
        self.assertNoFormError(response)
        self.assertRedirects(response, gen.get_absolute_url())
        self.assertTemplateUsed(response, 'recurrents/view_generator.html')

        gen = self.refresh(gen)
        self.assertEqual(name, gen.name)
        self.assertEqual(
            self.create_datetime(year=2014, month=6, day=12, hour=10),
            gen.first_generation,
        )
        self.assertEqual(self.ct, gen.ct)
        self.assertEqual(tpl1, gen.template.get_real_entity())
        self.assertEqual({
            'type': 'months',
            'value': 1
        }, gen.periodicity.as_dict())

        self.assertEqual(1, len(queue.refreshed_jobs))
Example #7
0
    def test_refresh_job(self):
        queue = JobManagerQueue.get_main_queue()
        job = self._get_job()
        tpl = self._create_ticket_template()
        now_value = now()
        gen = RecurrentGenerator.objects.create(
            name='Generator',
            user=self.user,
            first_generation=now_value + timedelta(days=2),
            last_generation=None,
            periodicity=date_period_registry.get_period('weeks', 2),
            ct=self.ct,
            template=tpl,
        )

        queue.clear()
        gen.name = 'My Generator'
        gen.save()
        self.assertFalse(queue.refreshed_jobs)

        gen.first_generation = now_value + timedelta(hours=3)
        gen.save()
        refreshed_jobs = queue.refreshed_jobs
        self.assertEqual(1, len(refreshed_jobs))
        self.assertEqual(job, refreshed_jobs[0][0])

        queue.clear()
        gen.name = 'My Generator again'
        gen.save()
        self.assertFalse(
            queue.refreshed_jobs
        )  # The new value of 'first_generation' is cached -> no new refreshing

        gen.periodicity = date_period_registry.get_period('weeks', 1)
        gen.save()
        self.assertEqual(1, len(queue.refreshed_jobs))

        queue.clear()
        gen.name = 'My Generator again & again'
        gen.save()
        self.assertFalse(
            queue.refreshed_jobs
        )  # The new value of 'periodicity' is cached -> no new refreshing
Example #8
0
    def populate(self):
        SettingValue.objects.get_or_create(key_id=sandbox_key.id, defaults={'value': False})

        user = get_user_model().objects.get_admin()
        Job.objects.get_or_create(type_id=crudity_synchronize_type.id,
                                  defaults={'language':    settings.LANGUAGE_CODE,
                                            'periodicity': date_period_registry.get_period('minutes', 30),
                                            'status':      Job.STATUS_OK,
                                            'data':        {'user': user.id},
                                           },
                                 )
Example #9
0
    def populate(self):
        # SettingValue.create_if_needed(key=mapi_server_url_key, user=None, value='')
        # SettingValue.create_if_needed(key=mapi_domain_key,     user=None, value='')
        # SettingValue.create_if_needed(key=mapi_server_ssl_key, user=None, value=False)
        create_svalue = SettingValue.objects.get_or_create
        create_svalue(key_id=mapi_server_url_key.id, defaults={'value': ''})
        create_svalue(key_id=mapi_domain_key.id, defaults={'value': ''})
        create_svalue(key_id=mapi_server_ssl_key.id, defaults={'value': False})

        Job.objects.get_or_create(type_id=activesync_type.id,
                                  defaults={
                                      'language':
                                      settings.LANGUAGE_CODE,
                                      'periodicity':
                                      date_period_registry.get_period(
                                          'minutes', 30),
                                      'status':
                                      Job.STATUS_OK,
                                  })
Example #10
0
    def populate(self):
        SettingValue.objects.get_or_create(key_id=sandbox_key.id,
                                           defaults={'value': False})

        user = get_user_model().objects.get_admin()
        Job.objects.get_or_create(
            type_id=crudity_synchronize_type.id,
            defaults={
                'language': settings.LANGUAGE_CODE,
                'periodicity': date_period_registry.get_period('minutes', 30),
                'status': Job.STATUS_OK,
                'data': {
                    'user': user.id
                },
            },
        )

        # ---------------------------
        # TODO: move to a "not already_populated" section in creme2.4
        if not MenuConfigItem.objects.filter(
                entry_id__startswith='crudity-').exists():
            container = MenuConfigItem.objects.get_or_create(
                entry_id=ContainerEntry.id,
                entry_data={'label': _('Tools')},
                defaults={'order': 100},
            )[0]

            create_mitem = partial(MenuConfigItem.objects.create,
                                   parent=container)
            create_mitem(
                entry_id=Separator1Entry.id,
                entry_data={'label': _('External data')},
                order=250,
            )
            create_mitem(entry_id=menu.WaitingActionsEntry.id, order=255)
            create_mitem(entry_id=menu.CrudityHistoryEntry.id, order=260)
Example #11
0
 def _get_weekly(self):
     return date_period_registry.get_period('weeks', 1)
Example #12
0
    def populate(self):
        already_populated = RelationType.objects.filter(
            pk=constants.REL_SUB_SOLD).exists()

        Act = commercial.get_act_model()
        ActObjectivePattern = commercial.get_pattern_model()
        Strategy = commercial.get_strategy_model()
        Contact = persons.get_contact_model()
        Organisation = persons.get_organisation_model()
        Product = products.get_product_model()
        Service = products.get_service_model()

        RelationType.create(
            (constants.REL_SUB_SOLD, _('has sold'), [Contact, Organisation]),
            (constants.REL_OBJ_SOLD, _('has been sold by'), [Product, Service
                                                             ]),
        )

        complete_goal_models = {*creme_registry.iter_entity_models()}
        complete_goal_models.discard(Strategy)
        if apps.is_installed('creme.billing'):
            from creme import billing
            from creme.billing.registry import lines_registry

            complete_goal_models.discard(billing.get_credit_note_model())
            complete_goal_models.discard(billing.get_template_base_model())
            complete_goal_models.difference_update(lines_registry)

        RelationType.create(
            (
                constants.REL_SUB_COMPLETE_GOAL,
                _('completes a goal of the commercial action'),
                complete_goal_models,
            ),
            (
                constants.REL_OBJ_COMPLETE_GOAL,
                _('is completed thanks to'),
                [Act],
            ),
        )

        # ---------------------------
        CremePropertyType.create(constants.PROP_IS_A_SALESMAN,
                                 _('is a salesman'), [Contact])

        # ---------------------------
        MarketSegment.objects.get_or_create(
            property_type=None,
            defaults={'name': _('All the organisations')},
        )

        # ---------------------------
        for i, title in enumerate(
            [_('Phone calls'), _('Show'),
             _('Demo')], start=1):
            create_if_needed(ActType, {'pk': i}, title=title, is_custom=False)

        # ---------------------------
        create_hf = HeaderFilter.objects.create_if_needed
        create_hf(
            pk=constants.DEFAULT_HFILTER_ACT,
            model=Act,
            name=_('Com Action view'),
            cells_desc=[
                (EntityCellRegularField, {
                    'name': 'name'
                }),
                (EntityCellRegularField, {
                    'name': 'expected_sales'
                }),
                (EntityCellRegularField, {
                    'name': 'due_date'
                }),
            ],
        )
        create_hf(
            pk=constants.DEFAULT_HFILTER_STRATEGY,
            model=Strategy,
            name=_('Strategy view'),
            cells_desc=[(EntityCellRegularField, {
                'name': 'name'
            })],
        )
        create_hf(
            pk=constants.DEFAULT_HFILTER_PATTERN,
            model=ActObjectivePattern,
            name=_('Objective pattern view'),
            cells_desc=[
                (EntityCellRegularField, {
                    'name': 'name'
                }),
                (EntityCellRegularField, {
                    'name': 'segment'
                }),
            ],
        )

        # ---------------------------
        def build_custom_form_items(creation_descriptor, edition_descriptor,
                                    field_names):
            base_groups_desc = [
                {
                    'name':
                    _('General information'),
                    'layout':
                    LAYOUT_DUAL_FIRST,
                    'cells': [
                        *((EntityCellRegularField, {
                            'name': fname
                        }) for fname in field_names),
                        (
                            EntityCellCustomFormSpecial,
                            {
                                'name':
                                EntityCellCustomFormSpecial.
                                REMAINING_REGULARFIELDS
                            },
                        ),
                    ],
                },
                {
                    'name': _('Description'),
                    'layout': LAYOUT_DUAL_SECOND,
                    'cells': [
                        (EntityCellRegularField, {
                            'name': 'description'
                        }),
                    ],
                },
                {
                    'name':
                    _('Custom fields'),
                    'layout':
                    LAYOUT_DUAL_SECOND,
                    'cells': [
                        (
                            EntityCellCustomFormSpecial,
                            {
                                'name':
                                EntityCellCustomFormSpecial.
                                REMAINING_CUSTOMFIELDS
                            },
                        ),
                    ],
                },
            ]

            CustomFormConfigItem.objects.create_if_needed(
                descriptor=creation_descriptor,
                groups_desc=[
                    *base_groups_desc,
                    {
                        'name':
                        _('Properties'),
                        'cells': [
                            (
                                EntityCellCustomFormSpecial,
                                {
                                    'name':
                                    EntityCellCustomFormSpecial.
                                    CREME_PROPERTIES
                                },
                            ),
                        ],
                    },
                    {
                        'name':
                        _('Relationships'),
                        'cells': [
                            (
                                EntityCellCustomFormSpecial,
                                {
                                    'name':
                                    EntityCellCustomFormSpecial.RELATIONS
                                },
                            ),
                        ],
                    },
                ],
            )
            CustomFormConfigItem.objects.create_if_needed(
                descriptor=edition_descriptor,
                groups_desc=base_groups_desc,
            )

        build_custom_form_items(
            creation_descriptor=custom_forms.ACT_CREATION_CFORM,
            edition_descriptor=custom_forms.ACT_EDITION_CFORM,
            field_names=[
                'user',
                'name',
                'expected_sales',
                'cost',
                'goal',
                'start',
                'due_date',
                'act_type',
                'segment',
            ],
        )
        build_custom_form_items(
            creation_descriptor=custom_forms.PATTERN_CREATION_CFORM,
            edition_descriptor=custom_forms.PATTERN_EDITION_CFORM,
            field_names=[
                'user',
                'name',
                'average_sales',
                'segment',
            ],
        )
        build_custom_form_items(
            creation_descriptor=custom_forms.STRATEGY_CREATION_CFORM,
            edition_descriptor=custom_forms.STRATEGY_EDITION_CFORM,
            field_names=[
                'user',
                'name',
            ],
        )

        # ---------------------------
        create_searchconf = SearchConfigItem.objects.create_if_needed
        create_searchconf(Act, ['name', 'expected_sales', 'cost', 'goal'])
        create_searchconf(Strategy, ['name'])
        create_searchconf(ActObjectivePattern, [], disabled=True)

        # ---------------------------
        SettingValue.objects.get_or_create(
            key_id=setting_keys.orga_approaches_key.id,
            defaults={'value': True},
        )

        # ---------------------------
        Job.objects.get_or_create(
            type_id=creme_jobs.com_approaches_emails_send_type.id,
            defaults={
                'language': settings.LANGUAGE_CODE,
                'periodicity': date_period_registry.get_period('days', 1),
                'status': Job.STATUS_OK,
                # The CommercialApproach field for Activities' CustomForms is not
                # in the default configuration, so a enabled job would be annoying.
                'enabled': False,
            },
        )

        # ---------------------------
        # TODO: move to "not already_populated" section in creme2.4
        if not MenuConfigItem.objects.filter(
                entry_id__startswith='commercial-').exists():
            container = MenuConfigItem.objects.get_or_create(
                entry_id=ContainerEntry.id,
                entry_data={'label': _('Commercial')},
                defaults={'order': 30},
            )[0]

            create_mitem = MenuConfigItem.objects.create
            create_mitem(entry_id=menu.ActsEntry.id,
                         order=50,
                         parent=container)
            create_mitem(entry_id=menu.StrategiesEntry.id,
                         order=55,
                         parent=container)
            create_mitem(entry_id=menu.SegmentsEntry.id,
                         order=60,
                         parent=container)
            create_mitem(entry_id=menu.PatternsEntry.id,
                         order=70,
                         parent=container)

            directory = MenuConfigItem.objects.filter(
                entry_id=ContainerEntry.id,
                entry_data={
                    'label': _('Directory')
                },
            ).first()
            if directory is not None:
                create_mitem(entry_id=menu.SalesmenEntry.id,
                             order=100,
                             parent=directory)

            creations = MenuConfigItem.objects.filter(
                entry_id=ContainerEntry.id,
                entry_data={
                    'label': _('+ Creation')
                },
            ).first()
            if creations is not None:
                create_mitem(entry_id=menu.ActCreationEntry.id,
                             order=40,
                             parent=creations)

        # ---------------------------
        if not already_populated:
            ButtonMenuItem.objects.create_if_needed(
                button=buttons.CompleteGoalButton,
                order=60,
            )

            TOP = BrickDetailviewLocation.TOP
            RIGHT = BrickDetailviewLocation.RIGHT
            LEFT = BrickDetailviewLocation.LEFT

            # BrickDetailviewLocation.objects.multi_create(
            #     defaults={'brick': bricks.ApproachesBrick, 'order': 10, 'zone': RIGHT},
            #     data=[
            #         {},  # default configuration
            #         {'model': Contact},
            #         {'model': Organisation},
            #     ]
            # )

            BrickDetailviewLocation.objects.multi_create(
                defaults={
                    'model': Act,
                    'zone': LEFT
                },
                data=[
                    {
                        'order': 5
                    },  # generic information brick
                    {
                        'brick': bricks.ActObjectivesBrick,
                        'order': 10
                    },
                    {
                        'brick': bricks.RelatedOpportunitiesBrick,
                        'order': 20
                    },
                    {
                        'brick': core_bricks.CustomFieldsBrick,
                        'order': 40
                    },
                    {
                        'brick': core_bricks.PropertiesBrick,
                        'order': 450
                    },
                    {
                        'brick': core_bricks.RelationsBrick,
                        'order': 500
                    },
                    {
                        'brick': core_bricks.HistoryBrick,
                        'order': 20,
                        'zone': RIGHT
                    },
                ],
            )
            BrickDetailviewLocation.objects.multi_create(
                defaults={
                    'model': ActObjectivePattern,
                    'zone': LEFT
                },
                data=[
                    {
                        'brick': bricks.PatternComponentsBrick,
                        'order': 10,
                        'zone': TOP
                    },
                    {
                        'order': 5
                    },
                    {
                        'brick': core_bricks.CustomFieldsBrick,
                        'order': 40
                    },
                    {
                        'brick': core_bricks.PropertiesBrick,
                        'order': 450
                    },
                    {
                        'brick': core_bricks.RelationsBrick,
                        'order': 500
                    },
                    {
                        'brick': core_bricks.HistoryBrick,
                        'order': 20,
                        'zone': RIGHT
                    },
                ],
            )
            BrickDetailviewLocation.objects.multi_create(
                defaults={
                    'model': Strategy,
                    'zone': LEFT
                },
                data=[
                    {
                        'brick': bricks.SegmentDescriptionsBrick,
                        'order': 10,
                        'zone': TOP
                    },
                    {
                        'order': 5
                    },
                    {
                        'brick': core_bricks.CustomFieldsBrick,
                        'order': 40
                    },
                    {
                        'brick': bricks.EvaluatedOrgasBrick,
                        'order': 50
                    },
                    {
                        'brick': bricks.AssetsBrick,
                        'order': 60
                    },
                    {
                        'brick': bricks.CharmsBrick,
                        'order': 70
                    },
                    {
                        'brick': core_bricks.PropertiesBrick,
                        'order': 450
                    },
                    {
                        'brick': core_bricks.RelationsBrick,
                        'order': 500
                    },
                    {
                        'brick': core_bricks.HistoryBrick,
                        'order': 20,
                        'zone': RIGHT
                    },
                ],
            )

            if apps.is_installed('creme.assistants'):
                logger.info('Assistants app is installed '
                            '=> we use the assistants blocks on detail views')

                from creme.assistants import bricks as a_bricks

                for model in (Act, ActObjectivePattern, Strategy):
                    BrickDetailviewLocation.objects.multi_create(
                        defaults={
                            'model': model,
                            'zone': RIGHT
                        },
                        data=[
                            {
                                'brick': a_bricks.TodosBrick,
                                'order': 100
                            },
                            {
                                'brick': a_bricks.MemosBrick,
                                'order': 200
                            },
                            {
                                'brick': a_bricks.AlertsBrick,
                                'order': 300
                            },
                            {
                                'brick': a_bricks.UserMessagesBrick,
                                'order': 400
                            },
                        ],
                    )

            if apps.is_installed('creme.documents'):
                # logger.info("Documents app is installed
                # => we use the documents blocks on Strategy's detail views")

                from creme.documents.bricks import LinkedDocsBrick

                BrickDetailviewLocation.objects.multi_create(
                    defaults={
                        'brick': LinkedDocsBrick,
                        'order': 600,
                        'zone': RIGHT
                    },
                    data=[
                        {
                            'model': Act
                        },
                        {
                            'model': ActObjectivePattern
                        },
                        {
                            'model': Strategy
                        },
                    ],
                )
Example #13
0
    def populate(self):
        already_populated = RelationType.objects.filter(pk=constants.REL_SUB_SOLD_BY).exists()

        Act = commercial.get_act_model()
        ActObjectivePattern = commercial.get_pattern_model()
        Strategy = commercial.get_strategy_model()
        Contact = persons.get_contact_model()
        Organisation = persons.get_organisation_model()

        RelationType.create((constants.REL_SUB_SOLD_BY,       _(u'has sold')),
                            (constants.REL_OBJ_SOLD_BY,       _(u'has been sold by')))
        RelationType.create((constants.REL_SUB_COMPLETE_GOAL, _(u'completes a goal of the commercial action')),
                            (constants.REL_OBJ_COMPLETE_GOAL, _(u'is completed thanks to'), [Act]))

        # ---------------------------
        CremePropertyType.create(constants.PROP_IS_A_SALESMAN, _(u'is a salesman'), [Contact])

        # ---------------------------
        MarketSegment.objects.get_or_create(property_type=None,
                                            defaults={'name': _(u'All the organisations')},
                                           )

        # ---------------------------
        for i, title in enumerate([_(u'Phone calls'), _(u'Show'), _(u'Demo')], start=1):
            create_if_needed(ActType, {'pk': i}, title=title, is_custom=False)

        # ---------------------------
        create_hf = HeaderFilter.create
        create_hf(pk=constants.DEFAULT_HFILTER_ACT, model=Act,
                  name=_(u'Com Action view'),
                  cells_desc=[(EntityCellRegularField, {'name': 'name'}),
                              (EntityCellRegularField, {'name': 'expected_sales'}),
                              (EntityCellRegularField, {'name': 'due_date'}),
                             ],
                 )
        create_hf(pk=constants.DEFAULT_HFILTER_STRATEGY, model=Strategy,
                  name=_(u"Strategy view"),
                  cells_desc=[(EntityCellRegularField, {'name': 'name'})],
                 )
        create_hf(pk=constants.DEFAULT_HFILTER_PATTERN, model=ActObjectivePattern,
                  name=_(u"Objective pattern view"),
                  cells_desc=[(EntityCellRegularField, {'name': 'name'}),
                              (EntityCellRegularField, {'name': 'segment'}),
                             ]
                 )

        # ---------------------------
        create_searchconf = SearchConfigItem.create_if_needed
        create_searchconf(Act, ['name', 'expected_sales', 'cost', 'goal'])
        create_searchconf(Strategy, ['name'])
        create_searchconf(ActObjectivePattern, [], disabled=True)

        # ---------------------------
        SettingValue.objects.get_or_create(key_id=setting_keys.orga_approaches_key.id, defaults={'value': True})

        # ---------------------------
        Job.objects.get_or_create(type_id=creme_jobs.com_approaches_emails_send_type.id,
                                  defaults={'language':    settings.LANGUAGE_CODE,
                                            'periodicity': date_period_registry.get_period('days', 1),
                                            'status':      Job.STATUS_OK,
                                           }
                                 )

        # ---------------------------
        if not already_populated:
            ButtonMenuItem.create_if_needed(pk='commercial-complete_goal_button',
                                            model=None, button=buttons.CompleteGoalButton, order=60,
                                           )

            create_bdl = BrickDetailviewLocation.create_if_needed
            TOP = BrickDetailviewLocation.TOP
            RIGHT = BrickDetailviewLocation.RIGHT
            LEFT = BrickDetailviewLocation.LEFT

            create_bdl(brick_id=bricks.ApproachesBrick.id_, order=10, zone=RIGHT)
            create_bdl(brick_id=bricks.ApproachesBrick.id_, order=10, zone=RIGHT, model=Contact)
            create_bdl(brick_id=bricks.ApproachesBrick.id_, order=10, zone=RIGHT, model=Organisation)

            BrickDetailviewLocation.create_4_model_brick(             order=5,   zone=LEFT,  model=Act)
            create_bdl(brick_id=bricks.ActObjectivesBrick.id_,        order=10,  zone=LEFT,  model=Act)
            create_bdl(brick_id=bricks.RelatedOpportunitiesBrick.id_, order=20,  zone=LEFT,  model=Act)
            create_bdl(brick_id=core_bricks.CustomFieldsBrick.id_,    order=40,  zone=LEFT,  model=Act)
            create_bdl(brick_id=core_bricks.PropertiesBrick.id_,      order=450, zone=LEFT,  model=Act)
            create_bdl(brick_id=core_bricks.RelationsBrick.id_,       order=500, zone=LEFT,  model=Act)
            create_bdl(brick_id=core_bricks.HistoryBrick.id_,         order=20,  zone=RIGHT, model=Act)

            create_bdl(brick_id=bricks.PatternComponentsBrick.id_, order=10,  zone=TOP,   model=ActObjectivePattern)
            BrickDetailviewLocation.create_4_model_brick(          order=5,   zone=LEFT,  model=ActObjectivePattern)
            create_bdl(brick_id=core_bricks.CustomFieldsBrick.id_, order=40,  zone=LEFT,  model=ActObjectivePattern)
            create_bdl(brick_id=core_bricks.PropertiesBrick.id_,   order=450, zone=LEFT,  model=ActObjectivePattern)
            create_bdl(brick_id=core_bricks.RelationsBrick.id_,    order=500, zone=LEFT,  model=ActObjectivePattern)
            create_bdl(brick_id=core_bricks.HistoryBrick.id_,      order=20,  zone=RIGHT, model=ActObjectivePattern)

            create_bdl(brick_id=bricks.SegmentDescriptionsBrick.id_, order=10,  zone=TOP,   model=Strategy)
            BrickDetailviewLocation.create_4_model_brick(            order=5,   zone=LEFT,  model=Strategy)
            create_bdl(brick_id=core_bricks.CustomFieldsBrick.id_,   order=40,  zone=LEFT,  model=Strategy)
            create_bdl(brick_id=bricks.EvaluatedOrgasBrick.id_,      order=50,  zone=LEFT,  model=Strategy)
            create_bdl(brick_id=bricks.AssetsBrick.id_,              order=60,  zone=LEFT,  model=Strategy)
            create_bdl(brick_id=bricks.CharmsBrick.id_,              order=70,  zone=LEFT,  model=Strategy)
            create_bdl(brick_id=core_bricks.PropertiesBrick.id_,     order=450, zone=LEFT,  model=Strategy)
            create_bdl(brick_id=core_bricks.RelationsBrick.id_,      order=500, zone=LEFT,  model=Strategy)
            create_bdl(brick_id=core_bricks.HistoryBrick.id_,        order=20,  zone=RIGHT, model=Strategy)

            if apps.is_installed('creme.assistants'):
                logger.info('Assistants app is installed => we use the assistants blocks on detail views')

                from creme.assistants import bricks as assistants_bricks

                for model in (Act, ActObjectivePattern, Strategy):
                    create_bdl(brick_id=assistants_bricks.TodosBrick.id_,        order=100, zone=RIGHT, model=model)
                    create_bdl(brick_id=assistants_bricks.MemosBrick.id_,        order=200, zone=RIGHT, model=model)
                    create_bdl(brick_id=assistants_bricks.AlertsBrick.id_,       order=300, zone=RIGHT, model=model)
                    create_bdl(brick_id=assistants_bricks.UserMessagesBrick.id_, order=400, zone=RIGHT, model=model)

            if apps.is_installed('creme.documents'):
                # logger.info("Documents app is installed => we use the documents blocks on Strategy's detail views")

                from creme.documents.bricks import LinkedDocsBrick

                for model in (Act, ActObjectivePattern, Strategy):
                    create_bdl(brick_id=LinkedDocsBrick.id_, order=600, zone=RIGHT, model=model)