[IMP] *: use ast.literal_eval
When simply need to parse a domain, it is easier Add .strip() on ir.ui.view as ast.literal_eval produces an syntax error if the node starts with spaces (as done in the xpath of hr_attendance.view_employee_form_inherit_hr_attendance) closes odoo/odoo#43831 Related: odoo/enterprise#7894 Signed-off-by: Martin Trigaux (mat) <mat@odoo.com>
This commit is contained in:
@@ -5,7 +5,7 @@ from babel.dates import format_datetime, format_date
|
||||
from odoo import models, api, _, fields
|
||||
from odoo.osv import expression
|
||||
from odoo.release import version
|
||||
from odoo.tools import DEFAULT_SERVER_DATE_FORMAT as DF, safe_eval
|
||||
from odoo.tools import DEFAULT_SERVER_DATE_FORMAT as DF
|
||||
from odoo.tools.misc import formatLang, format_date as odoo_format_date, get_lang
|
||||
import random
|
||||
|
||||
@@ -491,7 +491,7 @@ class account_journal(models.Model):
|
||||
else:
|
||||
action_ref = 'account.action_account_payments'
|
||||
[action] = self.env.ref(action_ref).read()
|
||||
action['context'] = dict(safe_eval(action.get('context')), default_journal_id=self.id, search_default_journal_id=self.id)
|
||||
action['context'] = dict(ast.literal_eval(action.get('context')), default_journal_id=self.id, search_default_journal_id=self.id)
|
||||
if mode == 'form':
|
||||
action['views'] = [[False, 'form']]
|
||||
return action
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
from odoo import api, fields, models, _
|
||||
from odoo.exceptions import RedirectWarning, UserError, ValidationError
|
||||
from odoo.tools import float_is_zero, float_compare, safe_eval, date_utils, email_split, email_escape_char, email_re
|
||||
from odoo.tools import float_is_zero, float_compare, date_utils, email_split, email_escape_char, email_re
|
||||
from odoo.tools.misc import formatLang, format_date, get_lang
|
||||
|
||||
from datetime import date, timedelta
|
||||
@@ -11,6 +11,7 @@ from itertools import zip_longest
|
||||
from hashlib import sha256
|
||||
from json import dumps
|
||||
|
||||
import ast
|
||||
import json
|
||||
import re
|
||||
|
||||
@@ -3984,7 +3985,7 @@ class AccountMoveLine(models.Model):
|
||||
context = dict(self._context or {})
|
||||
domain = domain or []
|
||||
if not isinstance(domain, (list, tuple)):
|
||||
domain = safe_eval(domain)
|
||||
domain = ast.literal_eval(domain)
|
||||
|
||||
date_field = 'date'
|
||||
if context.get('aged_balance'):
|
||||
|
||||
@@ -7,6 +7,7 @@ from odoo import api, fields, models, _
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
from odoo.exceptions import ValidationError
|
||||
|
||||
import ast
|
||||
|
||||
class Team(models.Model):
|
||||
_name = 'crm.team'
|
||||
@@ -90,7 +91,7 @@ class Team(models.Model):
|
||||
def get_alias_values(self):
|
||||
has_group_use_lead = self.env.user.has_group('crm.group_use_lead')
|
||||
values = super(Team, self).get_alias_values()
|
||||
values['alias_defaults'] = defaults = safe_eval(self.alias_defaults or "{}")
|
||||
values['alias_defaults'] = defaults = ast.literal_eval(self.alias_defaults or "{}")
|
||||
defaults['type'] = 'lead' if has_group_use_lead and self.use_leads else 'opportunity'
|
||||
defaults['team_id'] = self.id
|
||||
return values
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
import ast
|
||||
import itertools
|
||||
import logging
|
||||
from datetime import date, timedelta
|
||||
@@ -8,7 +9,6 @@ from dateutil.relativedelta import relativedelta, MO
|
||||
|
||||
from odoo import api, models, fields, _, exceptions
|
||||
from odoo.tools import ustr
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -283,8 +283,7 @@ class Challenge(models.Model):
|
||||
return True
|
||||
|
||||
def _get_challenger_users(self, domain):
|
||||
# FIXME: literal_eval?
|
||||
user_domain = safe_eval(domain)
|
||||
user_domain = ast.literal_eval(domain)
|
||||
return self.env['res.users'].search(user_domain)
|
||||
|
||||
def _recompute_challenge_users(self):
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import ast
|
||||
import logging
|
||||
import time
|
||||
from datetime import date, datetime, timedelta
|
||||
@@ -292,7 +293,7 @@ class Goal(models.Model):
|
||||
field_date_name = definition.field_date_id.name
|
||||
if definition.computation_mode == 'count' and definition.batch_mode:
|
||||
# batch mode, trying to do as much as possible in one request
|
||||
general_domain = safe_eval(definition.domain)
|
||||
general_domain = ast.literal_eval(definition.domain)
|
||||
field_name = definition.batch_distinctive_field.name
|
||||
subqueries = {}
|
||||
for goal in goals:
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
import ast
|
||||
import logging
|
||||
import json
|
||||
import re
|
||||
@@ -9,7 +10,6 @@ import werkzeug.urls
|
||||
|
||||
from odoo import api, fields, models
|
||||
from odoo.exceptions import RedirectWarning, UserError
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
from odoo.tools.translate import _
|
||||
|
||||
from odoo.addons.google_account.models.google_service import GOOGLE_TOKEN_ENDPOINT, TIMEOUT
|
||||
@@ -165,8 +165,8 @@ class GoogleDrive(models.Model):
|
||||
if config.filter_id.user_id and config.filter_id.user_id.id != self.env.user.id:
|
||||
#Private
|
||||
continue
|
||||
domain = [('id', 'in', [res_id])] + safe_eval(config.filter_id.domain)
|
||||
additionnal_context = safe_eval(config.filter_id.context)
|
||||
domain = [('id', 'in', [res_id])] + ast.literal_eval(config.filter_id.domain)
|
||||
additionnal_context = ast.literal_eval(config.filter_id.context)
|
||||
google_doc_configs = self.env[config.filter_id.model_id].with_context(**additionnal_context).search(domain)
|
||||
if google_doc_configs:
|
||||
config_values.append({'id': config.id, 'name': config.name})
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import ast
|
||||
import logging
|
||||
import re
|
||||
|
||||
from odoo import _, api, fields, models
|
||||
from odoo.exceptions import ValidationError
|
||||
from odoo.tools import remove_accents
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -82,7 +82,7 @@ class Alias(models.Model):
|
||||
def _check_alias_defaults(self):
|
||||
for alias in self:
|
||||
try:
|
||||
dict(safe_eval(alias.alias_defaults))
|
||||
dict(ast.literal_eval(alias.alias_defaults))
|
||||
except Exception:
|
||||
raise ValidationError(_('Invalid expression, it must be a literal python dictionary definition e.g. "{\'field\': \'value\'}"'))
|
||||
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import ast
|
||||
import base64
|
||||
import datetime
|
||||
import logging
|
||||
@@ -14,7 +15,6 @@ from collections import defaultdict
|
||||
from odoo import _, api, fields, models
|
||||
from odoo import tools
|
||||
from odoo.addons.base.models.ir_mail_server import MailDeliveryException
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -319,7 +319,7 @@ class MailMail(models.Model):
|
||||
headers['Return-Path'] = '%s+%d@%s' % (bounce_alias, mail.id, catchall_domain)
|
||||
if mail.headers:
|
||||
try:
|
||||
headers.update(safe_eval(mail.headers))
|
||||
headers.update(ast.literal_eval(mail.headers))
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import ast
|
||||
import base64
|
||||
import datetime
|
||||
import dateutil
|
||||
@@ -31,7 +32,6 @@ from odoo.osv import expression
|
||||
|
||||
from odoo.tools import pycompat, ustr
|
||||
from odoo.tools.misc import clean_context, split_every
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -416,7 +416,7 @@ class MailThread(models.AbstractModel):
|
||||
doc = etree.XML(res['arch'])
|
||||
for node in doc.xpath("//field[@name='message_ids']"):
|
||||
# the 'Log a note' button is employee only
|
||||
options = safe_eval(node.get('options', '{}'))
|
||||
options = ast.literal_eval(node.get('options', '{}'))
|
||||
is_employee = self.env.user.has_group('base.group_user')
|
||||
options['display_log_button'] = is_employee
|
||||
# save options on the node
|
||||
@@ -1001,7 +1001,7 @@ class MailThread(models.AbstractModel):
|
||||
routes = []
|
||||
for alias in dest_aliases:
|
||||
user_id = self._mail_find_user_for_gateway(email_from, alias=alias).id or self._uid
|
||||
route = (alias.alias_model_id.model, alias.alias_force_thread_id, safe_eval(alias.alias_defaults), user_id, alias)
|
||||
route = (alias.alias_model_id.model, alias.alias_force_thread_id, ast.literal_eval(alias.alias_defaults), user_id, alias)
|
||||
route = self._routing_check_route(message, message_dict, route, raise_exception=True)
|
||||
if route:
|
||||
_logger.info(
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import ast
|
||||
import base64
|
||||
import re
|
||||
|
||||
from odoo import _, api, fields, models, tools
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
from odoo.exceptions import UserError
|
||||
|
||||
|
||||
@@ -215,7 +215,7 @@ class MailComposer(models.TransientModel):
|
||||
ActiveModel = ActiveModel.with_context(mail_notify_force_send=False, mail_create_nosubscribe=True)
|
||||
# wizard works in batch mode: [res_id] or active_ids or active_domain
|
||||
if mass_mode and wizard.use_active_domain and wizard.model:
|
||||
res_ids = self.env[wizard.model].search(safe_eval(wizard.active_domain)).ids
|
||||
res_ids = self.env[wizard.model].search(ast.literal_eval(wizard.active_domain)).ids
|
||||
elif mass_mode and wizard.model and self._context.get('active_ids'):
|
||||
res_ids = self._context['active_ids']
|
||||
else:
|
||||
|
||||
@@ -15,7 +15,6 @@ from datetime import datetime
|
||||
from odoo import api, fields, models, tools, _, SUPERUSER_ID
|
||||
from odoo.exceptions import UserError
|
||||
from odoo.osv import expression
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import ast
|
||||
from datetime import timedelta
|
||||
|
||||
from odoo import api, fields, models, tools, SUPERUSER_ID, _
|
||||
from odoo.exceptions import UserError, AccessError, ValidationError
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
from odoo.tools.misc import format_date
|
||||
|
||||
|
||||
@@ -406,7 +406,7 @@ class Project(models.Model):
|
||||
}
|
||||
action = self.env['ir.actions.act_window'].for_xml_id('project', 'rating_rating_action_view_project_rating')
|
||||
action['name'] = _('Ratings of %s') % (self.name,)
|
||||
action_context = safe_eval(action['context']) if action['context'] else {}
|
||||
action_context = ast.literal_eval(action['context']) if action['context'] else {}
|
||||
action_context.update(self._context)
|
||||
action_context['search_default_parent_res_name'] = self.name
|
||||
action_context.pop('group_by', None)
|
||||
|
||||
@@ -3,7 +3,8 @@
|
||||
|
||||
from odoo import api, fields, models, _
|
||||
from odoo.exceptions import UserError, ValidationError
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
import ast
|
||||
|
||||
|
||||
class SaleCouponProgram(models.Model):
|
||||
@@ -285,7 +286,7 @@ class SaleCouponProgram(models.Model):
|
||||
|
||||
def _is_valid_partner(self, partner):
|
||||
if self.rule_partners_domain:
|
||||
domain = safe_eval(self.rule_partners_domain) + [('id', '=', partner.id)]
|
||||
domain = ast.literal_eval(self.rule_partners_domain) + [('id', '=', partner.id)]
|
||||
return bool(self.env['res.partner'].search_count(domain))
|
||||
else:
|
||||
return True
|
||||
@@ -293,13 +294,13 @@ class SaleCouponProgram(models.Model):
|
||||
def _is_valid_product(self, product):
|
||||
# NOTE: if you override this method, think of also overriding _get_valid_products
|
||||
if self.rule_products_domain:
|
||||
domain = safe_eval(self.rule_products_domain) + [('id', '=', product.id)]
|
||||
domain = ast.literal_eval(self.rule_products_domain) + [('id', '=', product.id)]
|
||||
return bool(self.env['product.product'].search_count(domain))
|
||||
else:
|
||||
return True
|
||||
|
||||
def _get_valid_products(self, products):
|
||||
if self.rule_products_domain:
|
||||
domain = safe_eval(self.rule_products_domain) + [('id', 'in', products.ids)]
|
||||
domain = ast.literal_eval(self.rule_products_domain) + [('id', 'in', products.ids)]
|
||||
return self.env['product.product'].search(domain)
|
||||
return products
|
||||
|
||||
@@ -3,7 +3,6 @@
|
||||
|
||||
from odoo import api, fields, models, _
|
||||
from odoo.exceptions import ValidationError
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
|
||||
class SaleCouponRule(models.Model):
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
from odoo import api, fields, models
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
import ast
|
||||
|
||||
|
||||
class SaleCouponGenerate(models.TransientModel):
|
||||
@@ -27,7 +28,7 @@ class SaleCouponGenerate(models.TransientModel):
|
||||
self.env['sale.coupon'].create(vals)
|
||||
|
||||
if self.generation_type == 'nbr_customer' and self.partners_domain:
|
||||
for partner in self.env['res.partner'].search(safe_eval(self.partners_domain)):
|
||||
for partner in self.env['res.partner'].search(ast.literal_eval(self.partners_domain)):
|
||||
vals.update({'partner_id': partner.id})
|
||||
coupon = self.env['sale.coupon'].create(vals)
|
||||
subject = '%s, a coupon has been generated for you' % (partner.name)
|
||||
|
||||
@@ -6,7 +6,6 @@ from ast import literal_eval
|
||||
from odoo import api, fields, models, _
|
||||
from odoo.addons.phone_validation.tools import phone_validation
|
||||
from odoo.exceptions import UserError
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
|
||||
class SendSMS(models.TransientModel):
|
||||
@@ -87,7 +86,7 @@ class SendSMS(models.TransientModel):
|
||||
def _compute_recipients_count(self):
|
||||
self.res_ids_count = len(literal_eval(self.res_ids)) if self.res_ids else 0
|
||||
if self.res_model:
|
||||
self.active_domain_count = self.env[self.res_model].search_count(safe_eval(self.active_domain or '[]'))
|
||||
self.active_domain_count = self.env[self.res_model].search_count(literal_eval(self.active_domain or '[]'))
|
||||
else:
|
||||
self.active_domain_count = 0
|
||||
|
||||
@@ -308,7 +307,7 @@ class SendSMS(models.TransientModel):
|
||||
if not self.res_model:
|
||||
return None
|
||||
if self.use_active_domain:
|
||||
active_domain = safe_eval(self.active_domain or '[]')
|
||||
active_domain = literal_eval(self.active_domain or '[]')
|
||||
records = self.env[self.res_model].search(active_domain)
|
||||
elif self.res_id:
|
||||
records = self.env[self.res_model].browse(self.res_id)
|
||||
|
||||
@@ -10,7 +10,7 @@ import babel.dates
|
||||
from lxml import etree
|
||||
import math
|
||||
|
||||
from odoo.tools import html_escape as escape, posix_to_ldml, safe_eval, float_utils, format_date, format_duration, pycompat
|
||||
from odoo.tools import html_escape as escape, posix_to_ldml, float_utils, format_date, format_duration, pycompat
|
||||
from odoo.tools.misc import get_lang
|
||||
|
||||
import logging
|
||||
|
||||
@@ -9,7 +9,6 @@ from odoo import api, fields, models, tools, _
|
||||
from odoo.exceptions import ValidationError
|
||||
from odoo.http import request
|
||||
from odoo.modules import get_module_resource
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
|
||||
MENU_ITEM_SEPARATOR = "/"
|
||||
NUMBER_PARENS = re.compile(r"\(([0-9]+)\)")
|
||||
|
||||
@@ -63,7 +63,8 @@ def transfer_node_to_modifiers(node, modifiers, context=None, current_node_path=
|
||||
# Need the context to evaluate the invisible attribute on tree views.
|
||||
# For non-tree views, the context shouldn't be given.
|
||||
if node.get('attrs'):
|
||||
modifiers.update(safe_eval(node.get('attrs')))
|
||||
attrs = node.get('attrs').strip()
|
||||
modifiers.update(ast.literal_eval(attrs))
|
||||
|
||||
if node.get('states'):
|
||||
if 'invisible' in modifiers and isinstance(modifiers['invisible'], list):
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import ast
|
||||
import json
|
||||
import locale
|
||||
import logging
|
||||
@@ -8,7 +9,6 @@ import re
|
||||
from operator import itemgetter
|
||||
|
||||
from odoo import api, fields, models, tools, _
|
||||
from odoo.tools.safe_eval import safe_eval
|
||||
from odoo.exceptions import UserError, ValidationError
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
@@ -275,7 +275,7 @@ class Lang(models.Model):
|
||||
# floats and decimal ints need special action!
|
||||
if grouping:
|
||||
lang_grouping, thousands_sep, decimal_point = self._data_get(monetary)
|
||||
eval_lang_grouping = safe_eval(lang_grouping)
|
||||
eval_lang_grouping = ast.literal_eval(lang_grouping)
|
||||
|
||||
if percent[-1] in 'eEfFgG':
|
||||
parts = formatted.split('.')
|
||||
|
||||
@@ -57,7 +57,6 @@ from .tools import frozendict, lazy_classproperty, lazy_property, ormcache, \
|
||||
from .tools.config import config
|
||||
from .tools.func import frame_codeinfo
|
||||
from .tools.misc import CountingStream, clean_context, DEFAULT_SERVER_DATETIME_FORMAT, DEFAULT_SERVER_DATE_FORMAT, get_lang
|
||||
from .tools.safe_eval import safe_eval
|
||||
from .tools.translate import _
|
||||
from .tools import date_utils
|
||||
|
||||
|
||||
Reference in New Issue
Block a user