def test_filtered_cells(self): hidden = 'first_name' FieldsConfig.objects.create( content_type=FakeContact, descriptions=[ (hidden, { FieldsConfig.HIDDEN: True }), ], ) rtype = self.get_object_or_fail(RelationType, id=REL_SUB_HAS) hf = HeaderFilter.objects.create_if_needed( pk='tests-hf_contact', name='Contact view', model=FakeContact, cells_desc=[ (EntityCellRegularField, { 'name': 'last_name' }), (EntityCellRegularField, { 'name': hidden }), EntityCellRelation(model=FakeContact, rtype=rtype), ], ) self.assertListEqual( [ EntityCellRegularField.build(FakeContact, 'last_name'), EntityCellRelation(model=FakeContact, rtype=rtype), ], hf.filtered_cells, )
def test_relationtype_registry01(self): "Default data + register() method." registry = lv_search.RelationSearchRegistry() cell1 = EntityCellRelation.build(model=FakeContact, rtype_id=REL_SUB_HAS) field = registry.get_field(cell=cell1, user=self.user) self.assertIsInstance(field, lv_form.RelationField) self.assertIsNone(registry.builder(REL_SUB_HAS)) self.assertEqual(lv_form.RelationField, registry.default_builder) # --- class MyRelationField(lv_form.ListViewSearchField): pass rtype2 = RelationType.create( ('test-subject_loves', 'loves'), ('test-object_loved', 'is loved by'), )[0] cell2 = EntityCellRelation(model=FakeContact, rtype=rtype2) registry.register(rtype_id=rtype2.id, sfield_builder=MyRelationField) self.assertIsInstance(registry.get_field(cell=cell2, user=self.user), MyRelationField) self.assertIsInstance(registry.get_field(cell=cell1, user=self.user), lv_form.RelationField) self.assertIsNone(registry.builder(REL_SUB_HAS)) self.assertEqual(MyRelationField, registry.builder(rtype2.id))
def test_populate_entities_relations01(self): user = self.login() create_rt = RelationType.create loved = create_rt(('test-subject_love', u'Is loving'), ('test-object_love', u'Is loved by'))[1] hated = create_rt(('test-subject_hate', u'Is hating'), ('test-object_hate', u'Is hated by'))[1] hf = HeaderFilter.create( pk='test-hf', name=u'Contact view', model=FakeContact, cells_desc=[ EntityCellRegularField.build(model=FakeContact, name='last_name'), EntityCellRelation(model=FakeContact, rtype=loved), EntityCellRelation(model=FakeContact, rtype=hated), ], ) create_contact = partial(FakeContact.objects.create, user=user) nagate = create_contact(first_name='Nagate', last_name='Tanikaze') shizuka = create_contact(first_name='Shizuka', last_name='Hoshijiro') izana = create_contact(first_name='Izana', last_name='Shinatose') norio = create_contact(first_name='Norio', last_name='Kunato') create_rel = partial(Relation.objects.create, user=user) create_rel(subject_entity=nagate, type=loved, object_entity=izana) create_rel(subject_entity=nagate, type=hated, object_entity=norio) create_rel(subject_entity=shizuka, type=loved, object_entity=norio) # NB: sometimes a query to get this CT is performed when the Relations # are retrieved. So we force the cache to be filled has he should be ContentType.objects.get_for_model(CremeEntity) with self.assertNumQueries(2): hf.populate_entities([nagate, shizuka], user) with self.assertNumQueries(0): r1 = nagate.get_relations(loved.id, real_obj_entities=True) r2 = nagate.get_relations(hated.id, real_obj_entities=True) r3 = shizuka.get_relations(loved.id, real_obj_entities=True) r4 = shizuka.get_relations(hated.id, real_obj_entities=True) with self.assertNumQueries(0): objs1 = [r.object_entity.get_real_entity() for r in r1] objs2 = [r.object_entity.get_real_entity() for r in r2] objs3 = [r.object_entity.get_real_entity() for r in r3] objs4 = [r.object_entity.get_real_entity() for r in r4] self.assertEqual([izana], objs1) self.assertEqual([norio], objs2) self.assertEqual([norio], objs3) self.assertEqual([], objs4)
def test_relationship(self): constraint = GHCCRelation(model=FakeContact) rtype1 = RelationType.create( ('test-subject_likes', 'likes'), ('test-object_likes', 'is liked by'), )[0] self.assertTrue( constraint.check_cell(EntityCellRelation(FakeContact, rtype1))) rtype2 = RelationType.create( ('test-subject_loves', 'is loving', [FakeContact]), ('test-object_loves', 'is loved by', [FakeContact]), )[0] self.assertTrue( constraint.check_cell(EntityCellRelation(FakeContact, rtype2))) rtype3 = RelationType.create( ('test-subject_branch', 'has branch', [FakeOrganisation]), ('test-object_branch', 'is a branch of', [FakeOrganisation]), )[0] self.assertFalse( constraint.check_cell(EntityCellRelation(FakeContact, rtype3))) # --- cell1 = constraint.get_cell(cell_key=f'relation-{rtype2.id}') self.assertIsInstance(cell1, EntityCellRelation) self.assertEqual(rtype2, cell1.relation_type) self.assertIsNone( constraint.get_cell(cell_key=f'relation-{rtype3.id}')) # --- cells = [*constraint.cells()] self.assertGreaterEqual(len(cells), 2) self.assertIsInstance(cells[0], EntityCellRelation) def find_cell(rtype): for cell in cells: if cell.relation_type == rtype: return self.fail(f'{rtype} not found in cells.') find_cell(rtype1) find_cell(rtype2) for cell in cells: if cell.relation_type == rtype3: self.fail(f'{rtype3} should not be found in cells.')
def test_relationtype_registry06(self): "Register a default sub-registry." user1 = self.user user2 = CremeUser( username='******', email='*****@*****.**', first_name='Chie', last_name='Uru', ) class MyRelationField1(lv_form.ListViewSearchField): pass class MyRelationField2(lv_form.ListViewSearchField): pass class MyRelRegistry(lv_search.AbstractListViewSearchFieldRegistry): def get_field(self, *, cell, user, **kwarg): cls = MyRelationField1 if user.username == user1.username else MyRelationField2 return cls(cell=cell, user=user) registry = lv_search.RelationSearchRegistry().register_default( MyRelRegistry) cell = EntityCellRelation.build(model=FakeContact, rtype_id=REL_SUB_HAS) get_field = registry.get_field self.assertIsInstance(get_field(cell=cell, user=user1), MyRelationField1) self.assertIsInstance(get_field(cell=cell, user=user2), MyRelationField2)
def create_hf(hf_pk, name, model, status=True): HeaderFilter.objects.create_if_needed( pk=hf_pk, name=name, model=model, cells_desc=[ (EntityCellRegularField, { 'name': 'name' }), EntityCellRelation(model=model, rtype=rt_sub_bill_received), (EntityCellRegularField, { 'name': 'number' }), (EntityCellRegularField, { 'name': 'status' }) if status else None, (EntityCellRegularField, { 'name': 'total_no_vat' }), (EntityCellRegularField, { 'name': 'issuing_date' }), (EntityCellRegularField, { 'name': 'expiration_date' }), ], )
def _get_cells(self, model): cells = [] for cell_cls, data in self._cells: cell = None if cell_cls is EntityCellRegularField: cell = EntityCellRegularField.build(model=model, name=data) elif cell_cls is EntityCellFunctionField: cell = EntityCellFunctionField.build(model, func_field_name=data) else: # EntityCellRelation rtype = self._get_relationtype(data) if rtype is False: logger.warning( 'SmartColumnsRegistry: relation type "%s" does not exist', data) else: cell = EntityCellRelation(model=model, rtype=rtype) # Has no sense here: # EntityCellActions : not configurable in HeaderFilter form # EntityCellCustomField : dynamically created by user # TODO: other types if cell is not None: cells.append(cell) return cells
def test_cell_registry_relation02(self): "Default data." registry = lv_search.ListViewSearchFieldRegistry() cell = EntityCellRelation.build(model=FakeContact, rtype_id=REL_SUB_HAS) field = registry.get_field(cell=cell, user=self.user) self.assertIsInstance(field, lv_form.RelationField)
def _build_hf_n_contacts(self): user = self.user create_orga = partial(FakeOrganisation.objects.create, user=user) self.organisations = organisations = { name: create_orga(name=name) for name in ('Bebop', 'Swordfish') } rtype_pilots = RelationType.create(('test-subject_pilots', 'pilots'), ('test-object_pilots', 'is piloted by') )[0] create_ptype = CremePropertyType.create ptype_beautiful = create_ptype(str_pk='test-prop_beautiful', text='is beautiful') ptype_girl = create_ptype(str_pk='test-prop_girl', text='is a girl') create_contact = partial(FakeContact.objects.create, user=user) self.contacts = contacts = { first_name: create_contact(first_name=first_name, last_name=last_name) for first_name, last_name in [('Spike', 'Spiegel'), ('Jet', 'Black'), ('Faye', 'Valentine'), ('Edward', 'Wong'), ] } create_rel = partial(Relation.objects.create, user=user, type=rtype_pilots, object_entity=organisations['Bebop'], ) create_rel(subject_entity=contacts['Jet']) create_rel(subject_entity=contacts['Spike']) create_rel(subject_entity=contacts['Spike'], object_entity=organisations['Swordfish']) create_prop = CremeProperty.objects.create create_prop(type=ptype_girl, creme_entity=contacts['Faye']) create_prop(type=ptype_girl, creme_entity=contacts['Edward']) create_prop(type=ptype_beautiful, creme_entity=contacts['Faye']) cells = [ EntityCellRegularField.build(model=FakeContact, name='civility'), EntityCellRegularField.build(model=FakeContact, name='last_name'), EntityCellRegularField.build(model=FakeContact, name='first_name'), EntityCellRelation(model=FakeContact, rtype=rtype_pilots), # TODO: EntityCellCustomField EntityCellFunctionField.build(model=FakeContact, func_field_name='get_pretty_properties'), ] hf = HeaderFilter.create(pk='test-hf_contact', name='Contact view', model=FakeContact, cells_desc=cells, ) # return cells return hf
def test_relationtype_registry03(self): "Set default." class MyRelationField(lv_form.ListViewSearchField): pass registry = lv_search.RelationSearchRegistry(default=MyRelationField) self.assertEqual(MyRelationField, registry.default_builder) cell = EntityCellRelation.build(model=FakeContact, rtype_id=REL_SUB_HAS) self.assertIsInstance(registry.get_field(cell=cell, user=self.user), MyRelationField)
def test_relationtype_registry02(self): "Register in constructor." class MyRelationField(lv_form.ListViewSearchField): pass registry = lv_search.RelationSearchRegistry(to_register=[ (REL_SUB_HAS, MyRelationField), ]) cell = EntityCellRelation.build(model=FakeContact, rtype_id=REL_SUB_HAS) self.assertIsInstance(registry.get_field(cell=cell, user=self.user), MyRelationField)
def get_cells(self, hfilter): cells = super().get_cells(hfilter=hfilter) rtypes = RelationType.objects.filter(pk__in=self.RTYPE_IDS) # NB: add relations items to use the pre-cache system of HeaderFilter # (TODO: problem: retrieve other related events too) cells.extend( EntityCellRelation(model=Contact, rtype=rtype, is_hidden=True) for rtype in rtypes) event = self.get_related_entity() cells.append(gui.EntityCellVolatileInvitation(event=event)) cells.append(gui.EntityCellVolatilePresence(event=event)) return cells
def test_create02(self): "With cells" user = self.login() create_rtype = RelationType.create loves = create_rtype(('test-subject_love', u'Is loving'), ('test-object_love', u'Is loved by'))[0] likes = create_rtype(('test-subject_like', u'Is liking'), ('test-object_like', u'Is liked by'))[0] hf = HeaderFilter.create( pk='tests-hf_contact', name='Contact view', model=FakeContact, is_custom=True, is_private=True, user=user, cells_desc=[ (EntityCellRegularField, { 'name': 'last_name' }), EntityCellRelation(model=FakeContact, rtype=loves), (EntityCellRelation, { 'rtype_id': likes.id }), None, ], ) hf = self.refresh(hf) self.assertEqual(user, hf.user) self.assertTrue(hf.is_private) cells = hf.cells self.assertEqual(3, len(cells)) cell = cells[0] self.assertIsInstance(cell, EntityCellRegularField) self.assertEqual('last_name', cell.value) cell = cells[1] self.assertIsInstance(cell, EntityCellRelation) self.assertEqual(loves.id, cell.value) cell = cells[2] self.assertIsInstance(cell, EntityCellRelation) self.assertEqual(likes.id, cell.value)
def test_mixed_populate_entities04(self): "Mixed types." user = self.create_user() pos = FakePosition.objects.all()[0] create_contact = partial(FakeContact.objects.create, user=user) contacts = [ create_contact(first_name='Nagate', last_name='Tanikaze', position=pos), create_contact(first_name='Shizuka', last_name='Hoshijiro'), create_contact(first_name='Izana', last_name='Shinatose'), ] loved = RelationType.create( ('test-subject_love', 'Is loving'), ('test-object_love', 'Is loved by'), )[1] Relation.objects.create( user=user, subject_entity=contacts[0], type=loved, object_entity=contacts[2], ) build_rfield = partial(EntityCellRegularField.build, model=FakeContact) cells = [ build_rfield(name='last_name'), build_rfield(name='position'), EntityCellRelation(model=FakeContact, rtype=loved), ] # NB: sometimes a query to get this CT is performed when the Relations # are retrieved. So we force the cache to be filled has he should be ContentType.objects.get_for_model(CremeEntity) # Drop caches contacts = [self.refresh(c) for c in contacts] with self.assertNumQueries(3): EntityCell.mixed_populate_entities(cells, contacts, user) with self.assertNumQueries(0): contacts[0].position # NOQA with self.assertNumQueries(0): contacts[0].get_relations(loved.id, real_obj_entities=True)
def test_relation(self): self.assertEqual(_('Relationships'), EntityCellRelation.verbose_name) loves = RelationType.create(('test-subject_love', 'Is loving'), ('test-object_love', 'Is loved by'))[0] cell = EntityCellRelation(model=FakeContact, rtype=loves) self.assertIsInstance(cell, EntityCellRelation) self.assertEqual(FakeContact, cell.model) self.assertEqual(str(loves.id), cell.value) self.assertEqual(loves.predicate, cell.title) self.assertEqual(f'relation-{loves.id}', cell.key) self.assertIs(cell.is_multiline, True) self.assertEqual(loves, cell.relation_type) self.assertEqual(settings.CSS_DEFAULT_LISTVIEW, cell.listview_css_class) self.assertEqual(settings.CSS_DEFAULT_HEADER_LISTVIEW, cell.header_listview_css_class)
def test_build_4_relation(self): loves = RelationType.create(('test-subject_love', 'Is loving'), ('test-object_love', 'Is loved by'))[0] cell = EntityCellRelation(model=FakeContact, rtype=loves) self.assertIsInstance(cell, EntityCellRelation) self.assertEqual(FakeContact, cell.model) self.assertEqual(str(loves.id), cell.value) self.assertEqual(loves.predicate, cell.title) self.assertEqual('relation-{}'.format(loves.id), cell.key) # self.assertIs(cell.has_a_filter, True) # self.assertIs(cell.editable, False) # self.assertIs(cell.sortable, False) self.assertIs(cell.is_multiline, True) # self.assertEqual('', cell.filter_string) self.assertEqual(loves, cell.relation_type) self.assertEqual(settings.CSS_DEFAULT_LISTVIEW, cell.listview_css_class) self.assertEqual(settings.CSS_DEFAULT_HEADER_LISTVIEW, cell.header_listview_css_class)
def test_cell_registry_relation01(self): cell = EntityCellRelation.build(model=FakeContact, rtype_id=REL_SUB_HAS) registry = lv_search.ListViewSearchFieldRegistry(to_register=()) field = registry.get_field(cell=cell, user=self.user) self.assertIsInstance(field, lv_form.ListViewSearchField) class MyField(lv_form.RelationField): pass class Registry: def get_field(this, *, cell, user): return MyField(cell=cell, user=user) registry.register(cell_id=EntityCellRelation.type_id, registry_class=Registry) field = registry.get_field(cell=cell, user=self.user) self.assertIsInstance(field, MyField)
def test_relations(self): rtype1 = self.get_object_or_fail( RelationType, id=fake_constants.FAKE_REL_SUB_EMPLOYED_BY, ) rtype2 = self.get_object_or_fail( RelationType, id=fake_constants.FAKE_REL_OBJ_EMPLOYED_BY, ) rtype3 = self.get_object_or_fail( RelationType, id=fake_constants.FAKE_REL_SUB_BILL_ISSUED, ) field1 = EntityCellsField(model=FakeContact) choices1 = self._find_sub_widget(field1, 'relation').choices self.assertCellInChoices(f'relation-{rtype1.id}', choices=choices1) self.assertCellNotInChoices(f'relation-{rtype2.id}', choices=choices1) self.assertCellNotInChoices(f'relation-{rtype3.id}', choices=choices1) # --- field2 = EntityCellsField() field2.model = FakeContact choices2 = self._find_sub_widget(field2, 'relation').choices self.assertCellInChoices(f'relation-{rtype1.id}', choices=choices2) self.assertCellNotInChoices(f'relation-{rtype2.id}', choices=choices2) self.assertListEqual( [EntityCellRelation(model=FakeContact, rtype=rtype1)], field2.clean(f'relation-{rtype1.id}')) self.assertFieldValidationError( EntityCellRelationsField, 'incompatible', field2.clean, f'relation-{rtype2.id}', message_args={'model': 'Test Contact'}, )
def test_relation(self): "EntityCellRelation are not sortable." sorter = QuerySorter() field_name = 'name' cells = [ EntityCellRegularField.build(model=FakeOrganisation, name=field_name), EntityCellRelation.build(model=FakeOrganisation, rtype_id=REL_SUB_HAS), ] sortinfo = sorter.get( model=FakeInvoice, cells=cells, cell_key=cells[1].key, order=Order(), ) self.assertEqual((field_name, 'cremeentity_ptr_id'), sortinfo.field_names) self.assertEqual(cells[0].key, sortinfo.main_cell_key) self.assertTrue(sortinfo.main_order.asc)
def _create_report(self, name='Report #1', efilter=None, extra_cells=()): cells = [ EntityCellRegularField.build(model=FakeContact, name='last_name'), EntityCellRegularField.build(model=FakeContact, name='user'), EntityCellRelation(model=FakeContact, rtype=RelationType.objects.get(pk=REL_SUB_HAS)), EntityCellFunctionField.build(model=FakeContact, func_field_name='get_pretty_properties'), *extra_cells, ] hf = HeaderFilter.create(pk='test_hf', name='name', model=FakeContact, cells_desc=cells) response = self.client.post(self.ADD_URL, follow=True, data={'user': self.user.pk, 'name': name, 'ct': self.ct_contact.id, 'hf': hf.id, 'filter': efilter.id if efilter else '', }, ) self.assertNoFormError(response) return self.get_object_or_fail(Report, name=name)
def __call__(self, context, request): self.user = request.user cells = context['header_filters'].selected.cells rtypes = RelationType.objects.filter(pk__in=self._RTYPE_IDS) # NB: add relations items to use the pre-cache system of HeaderFilter # (TODO: problem: retrieve other related events too) cells.extend( EntityCellRelation(model=Contact, rtype=rtype, is_hidden=True) for rtype in rtypes) cells.append( EntityCellVolatile(model=Contact, value='invitation_management', title=_('Invitation'), render_func=self.invitation_render)) cells.append( EntityCellVolatile(model=Contact, value='presence_management', title=_('Presence'), render_func=self.presence_render)) # TODO: in the future listview CBV a method that returns the instance of class registry # (None would have the same meaning than context['show_actions']==False) if context['show_actions']: actions_cell = cells[0] view_action_class = next( (c for c in actions_cell.registry.instance_action_classes( model=Contact) if (issubclass(c, ViewAction))), None) actions_cell.registry = action_registry = RelatedContactsActionsRegistry( event=self.event) action_registry.register_instance_actions( AddRelatedOpportunityAction) if view_action_class is not None: action_registry.register_instance_actions(view_action_class)
def populate(self): already_populated = RelationType.objects.filter( pk=constants.REL_SUB_LINKED_2_ACTIVITY, ).exists() Contact = persons.get_contact_model() Organisation = persons.get_organisation_model() Activity = get_activity_model() # --------------------------- create_rtype = RelationType.create create_rtype( (constants.REL_SUB_LINKED_2_ACTIVITY, _('related to the activity')), (constants.REL_OBJ_LINKED_2_ACTIVITY, _('(activity) related to'), [Activity]), minimal_display=(True, False), ) rt_obj_activity_subject = create_rtype( ( constants.REL_SUB_ACTIVITY_SUBJECT, _('is subject of the activity'), [Contact, Organisation], ), ( constants.REL_OBJ_ACTIVITY_SUBJECT, _('(activity) has for subject'), [Activity], ), minimal_display=(True, False), )[1] rt_obj_part_2_activity = create_rtype( (constants.REL_SUB_PART_2_ACTIVITY, _('participates to the activity'), [Contact]), (constants.REL_OBJ_PART_2_ACTIVITY, _('(activity) has as participant'), [Activity]), is_internal=True, minimal_display=(True, False), )[1] # --------------------------- def create_status(pk, name): create_if_needed( Status, {'pk': pk}, name=name, description=name, is_custom=False, ) create_status(constants.STATUS_PLANNED, pgettext('activities-status', 'Planned')), create_status(constants.STATUS_IN_PROGRESS, pgettext('activities-status', 'In progress')), create_status(constants.STATUS_DONE, pgettext('activities-status', 'Done')), create_status(constants.STATUS_DELAYED, pgettext('activities-status', 'Delayed')), create_status(constants.STATUS_CANCELLED, pgettext('activities-status', 'Cancelled')), # --------------------------- act_types_info = { constants.ACTIVITYTYPE_TASK: { 'name': _('Task'), 'day': 0, 'hour': '00:15:00', }, constants.ACTIVITYTYPE_MEETING: { 'name': _('Meeting'), 'day': 0, 'hour': '00:15:00', }, constants.ACTIVITYTYPE_PHONECALL: { 'name': _('Phone call'), 'day': 0, 'hour': '00:15:00', }, constants.ACTIVITYTYPE_GATHERING: { 'name': _('Gathering'), 'day': 0, 'hour': '00:15:00', }, constants.ACTIVITYTYPE_SHOW: { 'name': _('Show'), 'day': 1, 'hour': '00:00:00', }, constants.ACTIVITYTYPE_DEMO: { 'name': _('Demonstration'), 'day': 0, 'hour': '01:00:00', }, constants.ACTIVITYTYPE_INDISPO: { 'name': _('Unavailability'), 'day': 1, 'hour': '00:00:00', }, } act_types = { pk: create_if_needed( ActivityType, {'pk': pk}, name=info['name'], default_day_duration=info['day'], default_hour_duration=info['hour'], is_custom=False, ) for pk, info in act_types_info.items() } def create_subtype(atype, pk, name): create_if_needed( ActivitySubType, {'pk': pk}, name=name, type=atype, is_custom=False, ) meeting_t = act_types[constants.ACTIVITYTYPE_MEETING] for pk, name in [ (constants.ACTIVITYSUBTYPE_MEETING_MEETING, _('Meeting')), (constants.ACTIVITYSUBTYPE_MEETING_QUALIFICATION, _('Qualification')), (constants.ACTIVITYSUBTYPE_MEETING_REVIVAL, _('Revival')), (constants.ACTIVITYSUBTYPE_MEETING_NETWORK, _('Network')), (constants.ACTIVITYSUBTYPE_MEETING_OTHER, pgettext('activities-meeting', 'Other')), ]: create_subtype(meeting_t, pk, name) pcall_t = act_types[constants.ACTIVITYTYPE_PHONECALL] for pk, name in [ (constants.ACTIVITYSUBTYPE_PHONECALL_INCOMING, _('Incoming')), (constants.ACTIVITYSUBTYPE_PHONECALL_OUTGOING, _('Outgoing')), (constants.ACTIVITYSUBTYPE_PHONECALL_CONFERENCE, _('Conference')), (constants.ACTIVITYSUBTYPE_PHONECALL_FAILED, _('Outgoing - Failed')), ]: create_subtype(pcall_t, pk, name) # --------------------------- HeaderFilter.objects.create_if_needed( pk=constants.DEFAULT_HFILTER_ACTIVITY, name=_('Activity view'), model=Activity, cells_desc=[ (EntityCellRegularField, { 'name': 'start' }), (EntityCellRegularField, { 'name': 'title' }), (EntityCellRegularField, { 'name': 'type' }), EntityCellRelation(model=Activity, rtype=rt_obj_part_2_activity), EntityCellRelation(model=Activity, rtype=rt_obj_activity_subject), (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'end' }), ], ) # --------------------------- create_efilter = EntityFilter.objects.smart_update_or_create for pk, name, atype_id in [ (constants.EFILTER_MEETINGS, _('Meetings'), constants.ACTIVITYTYPE_MEETING), (constants.EFILTER_PHONECALLS, _('Phone calls'), constants.ACTIVITYTYPE_PHONECALL), (constants.EFILTER_TASKS, _('Tasks'), constants.ACTIVITYTYPE_TASK), ]: create_efilter( pk, name=name, model=Activity, is_custom=False, user='******', conditions=[ condition_handler.RegularFieldConditionHandler. build_condition( model=Activity, operator=operators.EqualsOperator, field_name='type', values=[atype_id], ), ], ) create_efilter( constants.EFILTER_PARTICIPATE, name=_('In which I participate'), model=Activity, is_custom=False, user='******', conditions=[ condition_handler.RelationSubFilterConditionHandler. build_condition( model=Activity, rtype=rt_obj_part_2_activity, subfilter=EntityFilter.objects.get_latest_version( FILTER_CONTACT_ME), ), ], ) # --------------------------- when_group = { 'name': _('When'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ act_forms.StartSubCell(model=Activity).into_cell(), act_forms.EndSubCell(model=Activity).into_cell(), (EntityCellRegularField, { 'name': 'is_all_day' }), ], } alerts_groups = [ { 'name': _('Generate an alert on a specific date'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ act_forms.DatetimeAlertSubCell(model=Activity).into_cell(), ], }, { 'name': _('Generate an alert in a while'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ act_forms.PeriodAlertSubCell(model=Activity).into_cell(), ], }, ] participants_group = { 'name': _('Participants & subjects'), 'cells': [ act_forms.MyParticipationSubCell(model=Activity).into_cell(), act_forms.ParticipatingUsersSubCell( model=Activity).into_cell(), act_forms.OtherParticipantsSubCell(model=Activity).into_cell(), act_forms.ActivitySubjectsSubCell(model=Activity).into_cell(), act_forms.LinkedEntitiesSubCell(model=Activity).into_cell(), ], } common_groups_desc = [ { 'name': _('Description'), 'cells': [ (EntityCellRegularField, { 'name': 'description' }), ], }, { 'name': _('Custom fields'), 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.REMAINING_CUSTOMFIELDS }, ), ], }, ] relations_n_properties_groups = [ { 'name': _('Properties'), 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.CREME_PROPERTIES }, ), ], }, { 'name': _('Relationships'), 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.RELATIONS }, ), ], }, ] CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.ACTIVITY_CREATION_CFORM, groups_desc=[ { 'name': _('General information'), 'layout': LAYOUT_DUAL_FIRST, 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'title' }), (EntityCellRegularField, { 'name': 'minutes' }), (EntityCellRegularField, { 'name': 'place' }), (EntityCellRegularField, { 'name': 'duration' }), (EntityCellRegularField, { 'name': 'status' }), (EntityCellRegularField, { 'name': 'busy' }), act_forms.ActivitySubTypeSubCell( model=Activity).into_cell(), # act_forms.CommercialApproachSubCell(model=Activity).into_cell(), ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial. REMAINING_REGULARFIELDS }, ), ], }, when_group, *alerts_groups, participants_group, *common_groups_desc, *relations_n_properties_groups, # { # 'name': _('Users to keep informed'), # 'cells': [ # ( # act_forms.UserMessagesSubCell(model=Activity).into_cell(), # ), # ], # }, ], ) CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.ACTIVITY_CREATION_FROM_CALENDAR_CFORM, groups_desc=[ { 'name': _('General information'), 'layout': LAYOUT_DUAL_FIRST, 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'title' }), # (EntityCellRegularField, {'name': 'minutes'}), (EntityCellRegularField, { 'name': 'place' }), (EntityCellRegularField, { 'name': 'duration' }), (EntityCellRegularField, { 'name': 'status' }), (EntityCellRegularField, { 'name': 'busy' }), act_forms.ActivitySubTypeSubCell( model=Activity).into_cell(), # act_forms.CommercialApproachSubCell(model=Activity).into_cell(), # NB: we do not want 'minutes' in the default form # ( # EntityCellCustomFormSpecial, # {'name': EntityCellCustomFormSpecial.REMAINING_REGULARFIELDS}, # ), ], }, when_group, *alerts_groups, participants_group, *common_groups_desc, *relations_n_properties_groups, ], ) CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.UNAVAILABILITY_CREATION_FROM, groups_desc=[ { 'name': _('General information'), 'layout': LAYOUT_DUAL_FIRST, 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'title' }), act_forms.UnavailabilityTypeSubCell( model=Activity).into_cell(), ], }, when_group, { 'name': _('Unavailable users'), 'cells': [ act_forms.ParticipatingUsersSubCell( model=Activity).into_cell(), ], }, *common_groups_desc, *relations_n_properties_groups, ], ) CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.ACTIVITY_EDITION_CFORM, groups_desc=[ { 'name': _('General information'), 'layout': LAYOUT_DUAL_FIRST, 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'title' }), (EntityCellRegularField, { 'name': 'minutes' }), (EntityCellRegularField, { 'name': 'place' }), (EntityCellRegularField, { 'name': 'duration' }), (EntityCellRegularField, { 'name': 'status' }), (EntityCellRegularField, { 'name': 'busy' }), act_forms.ActivitySubTypeSubCell( model=Activity).into_cell(), ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial. REMAINING_REGULARFIELDS }, ), ], }, when_group, *common_groups_desc, ], ) # --------------------------- SearchConfigItem.objects.create_if_needed( Activity, ['title', 'description', 'type__name'], ) # --------------------------- create_svalue = SettingValue.objects.get_or_create create_svalue(key_id=setting_keys.review_key.id, defaults={'value': True}) create_svalue(key_id=setting_keys.auto_subjects_key.id, defaults={'value': True}) # create_svalue(key_id=setting_keys.form_user_messages_key.id, defaults={'value': False}) # --------------------------- # TODO: move to "not already_populated" section in creme2.4 if not MenuConfigItem.objects.filter( entry_id__startswith='activities-').exists(): create_mitem = MenuConfigItem.objects.create container = create_mitem( entry_id=ContainerEntry.id, entry_data={'label': _('Activities')}, order=10, ) create_mitem(entry_id=menu.CalendarEntry.id, order=10, parent=container) create_mitem(entry_id=menu.ActivitiesEntry.id, order=20, parent=container) create_mitem(entry_id=menu.PhoneCallsEntry.id, order=30, parent=container) create_mitem(entry_id=menu.MeetingsEntry.id, order=40, parent=container) # --------------------------- if not already_populated: LEFT = BrickDetailviewLocation.LEFT RIGHT = BrickDetailviewLocation.RIGHT BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Activity, 'zone': LEFT }, data=[ { 'order': 5 }, { 'brick': core_bricks.CustomFieldsBrick, 'order': 40 }, { 'brick': bricks.RelatedCalendarBrick, 'order': 90 }, { 'brick': bricks.ParticipantsBrick, 'order': 100 }, { 'brick': bricks.SubjectsBrick, 'order': 120 }, { '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 BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Activity, '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 block on detail views') from creme.documents.bricks import LinkedDocsBrick BrickDetailviewLocation.objects.create_if_needed( brick=LinkedDocsBrick, order=600, zone=RIGHT, model=Activity, ) future_id = bricks.FutureActivitiesBrick.id_ past_id = bricks.PastActivitiesBrick.id_ BrickDetailviewLocation.objects.multi_create( defaults={'zone': RIGHT}, data=[ { 'brick': future_id, 'order': 20, 'model': Contact }, { 'brick': past_id, 'order': 21, 'model': Contact }, { 'brick': future_id, 'order': 20, 'model': Organisation }, { 'brick': past_id, 'order': 21, 'model': Organisation }, ], ) BrickHomeLocation.objects.create(brick_id=future_id, order=20) BrickHomeLocation.objects.create(brick_id=past_id, order=21) # --------------------------- create_button = ButtonMenuItem.objects.create_if_needed create_button(button=buttons.AddRelatedActivityButton, order=10) create_button(button=buttons.AddMeetingButton, order=11) create_button(button=buttons.AddPhoneCallButton, order=12)
def populate(self): already_populated = RelationType.objects.filter( pk=constants.REL_SUB_TARGETS).exists() Contact = persons.get_contact_model() Organisation = persons.get_organisation_model() Product = products.get_product_model() Service = products.get_service_model() # --------------------------- create_rtype = RelationType.create rt_sub_targets = create_rtype( ( constants.REL_SUB_TARGETS, _('targets the organisation/contact'), [Opportunity], ), ( constants.REL_OBJ_TARGETS, _('targeted by the opportunity'), [Organisation, Contact], ), is_internal=True, minimal_display=(True, True), )[0] rt_obj_emit_orga = create_rtype( ( constants.REL_SUB_EMIT_ORGA, _('has generated the opportunity'), [Organisation], ), ( constants.REL_OBJ_EMIT_ORGA, _('has been generated by'), [Opportunity], ), is_internal=True, minimal_display=(True, True), )[1] create_rtype((constants.REL_SUB_LINKED_PRODUCT, _('is linked to the opportunity'), [Product]), (constants.REL_OBJ_LINKED_PRODUCT, _('concerns the product'), [Opportunity])) create_rtype( (constants.REL_SUB_LINKED_SERVICE, _('is linked to the opportunity'), [Service]), (constants.REL_OBJ_LINKED_SERVICE, _('concerns the service'), [Opportunity]), ) create_rtype( (constants.REL_SUB_LINKED_CONTACT, _('involves in the opportunity'), [Contact]), (constants.REL_OBJ_LINKED_CONTACT, _('stages'), [Opportunity])), create_rtype( (constants.REL_SUB_RESPONSIBLE, _('is responsible for'), [Contact ]), (constants.REL_OBJ_RESPONSIBLE, _('has as responsible contact'), [Opportunity]), ) if apps.is_installed('creme.activities'): logger.info('Activities app is installed' ' => an Opportunity can be the subject of an Activity') from creme.activities.constants import REL_SUB_ACTIVITY_SUBJECT RelationType.objects.get( pk=REL_SUB_ACTIVITY_SUBJECT, ).add_subject_ctypes(Opportunity) if apps.is_installed('creme.billing'): logger.info( 'Billing app is installed' ' => we create relationships between Opportunities & billing models' ) from creme import billing Invoice = billing.get_invoice_model() Quote = billing.get_quote_model() SalesOrder = billing.get_sales_order_model() create_rtype( ( constants.REL_SUB_LINKED_SALESORDER, _('is associate with the opportunity'), [SalesOrder], ), (constants.REL_OBJ_LINKED_SALESORDER, _('has generated the salesorder'), [Opportunity]), ) create_rtype( ( constants.REL_SUB_LINKED_INVOICE, pgettext('opportunities-invoice', 'generated for the opportunity'), [Invoice], ), ( constants.REL_OBJ_LINKED_INVOICE, _('has resulted in the invoice'), [Opportunity], ), ) create_rtype( ( constants.REL_SUB_LINKED_QUOTE, pgettext('opportunities-quote', 'generated for the opportunity'), [Quote], ), ( constants.REL_OBJ_LINKED_QUOTE, _('has resulted in the quote'), [Opportunity], ), ) create_rtype( ( constants.REL_SUB_CURRENT_DOC, _('is the current accounting document of'), [SalesOrder, Invoice, Quote], ), ( constants.REL_OBJ_CURRENT_DOC, _('has as current accounting document'), [Opportunity], ), ) # --------------------------- create_sv = SettingValue.objects.get_or_create create_sv(key_id=setting_keys.quote_key.id, defaults={'value': False}) create_sv(key_id=setting_keys.target_constraint_key.id, defaults={'value': True}) create_sv(key_id=setting_keys.emitter_constraint_key.id, defaults={'value': True}) # --------------------------- create_efilter = partial( EntityFilter.objects.smart_update_or_create, model=Opportunity, user='******', ) build_cond = partial( condition_handler.RegularFieldConditionHandler.build_condition, model=Opportunity, ) create_efilter( 'opportunities-opportunities_won', name=_('Opportunities won'), conditions=[ build_cond( operator=operators.EqualsOperator, field_name='sales_phase__won', values=[True], ), ], ) create_efilter( 'opportunities-opportunities_lost', name=_('Opportunities lost'), conditions=[ build_cond( operator=operators.EqualsOperator, field_name='sales_phase__lost', values=[True], ), ], ) create_efilter( 'opportunities-neither_won_nor_lost_opportunities', name=_('Neither won nor lost opportunities'), conditions=[ build_cond( operator=operators.EqualsNotOperator, field_name='sales_phase__won', values=[True], ), build_cond( operator=operators.EqualsNotOperator, field_name='sales_phase__lost', values=[True], ), ], ) # --------------------------- HeaderFilter.objects.create_if_needed( pk=constants.DEFAULT_HFILTER_OPPORTUNITY, model=Opportunity, name=_('Opportunity view'), cells_desc=[ (EntityCellRegularField, { 'name': 'name' }), EntityCellRelation(model=Opportunity, rtype=rt_sub_targets), (EntityCellRegularField, { 'name': 'sales_phase' }), (EntityCellRegularField, { 'name': 'estimated_sales' }), (EntityCellRegularField, { 'name': 'made_sales' }), (EntityCellRegularField, { 'name': 'closing_date' }), ], ) # --------------------------- common_groups_desc = [ { 'name': _('Description'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ (EntityCellRegularField, { 'name': 'description' }), ], }, { 'name': _('Custom fields'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.REMAINING_CUSTOMFIELDS }, ), ], }, ] common_field_names = [ 'reference', 'estimated_sales', 'made_sales', 'currency', 'sales_phase', 'chance_to_win', 'expected_closing_date', 'closing_date', 'origin', 'first_action_date', ] CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.OPPORTUNITY_CREATION_CFORM, groups_desc=[ { 'name': _('General information'), 'layout': LAYOUT_DUAL_FIRST, 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'name' }), OppEmitterSubCell().into_cell(), OppTargetSubCell().into_cell(), *((EntityCellRegularField, { 'name': fname }) for fname in common_field_names), ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial. REMAINING_REGULARFIELDS }, ), ], }, *common_groups_desc, { 'name': _('Properties'), 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.CREME_PROPERTIES }, ), ], }, { 'name': _('Relationships'), 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.RELATIONS }, ), ], }, ], ) CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.OPPORTUNITY_EDITION_CFORM, groups_desc=[ { 'name': _('General information'), 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'name' }), OppTargetSubCell().into_cell(), *((EntityCellRegularField, { 'name': fname }) for fname in common_field_names), ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial. REMAINING_REGULARFIELDS }, ), ], }, *common_groups_desc, ], ) # --------------------------- SearchConfigItem.objects.create_if_needed( Opportunity, ['name', 'made_sales', 'sales_phase__name', 'origin__name'], ) # --------------------------- # TODO: move to "not already_populated" section in creme2.4 if not MenuConfigItem.objects.filter( entry_id__startswith='opportunities-').exists(): container = MenuConfigItem.objects.get_or_create( entry_id=ContainerEntry.id, entry_data={'label': _('Commercial')}, defaults={'order': 30}, )[0] MenuConfigItem.objects.create( entry_id=menu.OpportunitiesEntry.id, order=10, parent=container, ) creations = MenuConfigItem.objects.filter( entry_id=ContainerEntry.id, entry_data={ 'label': _('+ Creation') }, ).first() if creations is not None: MenuConfigItem.objects.create( entry_id=menu.OpportunityCreationEntry.id, order=30, parent=creations, ) # --------------------------- if not already_populated: create_sphase = SalesPhase.objects.create create_sphase(order=1, name=_('Forthcoming')) create_sphase(order=4, name=pgettext('opportunities-sales_phase', 'Abandoned')) create_sphase(order=5, name=pgettext('opportunities-sales_phase', 'Won'), won=True) create_sphase(order=6, name=pgettext('opportunities-sales_phase', 'Lost'), lost=True) create_sphase(order=3, name=_('Under negotiation')) create_sphase(order=2, name=_('In progress')) # --------------------------- create_origin = Origin.objects.create create_origin(name=pgettext('opportunities-origin', 'None')) create_origin(name=_('Web site')) create_origin(name=_('Mouth')) create_origin(name=_('Show')) create_origin(name=_('Direct email')) create_origin(name=_('Direct phone call')) create_origin(name=_('Employee')) create_origin(name=_('Partner')) create_origin(name=pgettext('opportunities-origin', 'Other')) # --------------------------- create_button = ButtonMenuItem.objects.create_if_needed create_button( model=Organisation, button=LinkedOpportunityButton, order=30, ) create_button( model=Contact, button=LinkedOpportunityButton, order=30, ) # --------------------------- LEFT = BrickDetailviewLocation.LEFT RIGHT = BrickDetailviewLocation.RIGHT build_cell = EntityCellRegularField.build cbci = CustomBrickConfigItem.objects.create( id='opportunities-complementary', name=_('Opportunity complementary information'), content_type=Opportunity, cells=[ build_cell(Opportunity, 'reference'), build_cell(Opportunity, 'currency'), build_cell(Opportunity, 'chance_to_win'), build_cell(Opportunity, 'expected_closing_date'), build_cell(Opportunity, 'closing_date'), build_cell(Opportunity, 'origin'), build_cell(Opportunity, 'first_action_date'), build_cell(Opportunity, 'description'), ], ) BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Opportunity, 'zone': LEFT }, data=[ { 'brick': bricks.OpportunityCardHatBrick, 'order': 1, 'zone': BrickDetailviewLocation.HAT, }, { 'brick': cbci.brick_id, 'order': 5 }, { 'brick': core_bricks.CustomFieldsBrick, 'order': 40 }, { 'brick': bricks.BusinessManagersBrick, 'order': 60 }, { 'brick': bricks.LinkedContactsBrick, 'order': 62 }, { 'brick': bricks.LinkedProductsBrick, 'order': 64 }, { 'brick': bricks.LinkedServicesBrick, 'order': 66 }, { 'brick': core_bricks.PropertiesBrick, 'order': 450 }, { 'brick': core_bricks.RelationsBrick, 'order': 500 }, { 'brick': bricks.OppTargetBrick, 'order': 1, 'zone': RIGHT }, { 'brick': bricks.OppTotalBrick, 'order': 2, 'zone': RIGHT }, { 'brick': core_bricks.HistoryBrick, 'order': 20, 'zone': RIGHT }, ], ) if apps.is_installed('creme.activities'): logger.info( 'Activities app is installed' ' => we use the "Future activities" & "Past activities" blocks' ) from creme.activities import bricks as act_bricks BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Opportunity, 'zone': RIGHT }, data=[ { 'brick': act_bricks.FutureActivitiesBrick, 'order': 20 }, { 'brick': act_bricks.PastActivitiesBrick, 'order': 21 }, ], ) if apps.is_installed('creme.assistants'): logger.info( 'Assistants app is installed' ' => we use the assistants blocks on detail views and portal' ) from creme.assistants import bricks as a_bricks BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Opportunity, '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': 500 }, ], ) if apps.is_installed('creme.documents'): # logger.info('Documents app is installed # => we use the documents block on detail view') from creme.documents.bricks import LinkedDocsBrick BrickDetailviewLocation.objects.create_if_needed( brick=LinkedDocsBrick, order=600, zone=RIGHT, model=Opportunity, ) if apps.is_installed('creme.billing'): logger.info('Billing app is installed' ' => we use the billing blocks on detail view') BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Opportunity, 'zone': LEFT }, data=[ { 'brick': bricks.QuotesBrick, 'order': 70 }, { 'brick': bricks.SalesOrdersBrick, 'order': 72 }, { 'brick': bricks.InvoicesBrick, 'order': 74 }, ], ) if apps.is_installed('creme.emails'): logger.info('Emails app is installed' ' => we use the emails blocks on detail view') from creme.emails.bricks import MailsHistoryBrick BrickDetailviewLocation.objects.create_if_needed( brick=MailsHistoryBrick, order=600, zone=RIGHT, model=Opportunity, ) BrickDetailviewLocation.objects.create_if_needed( brick=bricks.TargettingOpportunitiesBrick, order=16, zone=RIGHT, model=Organisation, ) # --------------------------- if apps.is_installed('creme.reports'): logger.info( 'Reports app is installed' ' => we create an Opportunity report, with 2 graphs, and related blocks' ) self.create_report_n_graphes(rt_obj_emit_orga)
def cells(self, not_hiddable_cell_keys=()): model = self.model for rtype in RelationType.objects.compatible(model, include_internals=True): yield EntityCellRelation(model=model, rtype=rtype)
def populate(self): already_populated = RelationType.objects.filter( pk=constants.REL_SUB_LINKED_2_ACTIVITY).exists() Contact = persons.get_contact_model() Organisation = persons.get_organisation_model() Activity = get_activity_model() # --------------------------- create_rtype = RelationType.create create_rtype( (constants.REL_SUB_LINKED_2_ACTIVITY, _('related to the activity')), (constants.REL_OBJ_LINKED_2_ACTIVITY, _('(activity) related to'), [Activity]), minimal_display=(True, False), ) rt_obj_activity_subject = create_rtype( (constants.REL_SUB_ACTIVITY_SUBJECT, _('is subject of the activity'), [Contact, Organisation]), (constants.REL_OBJ_ACTIVITY_SUBJECT, _('(activity) has for subject'), [Activity]), minimal_display=(True, False), )[1] rt_obj_part_2_activity = create_rtype( (constants.REL_SUB_PART_2_ACTIVITY, _('participates to the activity'), [Contact]), (constants.REL_OBJ_PART_2_ACTIVITY, _('(activity) has as participant'), [Activity]), is_internal=True, minimal_display=(True, False), )[1] # --------------------------- create_if_needed(Status, {'pk': constants.STATUS_PLANNED}, name=pgettext('activities-status', 'Planned'), description=pgettext('activities-status', 'Planned'), is_custom=False) create_if_needed(Status, {'pk': constants.STATUS_IN_PROGRESS}, name=pgettext('activities-status', 'In progress'), description=pgettext('activities-status', 'In progress'), is_custom=False) create_if_needed(Status, {'pk': constants.STATUS_DONE}, name=pgettext('activities-status', 'Done'), description=pgettext('activities-status', 'Done'), is_custom=False) create_if_needed(Status, {'pk': constants.STATUS_DELAYED}, name=pgettext('activities-status', 'Delayed'), description=pgettext('activities-status', 'Delayed'), is_custom=False) create_if_needed(Status, {'pk': constants.STATUS_CANCELLED}, name=pgettext('activities-status', 'Cancelled'), description=pgettext('activities-status', 'Cancelled'), is_custom=False) # --------------------------- create_if_needed(ActivityType, {'pk': constants.ACTIVITYTYPE_TASK}, name=_('Task'), default_day_duration=0, default_hour_duration="00:15:00", is_custom=False) meeting_type = \ create_if_needed(ActivityType, {'pk': constants.ACTIVITYTYPE_MEETING}, name=_('Meeting'), default_day_duration=0, default_hour_duration="00:15:00", is_custom=False) phone_call_type = \ create_if_needed(ActivityType, {'pk': constants.ACTIVITYTYPE_PHONECALL}, name=_('Phone call'), default_day_duration=0, default_hour_duration="00:15:00", is_custom=False) create_if_needed(ActivityType, {'pk': constants.ACTIVITYTYPE_GATHERING}, name=_('Gathering'), default_day_duration=0, default_hour_duration="00:15:00", is_custom=False) create_if_needed(ActivityType, {'pk': constants.ACTIVITYTYPE_SHOW}, name=_('Show'), default_day_duration=1, default_hour_duration="00:00:00", is_custom=False) create_if_needed(ActivityType, {'pk': constants.ACTIVITYTYPE_DEMO}, name=_('Demonstration'), default_day_duration=0, default_hour_duration="01:00:00", is_custom=False) create_if_needed(ActivityType, {'pk': constants.ACTIVITYTYPE_INDISPO}, name=_('Unavailability'), default_day_duration=1, default_hour_duration="00:00:00", is_custom=False) create_if_needed(ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_MEETING_MEETING}, name=_('Meeting'), type=meeting_type, is_custom=False) create_if_needed( ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_MEETING_QUALIFICATION}, name=_('Qualification'), type=meeting_type, is_custom=False) create_if_needed(ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_MEETING_REVIVAL}, name=_('Revival'), type=meeting_type, is_custom=False) create_if_needed(ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_MEETING_NETWORK}, name=_('Network'), type=meeting_type, is_custom=False) create_if_needed(ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_MEETING_OTHER}, name=pgettext('activities-meeting', 'Other'), type=meeting_type, is_custom=False) create_if_needed(ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_PHONECALL_INCOMING}, name=_('Incoming'), type=phone_call_type, is_custom=False) create_if_needed(ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_PHONECALL_OUTGOING}, name=_('Outgoing'), type=phone_call_type, is_custom=False) create_if_needed( ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_PHONECALL_CONFERENCE}, name=_('Conference'), type=phone_call_type, is_custom=False) create_if_needed(ActivitySubType, {'pk': constants.ACTIVITYSUBTYPE_PHONECALL_FAILED}, name=_('Outgoing - Failed'), type=phone_call_type, is_custom=False) # --------------------------- HeaderFilter.create( pk=constants.DEFAULT_HFILTER_ACTIVITY, name=_('Activity view'), model=Activity, cells_desc=[ (EntityCellRegularField, { 'name': 'start' }), (EntityCellRegularField, { 'name': 'title' }), (EntityCellRegularField, { 'name': 'type' }), EntityCellRelation(model=Activity, rtype=rt_obj_part_2_activity), EntityCellRelation(model=Activity, rtype=rt_obj_activity_subject), (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'end' }), ], ) # --------------------------- create_efilter = EntityFilter.create for pk, name, atype_id in ( (constants.EFILTER_MEETINGS, _('Meetings'), constants.ACTIVITYTYPE_MEETING), (constants.EFILTER_PHONECALLS, _('Phone calls'), constants.ACTIVITYTYPE_PHONECALL), (constants.EFILTER_TASKS, _('Tasks'), constants.ACTIVITYTYPE_TASK), ): create_efilter( pk, name=name, model=Activity, is_custom=False, user='******', conditions=[ # EntityFilterCondition.build_4_field( # model=Activity, # operator=EntityFilterCondition.EQUALS, # name='type', # values=[atype_id], # ), condition_handler.RegularFieldConditionHandler. build_condition( model=Activity, operator=operators.EqualsOperator, field_name='type', values=[atype_id], ), ], ) create_efilter( constants.EFILTER_PARTICIPATE, name=_('In which I participate'), model=Activity, is_custom=False, user='******', conditions=[ # EntityFilterCondition.build_4_relation_subfilter( # rtype=rt_obj_part_2_activity, # subfilter=EntityFilter.get_latest_version(FILTER_CONTACT_ME) # ), condition_handler.RelationSubFilterConditionHandler. build_condition( model=Activity, rtype=rt_obj_part_2_activity, subfilter=EntityFilter.get_latest_version( FILTER_CONTACT_ME), ), ], ) # --------------------------- SearchConfigItem.create_if_needed( Activity, ['title', 'description', 'type__name']) # --------------------------- # for user in get_user_model().objects.all(): # Calendar.objects.get_default_calendar(user) # TODO: remove this code in Creme 2.2 (it avoids install of creme which # are upgraded to 2.1 to force using the command "activities_create_default_calendars") cal_is_public = settings.ACTIVITIES_DEFAULT_CALENDAR_IS_PUBLIC if cal_is_public is not None: if isinstance(cal_is_public, bool): users = get_user_model().objects.filter( is_staff=False, is_active=True, calendar__is_default__isnull=True, ) for user in users: Calendar.objects.create_default_calendar( user=user, is_public=cal_is_public) else: logger.error( 'ACTIVITIES_DEFAULT_CALENDAR_IS_PUBLIC is invalid ' '(not in {None, True, False}) ') # --------------------------- create_svalue = SettingValue.objects.get_or_create create_svalue(key_id=setting_keys.review_key.id, defaults={'value': True}) create_svalue(key_id=setting_keys.auto_subjects_key.id, defaults={'value': True}) create_svalue(key_id=setting_keys.form_user_messages_key.id, defaults={'value': False}) # --------------------------- if not already_populated: LEFT = BrickDetailviewLocation.LEFT RIGHT = BrickDetailviewLocation.RIGHT BrickDetailviewLocation.objects.create_for_model_brick( order=5, zone=LEFT, model=Activity) create_bdl = BrickDetailviewLocation.objects.create_if_needed create_bdl(brick=core_bricks.CustomFieldsBrick, order=40, zone=LEFT, model=Activity) create_bdl(brick=bricks.RelatedCalendarBrick, order=90, zone=LEFT, model=Activity) create_bdl(brick=bricks.ParticipantsBrick, order=100, zone=LEFT, model=Activity) create_bdl(brick=bricks.SubjectsBrick, order=120, zone=LEFT, model=Activity) create_bdl(brick=core_bricks.PropertiesBrick, order=450, zone=LEFT, model=Activity) create_bdl(brick=core_bricks.RelationsBrick, order=500, zone=LEFT, model=Activity) create_bdl(brick=core_bricks.HistoryBrick, order=20, zone=RIGHT, model=Activity) 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 create_bdl(brick=a_bricks.TodosBrick, order=100, zone=RIGHT, model=Activity) create_bdl(brick=a_bricks.MemosBrick, order=200, zone=RIGHT, model=Activity) create_bdl(brick=a_bricks.AlertsBrick, order=300, zone=RIGHT, model=Activity) create_bdl(brick=a_bricks.UserMessagesBrick, order=400, zone=RIGHT, model=Activity) if apps.is_installed('creme.documents'): # logger.info('Documents app is installed => we use the documents block on detail views') from creme.documents.bricks import LinkedDocsBrick create_bdl(brick=LinkedDocsBrick, order=600, zone=RIGHT, model=Activity) future_id = bricks.FutureActivitiesBrick.id_ past_id = bricks.PastActivitiesBrick.id_ create_bdl(brick=future_id, order=20, zone=RIGHT, model=Contact) create_bdl(brick=past_id, order=21, zone=RIGHT, model=Contact) create_bdl(brick=future_id, order=20, zone=RIGHT, model=Organisation) create_bdl(brick=past_id, order=21, zone=RIGHT, model=Organisation) BrickHomeLocation.objects.create(brick_id=future_id, order=20) BrickHomeLocation.objects.create(brick_id=past_id, order=21) # --------------------------- create_button = ButtonMenuItem.create_if_needed create_button('activities-add_activity_button', model=None, button=buttons.AddRelatedActivityButton, order=10) create_button('activities-add_meeting_button', model=None, button=buttons.AddMeetingButton, order=11) create_button('activities-add_phonecall_button', model=None, button=buttons.AddPhoneCallButton, order=12)
def test_create02(self): user = self.login() lv_url = FakeContact.get_lv_absolute_url() # Create a view to post the entity filter HeaderFilter.create( pk='creme_core-tests_views_header_filter_test_create02', name='A FakeContact view', # Starts with "A" => first model=FakeContact, cells_desc=[ (EntityCellRegularField, { 'name': 'last_name' }), (EntityCellRegularField, { 'name': 'first_name' }), (EntityCellRegularField, { 'name': 'email' }), ], ) # Set a filter in the session (should be kept) efilter = EntityFilter.create( 'creme_core-tests_views_header_filter_test_create02', name='Misato', model=FakeContact, is_custom=True, conditions=[ # EntityFilterCondition.build_4_field( # model=FakeContact, # operator=EntityFilterCondition.EQUALS, # name='first_name', values=['Misato'], # ), RegularFieldConditionHandler.build_condition( model=FakeContact, field_name='first_name', operator=EQUALS, values=['Misato'], ), ], ) response = self.assertPOST200(lv_url, data={'filter': efilter.id}) self.assertEqual(efilter.id, response.context['list_view_state'].entity_filter_id) # -- ct = self.contact_ct loves = RelationType.create(('test-subject_love', 'Is loving'), ('test-object_love', 'Is loved by'))[0] customfield = CustomField.objects.create( name='Size (cm)', field_type=CustomField.INT, content_type=ct, ) # funcfield = FakeContact.function_fields.get('get_pretty_properties') funcfield = function_field_registry.get(FakeContact, 'get_pretty_properties') url = self._build_add_url(ct) response = self.assertGET200(url) with self.assertNoException(): cells_f = response.context['form'].fields['cells'] build_4_field = partial(EntityCellRegularField.build, model=FakeContact) self.assertCellsEqual([ build_4_field(name='first_name'), build_4_field(name='last_name'), EntityCellRelation( model=FakeContact, rtype=RelationType.objects.get(pk=FAKE_REL_SUB_EMPLOYED_BY), ), ], cells_f.initial) field_name = 'first_name' name = 'DefaultHeaderFilter' response = self.client.post(url, follow=True, data={ 'name': name, 'user': user.id, 'is_private': 'on', 'cells': 'relation-{rtype},' 'regular_field-{rfield},' 'function_field-{ffield},' 'custom_field-{cfield}'.format( rfield=field_name, cfield=customfield.id, rtype=loves.id, ffield=funcfield.name, ) }) self.assertNoFormError(response) hfilter = self.get_object_or_fail(HeaderFilter, name=name) self.assertEqual(user, hfilter.user) self.assertTrue(hfilter.is_private) cells = hfilter.cells self.assertEqual(4, len(cells)) cell = cells[0] self.assertIsInstance(cell, EntityCellRelation) self.assertEqual(loves.id, cell.value) cell = cells[1] self.assertIsInstance(cell, EntityCellRegularField) self.assertEqual(field_name, cell.value) cell = cells[2] self.assertIsInstance(cell, EntityCellFunctionField) self.assertEqual(funcfield.name, cell.value) cell = cells[3] self.assertIsInstance(cell, EntityCellCustomField) self.assertEqual(str(customfield.id), cell.value) self.assertRedirects(response, lv_url) # -- context = self.assertGET200(lv_url).context selected_hfilter = context['header_filters'].selected self.assertIsInstance(selected_hfilter, HeaderFilter) self.assertEqual(hfilter.id, selected_hfilter.id) lvs = context['list_view_state'] self.assertEqual(hfilter.id, lvs.header_filter_id) self.assertEqual(efilter.id, lvs.entity_filter_id)
def populate(self): already_populated = core_models.RelationType.objects.filter( pk=constants.REL_SUB_EMPLOYED_BY).exists() Contact = persons.get_contact_model() Organisation = persons.get_organisation_model() rt_map = {} for rt_info in [ ( (constants.REL_SUB_EMPLOYED_BY, _('is an employee of'), [Contact]), (constants.REL_OBJ_EMPLOYED_BY, _('employs'), [Organisation]), ), ( (constants.REL_SUB_CUSTOMER_SUPPLIER, _('is a customer of'), [Contact, Organisation]), (constants.REL_OBJ_CUSTOMER_SUPPLIER, _('is a supplier of'), [Contact, Organisation]), ), ( (constants.REL_SUB_MANAGES, _('manages'), [Contact]), (constants.REL_OBJ_MANAGES, _('managed by'), [Organisation]), ), ( (constants.REL_SUB_PROSPECT, _('is a prospect of'), [Contact, Organisation]), (constants.REL_OBJ_PROSPECT, _('has as prospect'), [Contact, Organisation]), ), ( (constants.REL_SUB_SUSPECT, _('is a suspect of'), [Contact, Organisation]), (constants.REL_OBJ_SUSPECT, _('has as suspect'), [Contact, Organisation]), ), ( (constants.REL_SUB_PARTNER, _('is a partner of'), [Contact, Organisation]), (constants.REL_OBJ_PARTNER, _('has as partner'), [Contact, Organisation]), ), ( (constants.REL_SUB_INACTIVE, _('is an inactive customer of'), [Contact, Organisation]), (constants.REL_OBJ_INACTIVE, _('has as inactive customer'), [Contact, Organisation]), ), ( (constants.REL_SUB_SUBSIDIARY, _('has as subsidiary'), [Organisation]), (constants.REL_OBJ_SUBSIDIARY, _('is a subsidiary of'), [Organisation]), ), ( (constants.REL_SUB_COMPETITOR, _('is a competitor of'), [Contact, Organisation]), (constants.REL_OBJ_COMPETITOR, _('has as competitor'), [Contact, Organisation]), ), ]: rt, sym_rt = core_models.RelationType.create(*rt_info) rt_map[rt.id] = rt rt_map[sym_rt.id] = sym_rt # --------------------------- EntityFilter.create( constants.FILTER_MANAGED_ORGA, name=_('Managed by creme'), model=Organisation, user='******', conditions=[ # EntityFilterCondition.build_4_field( # model=Organisation, # operator=EntityFilterCondition.EQUALS, # name='is_managed', # values=[True], # ), condition_handler.RegularFieldConditionHandler.build_condition( model=Organisation, operator=operators.EqualsOperator, field_name='is_managed', values=[True], ), ], ) EntityFilter.create( constants.FILTER_CONTACT_ME, name=_('Me'), model=Contact, user='******', conditions=[ # EntityFilterCondition.build_4_field( # model=Contact, # operator=EntityFilterCondition.EQUALS, # name='is_user', # values=[EntityFilterVariable.CURRENT_USER], # ), condition_handler.RegularFieldConditionHandler.build_condition( model=Contact, operator=operators.EqualsOperator, field_name='is_user', values=[operands.CurrentUserOperand.type_id], ), ], ) # --------------------------- create_hf = core_models.HeaderFilter.create create_hf( pk=constants.DEFAULT_HFILTER_CONTACT, model=Contact, name=_('Contact view'), cells_desc=[ (EntityCellRegularField, { 'name': 'last_name' }), (EntityCellRegularField, { 'name': 'first_name' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'email' }), (EntityCellRegularField, { 'name': 'user' }), EntityCellRelation( model=Contact, rtype=rt_map[constants.REL_SUB_EMPLOYED_BY]), ], ) create_hf( pk=constants.DEFAULT_HFILTER_ORGA, model=Organisation, name=_('Organisation view'), cells_desc=[ (EntityCellRegularField, { 'name': 'name' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'user' }), EntityCellRelation(model=Organisation, rtype=rt_map[constants.REL_OBJ_MANAGES]), ], ) create_hf( pk=constants.DEFAULT_HFILTER_ORGA_CUSTOMERS, model=Organisation, name=_('Prospect/Suspect view'), cells_desc=[ (EntityCellRegularField, { 'name': 'name' }), (EntityCellRegularField, { 'name': 'sector' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'email' }), (EntityCellRegularField, { 'name': 'user' }), EntityCellRelation( model=Organisation, rtype=rt_map[constants.REL_SUB_CUSTOMER_SUPPLIER]), EntityCellRelation(model=Organisation, rtype=rt_map[constants.REL_SUB_PROSPECT]), EntityCellRelation(model=Organisation, rtype=rt_map[constants.REL_SUB_SUSPECT]), ], ) # --------------------------- create_sci = core_models.SearchConfigItem.create_if_needed create_sci(Contact, ['last_name', 'first_name', 'phone', 'mobile', 'email']) create_sci( Organisation, ['name', 'phone', 'email', 'sector__title', 'legal_form__title']) # --------------------------- if not already_populated: create_if_needed(Civility, {'pk': 1}, title=_('Madam'), shortcut=_('Mrs.')) create_if_needed(Civility, {'pk': 2}, title=_('Miss'), shortcut=_('Ms.')) create_if_needed(Civility, {'pk': 3}, title=_('Mister'), shortcut=_('Mr.')) create_if_needed(Civility, {'pk': 4}, title=_('N/A'), shortcut='') # --------------------------- # TODO: add relation to admin ???? if not Organisation.objects.exists(): Organisation.objects.create( user=get_user_model().objects.get_admin(), name=_('ReplaceByYourSociety'), is_managed=True, uuid=constants.UUID_FIRST_ORGA, ) # --------------------------- create_if_needed(Position, {'pk': 1}, title=_('CEO')) create_if_needed(Position, {'pk': 2}, title=_('Secretary')) create_if_needed(Position, {'pk': 3}, title=_('Technician')) # --------------------------- create_if_needed(Sector, {'pk': 1}, title=_('Food Industry')) create_if_needed(Sector, {'pk': 2}, title=_('Industry')) create_if_needed(Sector, {'pk': 3}, title=_('Software')) create_if_needed(Sector, {'pk': 4}, title=_('Telecom')) create_if_needed(Sector, {'pk': 5}, title=_('Restoration')) # --------------------------- # TODO: depend on the country no ?? create_if_needed(LegalForm, {'pk': 1}, title='SARL') create_if_needed(LegalForm, {'pk': 2}, title='Association loi 1901') create_if_needed(LegalForm, {'pk': 3}, title='SA') create_if_needed(LegalForm, {'pk': 4}, title='SAS') # --------------------------- create_if_needed(StaffSize, {'pk': 1}, size='1 - 5', order=1) create_if_needed(StaffSize, {'pk': 2}, size='6 - 10', order=2) create_if_needed(StaffSize, {'pk': 3}, size='11 - 50', order=3) create_if_needed(StaffSize, {'pk': 4}, size='51 - 100', order=4) create_if_needed(StaffSize, {'pk': 5}, size='100 - 500', order=5) create_if_needed(StaffSize, {'pk': 6}, size='> 500', order=6) # --------------------------- create_bmi = core_models.ButtonMenuItem.create_if_needed create_bmi(pk='persons-customer_contact_button', model=Contact, button=buttons.BecomeCustomerButton, order=20) create_bmi(pk='persons-prospect_contact_button', model=Contact, button=buttons.BecomeProspectButton, order=21) create_bmi(pk='persons-suspect_contact_button', model=Contact, button=buttons.BecomeSuspectButton, order=22) create_bmi(pk='persons-inactive_contact_button', model=Contact, button=buttons.BecomeInactiveButton, order=24) create_bmi(pk='persons-customer_orga_button', model=Organisation, button=buttons.BecomeCustomerButton, order=20) create_bmi(pk='persons-prospect_orga_button', model=Organisation, button=buttons.BecomeProspectButton, order=21) create_bmi(pk='persons-suspect_orga_button', model=Organisation, button=buttons.BecomeSuspectButton, order=22) create_bmi(pk='persons-inactive_orga_button', model=Organisation, button=buttons.BecomeInactiveButton, order=23) create_bmi(pk='persons-supplier_button', model=Organisation, button=buttons.BecomeSupplierButton, order=24) create_bmi(pk='persons-linked_contact_button', model=Organisation, button=buttons.AddLinkedContactButton, order=25) # Populate bricks ------------------ create_rbi = core_models.RelationBrickItem.objects.create_if_needed rbi_1 = create_rbi(constants.REL_SUB_CUSTOMER_SUPPLIER) rbi_2 = create_rbi(constants.REL_OBJ_CUSTOMER_SUPPLIER) create_cbci = core_models.CustomBrickConfigItem.objects.create build_cell = EntityCellRegularField.build # cbci_orga_1 = create_cbci( id='persons-organisation_main_info', name=_('Organisation information'), content_type=Organisation, cells=[ build_cell(Organisation, 'name'), build_cell(Organisation, 'is_managed'), build_cell(Organisation, 'staff_size'), build_cell(Organisation, 'legal_form'), build_cell(Organisation, 'sector'), build_cell(Organisation, 'capital'), build_cell(Organisation, 'siren'), build_cell(Organisation, 'naf'), build_cell(Organisation, 'siret'), build_cell(Organisation, 'rcs'), build_cell(Organisation, 'tvaintra'), build_cell(Organisation, 'subject_to_vat'), build_cell(Organisation, 'annual_revenue'), build_cell(Organisation, 'creation_date'), build_cell(Organisation, 'image'), # -- build_cell(Organisation, 'description'), # -- build_cell(Organisation, 'created'), build_cell(Organisation, 'modified'), build_cell(Organisation, 'user'), ], ) # cbci_orga_2 = create_cbci( id='persons-organisation_details', name=_('Organisation details'), content_type=Organisation, cells=[ build_cell(Organisation, 'phone'), build_cell(Organisation, 'fax'), build_cell(Organisation, 'email'), build_cell(Organisation, 'url_site'), ], ) cbci_orga_extra = create_cbci( id='persons-organisation_complementary', name=_('Organisation complementary information'), content_type=Organisation, cells=[ build_cell(Organisation, 'staff_size'), build_cell(Organisation, 'sector'), build_cell(Organisation, 'capital'), build_cell(Organisation, 'siren'), build_cell(Organisation, 'naf'), build_cell(Organisation, 'siret'), build_cell(Organisation, 'rcs'), build_cell(Organisation, 'tvaintra'), build_cell(Organisation, 'subject_to_vat'), build_cell(Organisation, 'annual_revenue'), build_cell(Organisation, 'creation_date'), build_cell(Organisation, 'image'), # -- build_cell(Organisation, 'description'), # -- build_cell(Organisation, 'fax'), build_cell(Organisation, 'email'), build_cell(Organisation, 'url_site'), ], ) HAT = core_models.BrickDetailviewLocation.HAT LEFT = core_models.BrickDetailviewLocation.LEFT RIGHT = core_models.BrickDetailviewLocation.RIGHT create_bdl = core_models.BrickDetailviewLocation.objects.create_if_needed create_bdl(brick=bricks.OrganisationCardHatBrick, order=1, zone=HAT, model=Organisation) create_bdl(brick=cbci_orga_extra.generate_id(), order=5, zone=LEFT, model=Organisation) create_bdl(brick=core_bricks.CustomFieldsBrick, order=40, zone=LEFT, model=Organisation) create_bdl(brick=bricks.PrettyAddressesBrick, order=50, zone=LEFT, model=Organisation) create_bdl(brick=bricks.PrettyOtherAddressesBrick, order=60, zone=LEFT, model=Organisation) create_bdl(brick=bricks.ManagersBrick, order=100, zone=LEFT, model=Organisation) create_bdl(brick=bricks.EmployeesBrick, order=120, zone=LEFT, model=Organisation) create_bdl(brick=core_bricks.PropertiesBrick, order=450, zone=LEFT, model=Organisation) create_bdl(brick=core_bricks.RelationsBrick, order=500, zone=LEFT, model=Organisation) create_bdl(brick=rbi_1.brick_id, order=5, zone=RIGHT, model=Organisation) create_bdl(brick=rbi_2.brick_id, order=10, zone=RIGHT, model=Organisation) create_bdl(brick=core_bricks.HistoryBrick, order=30, zone=RIGHT, model=Organisation) create_cbci( id='persons-contact_main_info', name=_('Contact information'), content_type=Contact, cells=[ build_cell(Contact, 'civility'), build_cell(Contact, 'first_name'), build_cell(Contact, 'last_name'), build_cell(Contact, 'sector'), build_cell(Contact, 'position'), build_cell(Contact, 'full_position'), build_cell(Contact, 'is_user'), build_cell(Contact, 'birthday'), build_cell(Contact, 'image'), # -- build_cell(Contact, 'description'), # -- build_cell(Contact, 'created'), build_cell(Contact, 'modified'), build_cell(Contact, 'user'), ], ) create_cbci( id='persons-contact_details', name=_('Contact details'), content_type=Contact, cells=[ build_cell(Contact, 'phone'), build_cell(Contact, 'mobile'), build_cell(Contact, 'fax'), build_cell(Contact, 'email'), build_cell(Contact, 'url_site'), build_cell(Contact, 'skype'), ], ) cbci_contact_extra = create_cbci( id='persons-contact_complementary', name=_('Contact complementary information'), content_type=Contact, cells=[ build_cell(Contact, 'sector'), build_cell(Contact, 'full_position'), build_cell(Contact, 'birthday'), build_cell(Contact, 'image'), # -- build_cell(Contact, 'description'), # -- build_cell(Contact, 'fax'), build_cell(Contact, 'url_site'), build_cell(Contact, 'skype'), ], ) create_bdl(brick=bricks.ContactCardHatBrick, order=1, zone=HAT, model=Contact) create_bdl(brick=cbci_contact_extra.generate_id(), order=30, zone=LEFT, model=Contact) create_bdl(brick=core_bricks.CustomFieldsBrick, order=40, zone=LEFT, model=Contact) create_bdl(brick=bricks.PrettyAddressesBrick, order=50, zone=LEFT, model=Contact) create_bdl(brick=bricks.PrettyOtherAddressesBrick, order=60, zone=LEFT, model=Contact) create_bdl(brick=core_bricks.PropertiesBrick, order=450, zone=LEFT, model=Contact) create_bdl(brick=core_bricks.RelationsBrick, order=500, zone=LEFT, model=Contact) create_bdl(brick=core_bricks.HistoryBrick, order=20, zone=RIGHT, model=Contact) if apps.is_installed('creme.assistants'): logger.info( 'Assistants app is installed => we use the assistants blocks on detail views and portal' ) from creme.assistants import bricks as a_bricks create_bdl(brick=a_bricks.TodosBrick, order=100, zone=RIGHT, model=Contact) create_bdl(brick=a_bricks.MemosBrick, order=200, zone=RIGHT, model=Contact) create_bdl(brick=a_bricks.AlertsBrick, order=300, zone=RIGHT, model=Contact) create_bdl(brick=a_bricks.UserMessagesBrick, order=500, zone=RIGHT, model=Contact) create_bdl(brick=a_bricks.TodosBrick, order=100, zone=RIGHT, model=Organisation) create_bdl(brick=a_bricks.MemosBrick, order=200, zone=RIGHT, model=Organisation) create_bdl(brick=a_bricks.AlertsBrick, order=300, zone=RIGHT, model=Organisation) create_bdl(brick=a_bricks.UserMessagesBrick, order=500, zone=RIGHT, model=Organisation) if apps.is_installed('creme.documents'): # logger.info('Documents app is installed => we use the documents block on detail views') from creme.documents.bricks import LinkedDocsBrick create_bdl(brick=LinkedDocsBrick, order=600, zone=RIGHT, model=Contact) create_bdl(brick=LinkedDocsBrick, order=600, zone=RIGHT, model=Organisation) if apps.is_installed('creme.activities'): core_models.BrickHomeLocation.objects.create( brick_id=bricks.NeglectedOrganisationsBrick.id_, order=15)
def populate(self): already_populated = RelationType.objects.filter( pk=constants.REL_SUB_EMPLOYED_BY, ).exists() Contact = persons.get_contact_model() Organisation = persons.get_organisation_model() rt_map = {} for rt_info in [ ( (constants.REL_SUB_EMPLOYED_BY, _('is an employee of'), [Contact]), (constants.REL_OBJ_EMPLOYED_BY, _('employs'), [Organisation]), ), ( ( constants.REL_SUB_CUSTOMER_SUPPLIER, _('is a customer of'), [Contact, Organisation], ), ( constants.REL_OBJ_CUSTOMER_SUPPLIER, _('is a supplier of'), [Contact, Organisation], ), ), ( (constants.REL_SUB_MANAGES, _('manages'), [Contact]), (constants.REL_OBJ_MANAGES, _('managed by'), [Organisation]), ), ( (constants.REL_SUB_PROSPECT, _('is a prospect of'), [Contact, Organisation]), (constants.REL_OBJ_PROSPECT, _('has as prospect'), [Contact, Organisation]), ), ( (constants.REL_SUB_SUSPECT, _('is a suspect of'), [Contact, Organisation]), (constants.REL_OBJ_SUSPECT, _('has as suspect'), [Contact, Organisation]), ), ( (constants.REL_SUB_PARTNER, _('is a partner of'), [Contact, Organisation]), (constants.REL_OBJ_PARTNER, _('has as partner'), [Contact, Organisation]), ), ( ( constants.REL_SUB_INACTIVE, _('is an inactive customer of'), [Contact, Organisation], ), ( constants.REL_OBJ_INACTIVE, _('has as inactive customer'), [Contact, Organisation], ), ), ( (constants.REL_SUB_SUBSIDIARY, _('has as subsidiary'), [Organisation]), (constants.REL_OBJ_SUBSIDIARY, _('is a subsidiary of'), [Organisation]), ), ( (constants.REL_SUB_COMPETITOR, _('is a competitor of'), [Contact, Organisation]), (constants.REL_OBJ_COMPETITOR, _('has as competitor'), [Contact, Organisation]), ), ]: rt, sym_rt = RelationType.create(*rt_info) rt_map[rt.id] = rt rt_map[sym_rt.id] = sym_rt get_rtype = RelationType.objects.get get_rtype(pk=core_constants.REL_SUB_HAS).add_subject_ctypes( Contact, Organisation) get_rtype( pk=core_constants.REL_OBJ_HAS).add_subject_ctypes(Organisation) # --------------------------- EntityFilter.objects.smart_update_or_create( constants.FILTER_MANAGED_ORGA, name=_('Managed by creme'), model=Organisation, user='******', conditions=[ condition_handler.RegularFieldConditionHandler.build_condition( model=Organisation, operator=operators.EqualsOperator, field_name='is_managed', values=[True], ), ], ) EntityFilter.objects.smart_update_or_create( constants.FILTER_CONTACT_ME, name=_('Me'), model=Contact, user='******', conditions=[ condition_handler.RegularFieldConditionHandler.build_condition( model=Contact, operator=operators.EqualsOperator, field_name='is_user', values=[operands.CurrentUserOperand.type_id], ), ], ) # --------------------------- create_hf = HeaderFilter.objects.create_if_needed create_hf( pk=constants.DEFAULT_HFILTER_CONTACT, model=Contact, name=_('Contact view'), cells_desc=[ (EntityCellRegularField, { 'name': 'last_name' }), (EntityCellRegularField, { 'name': 'first_name' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'email' }), (EntityCellRegularField, { 'name': 'user' }), EntityCellRelation( model=Contact, rtype=rt_map[constants.REL_SUB_EMPLOYED_BY]), ], ) create_hf( pk=constants.DEFAULT_HFILTER_ORGA, model=Organisation, name=_('Organisation view'), cells_desc=[ (EntityCellRegularField, { 'name': 'name' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'user' }), EntityCellRelation(model=Organisation, rtype=rt_map[constants.REL_OBJ_MANAGES]), ], ) create_hf( pk=constants.DEFAULT_HFILTER_ORGA_CUSTOMERS, model=Organisation, name=_('Prospect/Suspect view'), cells_desc=[ (EntityCellRegularField, { 'name': 'name' }), (EntityCellRegularField, { 'name': 'sector' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'email' }), (EntityCellRegularField, { 'name': 'user' }), EntityCellRelation( model=Organisation, rtype=rt_map[constants.REL_SUB_CUSTOMER_SUPPLIER], ), EntityCellRelation( model=Organisation, rtype=rt_map[constants.REL_SUB_PROSPECT], ), EntityCellRelation( model=Organisation, rtype=rt_map[constants.REL_SUB_SUSPECT], ), ], ) # --------------------------- creation_only_groups_desc = [ { 'name': _('Properties'), 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.CREME_PROPERTIES }, ), ], }, { 'name': _('Relationships'), 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.RELATIONS }, ), ], }, ] description_group_desc = { 'name': _('Description'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ (EntityCellRegularField, { 'name': 'description' }), ], } cfields_group_desc = { 'name': _('Custom fields'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.REMAINING_CUSTOMFIELDS }, ), ], } contact_groups_desc = [ { 'name': _('General information'), 'layout': LAYOUT_DUAL_FIRST, 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'civility' }), (EntityCellRegularField, { 'name': 'last_name' }), (EntityCellRegularField, { 'name': 'first_name' }), (EntityCellRegularField, { 'name': 'position' }), (EntityCellRegularField, { 'name': 'full_position' }), (EntityCellRegularField, { 'name': 'sector' }), (EntityCellRegularField, { 'name': 'birthday' }), (EntityCellRegularField, { 'name': 'image' }), ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.REMAINING_REGULARFIELDS }, ), ], }, description_group_desc, { 'name': _('Contact details'), 'layout': LAYOUT_DUAL_SECOND, 'cells': [ (EntityCellRegularField, { 'name': 'skype' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'mobile' }), (EntityCellRegularField, { 'name': 'fax' }), (EntityCellRegularField, { 'name': 'email' }), (EntityCellRegularField, { 'name': 'url_site' }), ], }, cfields_group_desc, AddressesGroup(model=Contact), ] orga_groups_desc = [ { 'name': _('General information'), 'layout': LAYOUT_DUAL_FIRST, 'cells': [ (EntityCellRegularField, { 'name': 'user' }), (EntityCellRegularField, { 'name': 'name' }), (EntityCellRegularField, { 'name': 'phone' }), (EntityCellRegularField, { 'name': 'fax' }), (EntityCellRegularField, { 'name': 'email' }), (EntityCellRegularField, { 'name': 'url_site' }), (EntityCellRegularField, { 'name': 'sector' }), (EntityCellRegularField, { 'name': 'legal_form' }), (EntityCellRegularField, { 'name': 'staff_size' }), (EntityCellRegularField, { 'name': 'capital' }), (EntityCellRegularField, { 'name': 'annual_revenue' }), (EntityCellRegularField, { 'name': 'siren' }), (EntityCellRegularField, { 'name': 'naf' }), (EntityCellRegularField, { 'name': 'siret' }), (EntityCellRegularField, { 'name': 'rcs' }), (EntityCellRegularField, { 'name': 'tvaintra' }), (EntityCellRegularField, { 'name': 'subject_to_vat' }), (EntityCellRegularField, { 'name': 'creation_date' }), (EntityCellRegularField, { 'name': 'image' }), ( EntityCellCustomFormSpecial, { 'name': EntityCellCustomFormSpecial.REMAINING_REGULARFIELDS }, ), ], }, description_group_desc, cfields_group_desc, AddressesGroup(model=Organisation), ] CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.CONTACT_CREATION_CFORM, groups_desc=[ *contact_groups_desc, *creation_only_groups_desc, ], ) CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.CONTACT_EDITION_CFORM, groups_desc=contact_groups_desc, ) CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.ORGANISATION_CREATION_CFORM, groups_desc=[ *orga_groups_desc, *creation_only_groups_desc, ], ) CustomFormConfigItem.objects.create_if_needed( descriptor=custom_forms.ORGANISATION_EDITION_CFORM, groups_desc=orga_groups_desc, ) # --------------------------- create_sci = SearchConfigItem.objects.create_if_needed create_sci(Contact, ['last_name', 'first_name', 'phone', 'mobile', 'email']) create_sci( Organisation, ['name', 'phone', 'email', 'sector__title', 'legal_form__title']) # --------------------------- # TODO: move to "not already_populated" section in creme2.4 if not MenuConfigItem.objects.filter( entry_id__startswith='persons-').exists(): directory = MenuConfigItem.objects.get_or_create( entry_id=ContainerEntry.id, entry_data={'label': _('Directory')}, defaults={'order': 20}, )[0] create_mitem = MenuConfigItem.objects.create create_mitem(entry_id=menu.OrganisationsEntry.id, order=10, parent=directory) create_mitem(entry_id=menu.ContactsEntry.id, order=20, parent=directory) create_mitem(entry_id=menu.CustomersEntry.id, order=30, 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.OrganisationCreationEntry.id, order=10, parent=creations, ) create_mitem( entry_id=menu.ContactCreationEntry.id, order=20, parent=creations, ) # --------------------------- if not already_populated: create_if_needed(Civility, {'pk': 1}, title=_('Madam'), shortcut=_('Mrs.')) create_if_needed(Civility, {'pk': 2}, title=_('Miss'), shortcut=_('Ms.')) create_if_needed(Civility, {'pk': 3}, title=_('Mister'), shortcut=_('Mr.')) create_if_needed(Civility, {'pk': 4}, title=_('N/A'), shortcut='') # --------------------------- # TODO: add relation to admin ???? if not Organisation.objects.exists(): Organisation.objects.create( user=get_user_model().objects.get_admin(), name=_('ReplaceByYourSociety'), is_managed=True, uuid=constants.UUID_FIRST_ORGA, ) # --------------------------- create_if_needed(Position, {'pk': 1}, title=_('CEO')) create_if_needed(Position, {'pk': 2}, title=_('Secretary')) create_if_needed(Position, {'pk': 3}, title=_('Technician')) # --------------------------- create_if_needed(Sector, {'pk': 1}, title=_('Food Industry')) create_if_needed(Sector, {'pk': 2}, title=_('Industry')) create_if_needed(Sector, {'pk': 3}, title=_('Software')) create_if_needed(Sector, {'pk': 4}, title=_('Telecom')) create_if_needed(Sector, {'pk': 5}, title=_('Restoration')) # --------------------------- # TODO: depend on the country no ?? create_if_needed(LegalForm, {'pk': 1}, title='SARL') create_if_needed(LegalForm, {'pk': 2}, title='Association loi 1901') create_if_needed(LegalForm, {'pk': 3}, title='SA') create_if_needed(LegalForm, {'pk': 4}, title='SAS') # --------------------------- create_if_needed(StaffSize, {'pk': 1}, size='1 - 5', order=1) create_if_needed(StaffSize, {'pk': 2}, size='6 - 10', order=2) create_if_needed(StaffSize, {'pk': 3}, size='11 - 50', order=3) create_if_needed(StaffSize, {'pk': 4}, size='51 - 100', order=4) create_if_needed(StaffSize, {'pk': 5}, size='100 - 500', order=5) create_if_needed(StaffSize, {'pk': 6}, size='> 500', order=6) # --------------------------- create_bmi = ButtonMenuItem.objects.create_if_needed create_bmi(model=Contact, button=buttons.BecomeCustomerButton, order=20) create_bmi(model=Contact, button=buttons.BecomeProspectButton, order=21) create_bmi(model=Contact, button=buttons.BecomeSuspectButton, order=22) create_bmi(model=Contact, button=buttons.BecomeInactiveButton, order=24) create_bmi(model=Organisation, button=buttons.BecomeCustomerButton, order=20) create_bmi(model=Organisation, button=buttons.BecomeProspectButton, order=21) create_bmi(model=Organisation, button=buttons.BecomeSuspectButton, order=22) create_bmi(model=Organisation, button=buttons.BecomeInactiveButton, order=23) create_bmi(model=Organisation, button=buttons.BecomeSupplierButton, order=24) create_bmi(model=Organisation, button=buttons.AddLinkedContactButton, order=25) # Populate bricks ------------------ create_rbi = RelationBrickItem.objects.create_if_needed rbi_1 = create_rbi(constants.REL_SUB_CUSTOMER_SUPPLIER) rbi_2 = create_rbi(constants.REL_OBJ_CUSTOMER_SUPPLIER) create_cbci = CustomBrickConfigItem.objects.create build_cell = EntityCellRegularField.build # cbci_orga_1 = create_cbci( id='persons-organisation_main_info', name=_('Organisation information'), content_type=Organisation, cells=[ build_cell(Organisation, 'name'), build_cell(Organisation, 'is_managed'), build_cell(Organisation, 'staff_size'), build_cell(Organisation, 'legal_form'), build_cell(Organisation, 'sector'), build_cell(Organisation, 'capital'), build_cell(Organisation, 'siren'), build_cell(Organisation, 'naf'), build_cell(Organisation, 'siret'), build_cell(Organisation, 'rcs'), build_cell(Organisation, 'tvaintra'), build_cell(Organisation, 'subject_to_vat'), build_cell(Organisation, 'annual_revenue'), build_cell(Organisation, 'creation_date'), build_cell(Organisation, 'image'), # -- build_cell(Organisation, 'description'), # -- build_cell(Organisation, 'created'), build_cell(Organisation, 'modified'), build_cell(Organisation, 'user'), ], ) # cbci_orga_2 = create_cbci( id='persons-organisation_details', name=_('Organisation details'), content_type=Organisation, cells=[ build_cell(Organisation, 'phone'), build_cell(Organisation, 'fax'), build_cell(Organisation, 'email'), build_cell(Organisation, 'url_site'), ], ) cbci_orga_extra = create_cbci( id='persons-organisation_complementary', name=_('Organisation complementary information'), content_type=Organisation, cells=[ build_cell(Organisation, 'staff_size'), build_cell(Organisation, 'sector'), build_cell(Organisation, 'capital'), build_cell(Organisation, 'siren'), build_cell(Organisation, 'naf'), build_cell(Organisation, 'siret'), build_cell(Organisation, 'rcs'), build_cell(Organisation, 'tvaintra'), build_cell(Organisation, 'subject_to_vat'), build_cell(Organisation, 'annual_revenue'), build_cell(Organisation, 'creation_date'), build_cell(Organisation, 'image'), # -- build_cell(Organisation, 'description'), # -- build_cell(Organisation, 'fax'), build_cell(Organisation, 'email'), build_cell(Organisation, 'url_site'), ], ) HAT = BrickDetailviewLocation.HAT LEFT = BrickDetailviewLocation.LEFT RIGHT = BrickDetailviewLocation.RIGHT BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Organisation, 'zone': LEFT }, data=[ { 'brick': bricks.OrganisationCardHatBrick, 'order': 1, 'zone': HAT }, { 'brick': cbci_orga_extra.brick_id, 'order': 5 }, { 'brick': core_bricks.CustomFieldsBrick, 'order': 40 }, { 'brick': bricks.PrettyAddressesBrick, 'order': 50 }, { 'brick': bricks.PrettyOtherAddressesBrick, 'order': 60 }, { 'brick': bricks.ManagersBrick, 'order': 100 }, { 'brick': bricks.EmployeesBrick, 'order': 120 }, { 'brick': core_bricks.PropertiesBrick, 'order': 450 }, { 'brick': core_bricks.RelationsBrick, 'order': 500 }, { 'brick': rbi_1.brick_id, 'order': 5, 'zone': RIGHT }, { 'brick': rbi_2.brick_id, 'order': 10, 'zone': RIGHT }, { 'brick': core_bricks.HistoryBrick, 'order': 30, 'zone': RIGHT }, ], ) create_cbci( id='persons-contact_main_info', name=_('Contact information'), content_type=Contact, cells=[ build_cell(Contact, 'civility'), build_cell(Contact, 'first_name'), build_cell(Contact, 'last_name'), build_cell(Contact, 'sector'), build_cell(Contact, 'position'), build_cell(Contact, 'full_position'), build_cell(Contact, 'is_user'), build_cell(Contact, 'birthday'), build_cell(Contact, 'image'), # -- build_cell(Contact, 'description'), # -- build_cell(Contact, 'created'), build_cell(Contact, 'modified'), build_cell(Contact, 'user'), ], ) create_cbci( id='persons-contact_details', name=_('Contact details'), content_type=Contact, cells=[ build_cell(Contact, 'phone'), build_cell(Contact, 'mobile'), build_cell(Contact, 'fax'), build_cell(Contact, 'email'), build_cell(Contact, 'url_site'), build_cell(Contact, 'skype'), ], ) cbci_contact_extra = create_cbci( id='persons-contact_complementary', name=_('Contact complementary information'), content_type=Contact, cells=[ build_cell(Contact, 'sector'), build_cell(Contact, 'full_position'), build_cell(Contact, 'birthday'), build_cell(Contact, 'image'), # -- build_cell(Contact, 'description'), # -- build_cell(Contact, 'fax'), build_cell(Contact, 'url_site'), build_cell(Contact, 'skype'), ], ) BrickDetailviewLocation.objects.multi_create( defaults={ 'model': Contact, 'zone': LEFT }, data=[ { 'brick': bricks.ContactCardHatBrick, 'order': 1, 'zone': HAT }, { 'brick': cbci_contact_extra.brick_id, 'order': 30 }, { 'brick': core_bricks.CustomFieldsBrick, 'order': 40 }, { 'brick': bricks.PrettyAddressesBrick, 'order': 50 }, { 'brick': bricks.PrettyOtherAddressesBrick, 'order': 60 }, { '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 and portal' ) from creme.assistants import bricks as a_bricks for model in (Contact, Organisation): 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': 500 }, ], ) if apps.is_installed('creme.documents'): # logger.info('Documents app is installed # => we use the documents block on detail views') from creme.documents.bricks import LinkedDocsBrick BrickDetailviewLocation.objects.multi_create( defaults={ 'brick': LinkedDocsBrick, 'order': 600, 'zone': RIGHT }, data=[ { 'model': Contact }, { 'model': Organisation }, ], ) if apps.is_installed('creme.activities'): BrickHomeLocation.objects.create( brick_id=bricks.NeglectedOrganisationsBrick.id_, order=15, )
def populate(self): already_populated = RelationType.objects.filter( pk=constants.REL_SUB_TARGETS).exists() Contact = persons.get_contact_model() Organisation = persons.get_organisation_model() Product = products.get_product_model() Service = products.get_service_model() # --------------------------- create_rtype = RelationType.create rt_sub_targets = create_rtype( (constants.REL_SUB_TARGETS, _('targets the organisation/contact'), [Opportunity]), (constants.REL_OBJ_TARGETS, _('targeted by the opportunity'), [Organisation, Contact]), is_internal=True, minimal_display=(True, True), )[0] rt_obj_emit_orga = create_rtype( (constants.REL_SUB_EMIT_ORGA, _('has generated the opportunity'), [Organisation]), (constants.REL_OBJ_EMIT_ORGA, _('has been generated by'), [Opportunity]), is_internal=True, minimal_display=(True, True), )[1] create_rtype((constants.REL_SUB_LINKED_PRODUCT, _('is linked to the opportunity'), [Product]), (constants.REL_OBJ_LINKED_PRODUCT, _('concerns the product'), [Opportunity])) create_rtype((constants.REL_SUB_LINKED_SERVICE, _('is linked to the opportunity'), [Service]), (constants.REL_OBJ_LINKED_SERVICE, _('concerns the service'), [Opportunity])) create_rtype( (constants.REL_SUB_LINKED_CONTACT, _('involves in the opportunity'), [Contact]), (constants.REL_OBJ_LINKED_CONTACT, _('stages'), [Opportunity])) create_rtype((constants.REL_SUB_RESPONSIBLE, _('is responsible for'), [Contact]), (constants.REL_OBJ_RESPONSIBLE, _('has as responsible contact'), [Opportunity])) if apps.is_installed('creme.activities'): logger.info( 'Activities app is installed => an Opportunity can be the subject of an Activity' ) from creme.activities.constants import REL_SUB_ACTIVITY_SUBJECT RelationType.objects.get( pk=REL_SUB_ACTIVITY_SUBJECT).add_subject_ctypes(Opportunity) if apps.is_installed('creme.billing'): logger.info( 'Billing app is installed => we create relationships between Opportunities & billing models' ) from creme.billing import get_invoice_model, get_quote_model, get_sales_order_model Invoice = get_invoice_model() Quote = get_quote_model() SalesOrder = get_sales_order_model() create_rtype( (constants.REL_SUB_LINKED_SALESORDER, _('is associate with the opportunity'), [SalesOrder]), (constants.REL_OBJ_LINKED_SALESORDER, _('has generated the salesorder'), [Opportunity])) create_rtype((constants.REL_SUB_LINKED_INVOICE, _('generated for the opportunity'), [Invoice]), (constants.REL_OBJ_LINKED_INVOICE, _('has resulted in the invoice'), [Opportunity])) create_rtype((constants.REL_SUB_LINKED_QUOTE, _('generated for the opportunity'), [Quote]), (constants.REL_OBJ_LINKED_QUOTE, _('has resulted in the quote'), [Opportunity])) create_rtype( (constants.REL_SUB_CURRENT_DOC, _('is the current accounting document of'), [SalesOrder, Invoice, Quote]), (constants.REL_OBJ_CURRENT_DOC, _('has as current accounting document'), [Opportunity])) # --------------------------- create_sv = SettingValue.objects.get_or_create create_sv(key_id=setting_keys.quote_key.id, defaults={'value': False}) create_sv(key_id=setting_keys.target_constraint_key.id, defaults={'value': True}) create_sv(key_id=setting_keys.emitter_constraint_key.id, defaults={'value': True}) # --------------------------- create_efilter = partial(EntityFilter.create, model=Opportunity, user='******') # create_cond = partial(EntityFilterCondition.build_4_field, model=Opportunity) build_cond = partial( condition_handler.RegularFieldConditionHandler.build_condition, model=Opportunity, ) create_efilter( 'opportunities-opportunities_won', name=_('Opportunities won'), conditions=[ # create_cond(operator=EntityFilterCondition.EQUALS, # name='sales_phase__won', # values=[True], # ), build_cond( operator=operators.EqualsOperator, field_name='sales_phase__won', values=[True], ), ], ) create_efilter( 'opportunities-opportunities_lost', name=_('Opportunities lost'), conditions=[ # create_cond(operator=EntityFilterCondition.EQUALS, # name='sales_phase__lost', # values=[True], # ), build_cond( operator=operators.EqualsOperator, field_name='sales_phase__lost', values=[True], ), ], ) create_efilter( 'opportunities-neither_won_nor_lost_opportunities', name=_('Neither won nor lost opportunities'), conditions=[ # create_cond(operator=EntityFilterCondition.EQUALS_NOT, # name='sales_phase__won', # values=[True], # ), build_cond( operator=operators.EqualsNotOperator, field_name='sales_phase__won', values=[True], ), # create_cond(operator=EntityFilterCondition.EQUALS_NOT, # name='sales_phase__lost', # values=[True], # ), build_cond( operator=operators.EqualsNotOperator, field_name='sales_phase__lost', values=[True], ), ], ) # --------------------------- HeaderFilter.create( pk=constants.DEFAULT_HFILTER_OPPORTUNITY, model=Opportunity, name=_('Opportunity view'), cells_desc=[ (EntityCellRegularField, { 'name': 'name' }), EntityCellRelation(model=Opportunity, rtype=rt_sub_targets), (EntityCellRegularField, { 'name': 'sales_phase' }), (EntityCellRegularField, { 'name': 'estimated_sales' }), (EntityCellRegularField, { 'name': 'made_sales' }), (EntityCellRegularField, { 'name': 'closing_date' }), ], ) # --------------------------- SearchConfigItem.create_if_needed( Opportunity, ['name', 'made_sales', 'sales_phase__name', 'origin__name']) # --------------------------- if not already_populated: create_sphase = SalesPhase.objects.create create_sphase(name=_('Forthcoming'), order=1) create_sphase(name=pgettext('opportunities-sales_phase', 'Abandoned'), order=4) create_sphase(name=pgettext('opportunities-sales_phase', 'Won'), order=5, won=True) create_sphase(name=pgettext('opportunities-sales_phase', 'Lost'), order=6, lost=True) create_sphase(name=_('Under negotiation'), order=3) create_sphase(name=_('In progress'), order=2) # --------------------------- create_origin = Origin.objects.create create_origin(name=pgettext('opportunities-origin', 'None')) create_origin(name=_('Web site')) create_origin(name=_('Mouth')) create_origin(name=_('Show')) create_origin(name=_('Direct email')) create_origin(name=_('Direct phone call')) create_origin(name=_('Employee')) create_origin(name=_('Partner')) create_origin(name=pgettext('opportunities-origin', 'Other')) # --------------------------- create_button = ButtonMenuItem.create_if_needed create_button(pk='opportunities-linked_opp_button', model=Organisation, button=LinkedOpportunityButton, order=30) # TODO: This pk is kept for compatibility create_button(pk='opportunities-linked_opp_button_contact', model=Contact, button=LinkedOpportunityButton, order=30) # --------------------------- create_bdl = partial( BrickDetailviewLocation.objects.create_if_needed, model=Opportunity) LEFT = BrickDetailviewLocation.LEFT RIGHT = BrickDetailviewLocation.RIGHT build_cell = EntityCellRegularField.build cbci = CustomBrickConfigItem.objects.create( id='opportunities-complementary', name=_('Opportunity complementary information'), content_type=Opportunity, cells=[ build_cell(Opportunity, 'reference'), build_cell(Opportunity, 'currency'), build_cell(Opportunity, 'chance_to_win'), build_cell(Opportunity, 'expected_closing_date'), build_cell(Opportunity, 'closing_date'), build_cell(Opportunity, 'origin'), build_cell(Opportunity, 'first_action_date'), build_cell(Opportunity, 'description'), ], ) create_bdl(brick=bricks.OpportunityCardHatBrick, order=1, zone=BrickDetailviewLocation.HAT) create_bdl(brick=cbci.generate_id(), order=5, zone=LEFT) create_bdl(brick=core_bricks.CustomFieldsBrick, order=40, zone=LEFT) create_bdl(brick=bricks.BusinessManagersBrick, order=60, zone=LEFT) create_bdl(brick=bricks.LinkedContactsBrick, order=62, zone=LEFT) create_bdl(brick=bricks.LinkedProductsBrick, order=64, zone=LEFT) create_bdl(brick=bricks.LinkedServicesBrick, order=66, zone=LEFT) create_bdl(brick=core_bricks.PropertiesBrick, order=450, zone=LEFT) create_bdl(brick=core_bricks.RelationsBrick, order=500, zone=LEFT) create_bdl(brick=bricks.OppTargetBrick, order=1, zone=RIGHT) create_bdl(brick=bricks.OppTotalBrick, order=2, zone=RIGHT) create_bdl(brick=core_bricks.HistoryBrick, order=20, zone=RIGHT) if apps.is_installed('creme.activities'): logger.info( 'Activities app is installed => we use the "Future activities" & "Past activities" blocks' ) from creme.activities import bricks as act_bricks create_bdl(brick=act_bricks.FutureActivitiesBrick, order=20, zone=RIGHT) create_bdl(brick=act_bricks.PastActivitiesBrick, order=21, zone=RIGHT) if apps.is_installed('creme.assistants'): logger.info( 'Assistants app is installed => we use the assistants blocks on detail views and portal' ) from creme.assistants import bricks as assistants_bricks create_bdl(brick=assistants_bricks.TodosBrick, order=100, zone=RIGHT) create_bdl(brick=assistants_bricks.MemosBrick, order=200, zone=RIGHT) create_bdl(brick=assistants_bricks.AlertsBrick, order=300, zone=RIGHT) create_bdl(brick=assistants_bricks.UserMessagesBrick, order=500, zone=RIGHT) if apps.is_installed('creme.documents'): # logger.info('Documents app is installed => we use the documents block on detail view') from creme.documents.bricks import LinkedDocsBrick create_bdl(brick=LinkedDocsBrick, order=600, zone=RIGHT) if apps.is_installed('creme.billing'): logger.info( 'Billing app is installed => we use the billing blocks on detail view' ) create_bdl(brick=bricks.QuotesBrick, order=70, zone=LEFT) create_bdl(brick=bricks.SalesOrdersBrick, order=72, zone=LEFT) create_bdl(brick=bricks.InvoicesBrick, order=74, zone=LEFT) if apps.is_installed('creme.emails'): logger.info( 'Emails app is installed => we use the emails blocks on detail view' ) from creme.emails.bricks import MailsHistoryBrick create_bdl(brick=MailsHistoryBrick, order=600, zone=RIGHT) create_bdl(brick=bricks.TargettingOpportunitiesBrick, order=16, zone=RIGHT, model=Organisation) # --------------------------- if apps.is_installed('creme.reports'): logger.info( 'Reports app is installed => we create an Opportunity report, with 2 graphs, and related blocks' ) self.create_report_n_graphes(rt_obj_emit_orga)