[REF] crm: simplify evaluation of assignment domains

GLOBAL PURPOSE

Ability to have salesmen belonging to several sales team is a core requirement
of CRM. It is therefore moved from website_crm_score to crm along with cleaning
and behavior improvement. Automatic lead assignment is also moved and cleaned.

SPECIFICATIONS

Remove safe_eval and its support of datetime and context_today. Check in
existing dbs show that it is not used in team or member assignment domains.
We therefore choose to limit content of domains to what goes through a
literal_eval. It allows to reduce potential issues.

We also improve warning messages in order to give clearer message to users
when dealing with input errors.

LINKS

Task ID-2086889 (main task)
Task ID-2357969 (scoring migration task)
Community PR odoo/odoo#48422
Enterprise PR odoo/enterprise#499
Upgrade PR odoo/upgrade#996
This commit is contained in:
Thibault Delavallée
2021-01-21 12:22:09 +00:00
parent f84270b072
commit 675623d390
3 changed files with 15 additions and 17 deletions
-6
View File
@@ -71,12 +71,6 @@ PARTNER_ADDRESS_FIELDS_TO_SYNC = [
PLS_COMPUTE_BATCH_STEP = 50000 # odoo.models.PREFETCH_MAX = 1000 but larger cluster can speed up global computation
PLS_UPDATE_BATCH_STEP = 5000
# Evaluation context for all domain-based lead auto assignment
LEAD_ASSIGN_EVAL_CONTEXT = {
'datetime': safe_eval.datetime,
'context_today': datetime.now,
}
class Lead(models.Model):
_name = "crm.lead"
+5 -5
View File
@@ -9,7 +9,6 @@ import threading
from ast import literal_eval
from odoo import api, exceptions, fields, models, _
from odoo.addons.crm.models.crm_lead import LEAD_ASSIGN_EVAL_CONTEXT
from odoo.osv import expression
from odoo.tools.safe_eval import safe_eval
@@ -118,10 +117,11 @@ class Team(models.Model):
def _constrains_assignment_domain(self):
for team in self:
try:
domain = safe_eval(team.assignment_domain or '[]', LEAD_ASSIGN_EVAL_CONTEXT)
self.env['crm.lead'].search_count(domain)
domain = literal_eval(team.assignment_domain or '[]')
if domain:
self.env['crm.lead'].search(domain, limit=1)
except Exception:
raise Warning('Domain for %s is incorrectly formatted' % team.name)
raise exceptions.ValidationError(_('Assignment domain for team %(team)s is incorrectly formatted', team=team.name))
# ------------------------------------------------------------
# ORM
@@ -419,7 +419,7 @@ class Team(models.Model):
# compute assign domain for each team before looping on them by bundle size
teams_domain = dict(
(team, safe_eval(team.assignment_domain or '[]', LEAD_ASSIGN_EVAL_CONTEXT))
(team, literal_eval(team.assignment_domain or '[]'))
for team in remaining_teams
)
# compute limit of leads to assign to each team: 2 times team capacity, based on given work_days
+10 -6
View File
@@ -7,10 +7,10 @@ import math
import threading
import random
from ast import literal_eval
from odoo import api, exceptions, fields, models, _
from odoo.addons.crm.models.crm_lead import LEAD_ASSIGN_EVAL_CONTEXT
from odoo.osv import expression
from odoo.tools import safe_eval
_logger = logging.getLogger(__name__)
@@ -38,10 +38,14 @@ class Team(models.Model):
def _constrains_assignment_domain(self):
for member in self:
try:
domain = safe_eval.safe_eval(member.assignment_domain or '[]', LEAD_ASSIGN_EVAL_CONTEXT)
self.env['crm.lead'].search(domain, limit=1)
domain = literal_eval(member.assignment_domain or '[]')
if domain:
self.env['crm.lead'].search(domain, limit=1)
except Exception:
raise exceptions.UserError(_('Team membership assign domain is incorrectly formatted'))
raise exceptions.ValidationEreror(_(
'Member assignment domain for user %(user)s and team %(team)s is incorrectly formatted',
user=member.user_id.name, team=member.crm_team_id.name
))
def _get_lead_month_domain(self):
limit_date = fields.Datetime.now() - datetime.timedelta(days=30)
@@ -133,7 +137,7 @@ class Team(models.Model):
# could probably be optimized
for member in members:
lead_domain = expression.AND([
safe_eval.safe_eval(member.assignment_domain or '[]', LEAD_ASSIGN_EVAL_CONTEXT),
literal_eval(member.assignment_domain or '[]'),
['&', '&', ('user_id', '=', False), ('date_open', '=', False), ('team_id', '=', member.crm_team_id.id)]
])