Functional
==========
Sales teams become sales channels. Their dashboard cards now include a graph
displaying customizable data for managers (comparable to those in accounting).
By default, you now have the following sales channels (non-demo):
Direct Sales (with installation of crm or sale)
Sales Channel type: Sales
Works same as before, what's changed is:
- their cards display one big button directing to the start of their
workflow
- the links on the right-hand side have been reworked, and are only
displayed when there is at least one item requiring attention.
- 'More' tab remains unchanged.
Website (with installation of website_sale)
Sales Channel type: Website
Differences lies in the links displayed in the dashboard card:
- it displays abandoned carts, awaiting payments and payments to capture
Default Channel linked to all sales made from the eCommerce.
Point of Sale (with installation of sale and point_of_sale
-> auto-installs pos_sale)
Sales Channel type: Point of Sale
Linked to pos.configs and their pos.sessions and pos.orders.
- only links to their linked pos.config dashboard and open sessions
- can't use opportunities, lead or invoicing and can only display
pos.order data in the graph.
Default Channel linked to the default pos.config.
Technical
=========
- Add a channel type: sales, pos, website that have different actions/settings
- Add a graphs to the kanban cards in the sales/crm dashboard, configurable in
the form view in the new dashboard page.
- Rename sales teams to sales channels, rename and add default and demo sales
channels
- Change dashboard links depending on the channel type and add a related
computed fields on crm.team
- Rename strings and improve channel form view.
- Leads are now checked by default once activated for 'sales' type channels
- Disable checking "leads" without using "opportunities".
- Hide invoicing and invoicing target depending on channel type.
- Move currency_id to sales_team
46 lines
2.1 KiB
Python
46 lines
2.1 KiB
Python
# -*- coding: utf-8 -*-
|
|
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
|
|
|
from odoo import api, fields, models
|
|
|
|
|
|
class Partner(models.Model):
|
|
|
|
_inherit = 'res.partner'
|
|
|
|
team_id = fields.Many2one('crm.team', string='Sales Channel', oldname='section_id')
|
|
opportunity_ids = fields.One2many('crm.lead', 'partner_id', string='Opportunities', domain=[('type', '=', 'opportunity')])
|
|
meeting_ids = fields.Many2many('calendar.event', 'calendar_event_res_partner_rel', 'res_partner_id', 'calendar_event_id', string='Meetings')
|
|
opportunity_count = fields.Integer("Opportunity", compute='_compute_opportunity_count')
|
|
meeting_count = fields.Integer("# Meetings", compute='_compute_meeting_count')
|
|
activities_count = fields.Integer("Activities", compute='_compute_activities_count')
|
|
|
|
@api.multi
|
|
def _compute_opportunity_count(self):
|
|
for partner in self:
|
|
operator = 'child_of' if partner.is_company else '=' # the opportunity count should counts the opportunities of this company and all its contacts
|
|
partner.opportunity_count = self.env['crm.lead'].search_count([('partner_id', operator, partner.id), ('type', '=', 'opportunity')])
|
|
|
|
@api.multi
|
|
def _compute_meeting_count(self):
|
|
for partner in self:
|
|
partner.meeting_count = len(partner.meeting_ids)
|
|
|
|
@api.multi
|
|
def _compute_activities_count(self):
|
|
activity_data = self.env['crm.activity.report'].read_group([('partner_id', 'in', self.ids)], ['partner_id'], ['partner_id'])
|
|
mapped_data = {act['partner_id'][0]: act['partner_id_count'] for act in activity_data}
|
|
for partner in self:
|
|
partner.activities_count = mapped_data.get(partner.id, 0)
|
|
|
|
@api.multi
|
|
def schedule_meeting(self):
|
|
partner_ids = self.ids
|
|
partner_ids.append(self.env.user.partner_id.id)
|
|
action = self.env.ref('calendar.action_calendar_event').read()[0]
|
|
action['context'] = {
|
|
'search_default_partner_ids': self._context['partner_name'],
|
|
'default_partner_ids': partner_ids,
|
|
}
|
|
return action
|