diff --git a/addons/hr_contract/data/hr_contract_data.xml b/addons/hr_contract/data/hr_contract_data.xml index 56f6aabceb9..43ccb242c64 100644 --- a/addons/hr_contract/data/hr_contract_data.xml +++ b/addons/hr_contract/data/hr_contract_data.xml @@ -50,7 +50,7 @@ ir.actions.server code - model.update_state() + model.with_context(from_cron=True).update_state() 1 days -1 diff --git a/addons/hr_contract/models/hr_contract.py b/addons/hr_contract/models/hr_contract.py index cc5cc34f434..9bf7b297f40 100644 --- a/addons/hr_contract/models/hr_contract.py +++ b/addons/hr_contract/models/hr_contract.py @@ -1,6 +1,8 @@ # -*- coding: utf-8 -*- # Part of Odoo. See LICENSE file for full copyright and licensing details. +import threading + from datetime import date from dateutil.relativedelta import relativedelta @@ -9,6 +11,10 @@ from odoo.exceptions import ValidationError from odoo.osv import expression +import logging +_logger = logging.getLogger(__name__) + + class Contract(models.Model): _name = 'hr.contract' _description = 'Contract' @@ -149,6 +155,7 @@ class Contract(models.Model): @api.model def update_state(self): + from_cron = 'from_cron' in self.env.context contracts = self.search([ ('state', '=', 'open'), ('kanban_state', '!=', 'blocked'), '|', @@ -172,20 +179,23 @@ class Contract(models.Model): ) ) - contracts.write({'kanban_state': 'blocked'}) + if contracts: + contracts._safe_write_for_cron({'kanban_state': 'blocked'}, from_cron) - self.search([ + contracts_to_close = self.search([ ('state', '=', 'open'), '|', ('date_end', '<=', fields.Date.to_string(date.today() + relativedelta(days=1))), ('visa_expire', '<=', fields.Date.to_string(date.today() + relativedelta(days=1))), - ]).write({ - 'state': 'close' - }) + ]) - self.search([('state', '=', 'draft'), ('kanban_state', '=', 'done'), ('date_start', '<=', fields.Date.to_string(date.today())),]).write({ - 'state': 'open' - }) + if contracts_to_close: + contracts_to_close._safe_write_for_cron({'state': 'close'}, from_cron) + + contracts_to_open = self.search([('state', '=', 'draft'), ('kanban_state', '=', 'done'), ('date_start', '<=', fields.Date.to_string(date.today())),]) + + if contracts_to_open: + contracts_to_open._safe_write_for_cron({'state': 'open'}, from_cron) contract_ids = self.search([('date_end', '=', False), ('state', '=', 'close'), ('employee_id', '!=', False)]) # Ensure all closed contract followed by a new contract have a end date. @@ -197,17 +207,32 @@ class Contract(models.Model): ('date_start', '>', contract.date_start) ], order="date_start asc", limit=1) if next_contract: - contract.date_end = next_contract.date_start - relativedelta(days=1) + contract._safe_write_for_cron({'date_end': next_contract.date_start - relativedelta(days=1)}, from_cron) continue next_contract = self.search([ ('employee_id', '=', contract.employee_id.id), ('date_start', '>', contract.date_start) ], order="date_start asc", limit=1) if next_contract: - contract.date_end = next_contract.date_start - relativedelta(days=1) + contract._safe_write_for_cron({'date_end': next_contract.date_start - relativedelta(days=1)}, from_cron) return True + def _safe_write_for_cron(self, vals, from_cron=False): + if from_cron: + auto_commit = not getattr(threading.current_thread(), 'testing', False) + for contract in self: + try: + with self.env.cr.savepoint(): + contract.write(vals) + except ValidationError as e: + _logger.warning(e) + else: + if auto_commit: + self.env.cr.commit() + else: + self.write(vals) + def _assign_open_contract(self): for contract in self: contract.employee_id.sudo().write({'contract_id': contract.id})