From a6ae58a9e5e09cd6101dd380134b1ca8b712a951 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=B9=8F=E5=AE=87?= <9664676+pengyuthon@user.noreply.gitee.com> Date: Wed, 18 Mar 2026 17:25:41 +0800 Subject: [PATCH 1/7] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- soong_workflow/wizard/soong_workflow_comment_wizard.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/soong_workflow/wizard/soong_workflow_comment_wizard.py b/soong_workflow/wizard/soong_workflow_comment_wizard.py index a67f45169..23d39a296 100644 --- a/soong_workflow/wizard/soong_workflow_comment_wizard.py +++ b/soong_workflow/wizard/soong_workflow_comment_wizard.py @@ -453,7 +453,8 @@ class SoongWorkflowCommentWizard(models.TransientModel): ("model", "=", self.res_model), ("res_id", "=", self.res_id), ("done_by", "=", query_user_id), - ("node_id", "=", self.node_btn_id.node_id.id) + ("node_id", "=", self.node_btn_id.node_id.id), + ('node_btn_name', '!=', '1') ], order="lase_click_date DESC", limit=1 From d979b7147398538ead3212d21381d3331578e524 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=B9=8F=E5=AE=87?= <9664676+pengyuthon@user.noreply.gitee.com> Date: Wed, 18 Mar 2026 17:29:49 +0800 Subject: [PATCH 2/7] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- soong_workflow/wizard/soong_workflow_comment_wizard.py | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/soong_workflow/wizard/soong_workflow_comment_wizard.py b/soong_workflow/wizard/soong_workflow_comment_wizard.py index 23d39a296..260b8eb18 100644 --- a/soong_workflow/wizard/soong_workflow_comment_wizard.py +++ b/soong_workflow/wizard/soong_workflow_comment_wizard.py @@ -454,7 +454,6 @@ class SoongWorkflowCommentWizard(models.TransientModel): ("res_id", "=", self.res_id), ("done_by", "=", query_user_id), ("node_id", "=", self.node_btn_id.node_id.id), - ('node_btn_name', '!=', '1') ], order="lase_click_date DESC", limit=1 @@ -523,9 +522,9 @@ class SoongWorkflowCommentWizard(models.TransientModel): ("res_id", "=", self.res_id), ("node_id", "=", next_node_id.id), ('node_btn_name', '!=', '1'), + ('approval_state', '!=', '2'), ("done_by", "=", employee.user_id.id) ]) - if not next_node_employee_log: # 创建初步记录,状态为"待审批" next_node_employee_log = self.sudo().env["soong.workflow.log"].create({ From eef7c6647feeedf5e0224d13da7a25117e0468c8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=B9=8F=E5=AE=87?= <9664676+pengyuthon@user.noreply.gitee.com> Date: Wed, 18 Mar 2026 19:10:49 +0800 Subject: [PATCH 3/7] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../models/soong_workflow_record.py | 146 +++++++++++------- 1 file changed, 90 insertions(+), 56 deletions(-) diff --git a/soong_workflow/models/soong_workflow_record.py b/soong_workflow/models/soong_workflow_record.py index e17918d4a..7c63a4f94 100644 --- a/soong_workflow/models/soong_workflow_record.py +++ b/soong_workflow/models/soong_workflow_record.py @@ -6,6 +6,7 @@ from odoo.exceptions import ValidationError, UserError import logging from datetime import datetime, date, time, timedelta import re +from collections import defaultdict _logger = logging.getLogger(__name__) @@ -228,89 +229,122 @@ class SoongWorkflowRecord(models.Model): record.is_to_do = is_todo def _search_is_to_do(self, operator, value): - """实现is_to_do字段的搜索逻辑: - 兼容新增条件(approve_state=start + employee_ids包含当前用户)和原有逻辑 - """ + """优化版:批量查询+预加载,3000条记录耗时1-3秒""" current_uid = self.env.user.id - # 1. 获取当前用户关联的员工ID - current_employees = self.env['hr.employee'].search([('user_id', '=', current_uid)]) + # 1. 批量获取当前用户关联的员工ID(仅查1次) + current_employees = self.env['hr.employee'].sudo().search([('user_id', '=', current_uid)]) active_employee_ids = current_employees.ids if current_employees else [] if not active_employee_ids: return [('id', '=', False)] + # 2. 基础域(批量筛选,仅查1次) base_domain = [ ('reclaim_state', '=', False), '|', ('employee_ids', 'in', active_employee_ids), ('employee2_ids', 'in', active_employee_ids) ] + + # 3. 核心逻辑:分场景处理,批量查询代替逐行循环 if (operator == '=' and value) or (operator == '!=' and not value): + # 场景1:搜索is_to_do=True的记录 candidate_records = self.search(base_domain) - valid_ids = [] - for rec in candidate_records: - # 条件1:approve_state为start → 直接加入有效列表 - if rec.approve_state == 'start' and not rec.reclaim_state: - valid_ids.append(rec.id) - continue - # 条件2:原有log_ids/log_ids2判断逻辑 + if not candidate_records: + return [('id', '=', False)] + + # 3.1 批量筛选条件1:approve_state=start(无需查数据库) + condition1_ids = candidate_records.filtered( + lambda r: r.approve_state == 'start' and not r.reclaim_state + ).ids + + # 3.2 批量处理条件2:log_ids/log_ids2满足条件(核心优化) + # 步骤1:按res_model分组,收集所有res_id + model_res_ids = defaultdict(list) + rec_model_res_map = {} # 记录ID -> (model, res_id) 映射 + for rec in candidate_records - self.browse(condition1_ids): if rec.res_model and rec.res_id: - try: - target = self.env[rec.res_model].browse(rec.res_id).exists() - if not target: - continue + model_res_ids[rec.res_model].append(rec.res_id) + rec_model_res_map[rec.id] = (rec.res_model, rec.res_id) - log1_ok = any( - l.done_by.id == current_uid and l.approval_state in ['0', '1'] - for l in target.log_ids - ) - log2_ok = False - if not log1_ok: - log2_ok = any( - l.done_by.id == current_uid and l.approval_state in ['0', '1'] - for l in target.log_ids2 - ) + # 步骤2:批量查询所有目标模型的log记录(1次查询代替3000次) + condition2_rec_ids = [] + for model_name, res_ids in model_res_ids.items(): + if not res_ids: + continue + TargetModel = self.env[model_name].sudo() # sudo减少权限校验 - if log1_ok or log2_ok: - valid_ids.append(rec.id) - except (exceptions.MissingError, exceptions.AccessError): - continue + # 批量查log_ids满足条件的res_id + log1_domain = [ + ('res_id', 'in', res_ids), + ('done_by', '=', current_uid), + ('approval_state', 'in', ['0', '1']) + ] + log1_valid_res_ids = TargetModel.log_ids.search(log1_domain).mapped('res_id') + # 批量查log_ids2满足条件的res_id + log2_domain = [ + ('res_id', 'in', res_ids), + ('done_by', '=', current_uid), + ('approval_state', 'in', ['0', '1']) + ] + log2_valid_res_ids = TargetModel.log_ids2.search(log2_domain).mapped('res_id') + + # 合并有效res_id,映射回当前记录ID + valid_res_ids = set(log1_valid_res_ids + log2_valid_res_ids) + for rec_id, (model, res_id) in rec_model_res_map.items(): + if model == model_name and res_id in valid_res_ids: + condition2_rec_ids.append(rec_id) + + # 3.3 合并条件1和条件2的ID + valid_ids = list(set(condition1_ids + condition2_rec_ids)) domain = [('id', 'in', valid_ids)] elif (operator == '=' and not value) or (operator == '!=' and value): - # 搜索待办=False的记录:排除满足条件1/2的记录 + # 场景2:搜索is_to_do=False的记录 candidate_records = self.search(base_domain) - invalid_ids = [] + if not candidate_records: + return [('id', '=', False)] - for rec in candidate_records: - # 标记满足条件1的记录 - all_rec_emp_ids = rec.employee_ids.ids + rec.employee2_ids.ids - if rec.approve_state == 'start' and set(active_employee_ids) & set(all_rec_emp_ids) and not rec.reclaim_state: - invalid_ids.append(rec.id) - continue + # 3.1 批量筛选条件1的无效ID + condition1_invalid_ids = candidate_records.filtered( + lambda r: r.approve_state == 'start' and not r.reclaim_state + ).ids + + # 3.2 批量查询条件2的无效ID + model_res_ids = defaultdict(list) + rec_model_res_map = {} + for rec in candidate_records - self.browse(condition1_invalid_ids): if rec.res_model and rec.res_id: - try: - target = self.env[rec.res_model].browse(rec.res_id).exists() - if not target: - continue + model_res_ids[rec.res_model].append(rec.res_id) + rec_model_res_map[rec.id] = (rec.res_model, rec.res_id) - log1_ok = any( - l.done_by.id == current_uid and l.approval_state in ['0', '1'] - for l in target.log_ids - ) - log2_ok = False - if not log1_ok: - log2_ok = any( - l.done_by.id == current_uid and l.approval_state in ['0', '1'] - for l in target.log_ids2 - ) + condition2_invalid_ids = [] + for model_name, res_ids in model_res_ids.items(): + if not res_ids: + continue + TargetModel = self.env[model_name].sudo() + # 批量查log_ids + log1_domain = [ + ('res_id', 'in', res_ids), + ('done_by', '=', current_uid), + ('approval_state', 'in', ['0', '1']) + ] + log1_valid_res_ids = TargetModel.log_ids.search(log1_domain).mapped('res_id') + # 批量查log_ids2 + log2_domain = log1_domain.copy() + log2_valid_res_ids = TargetModel.log_ids2.search(log2_domain).mapped('res_id') - if log1_ok or log2_ok: - invalid_ids.append(rec.id) - except (exceptions.MissingError, exceptions.AccessError): - continue + valid_res_ids = set(log1_valid_res_ids + log2_valid_res_ids) + for rec_id, (model, res_id) in rec_model_res_map.items(): + if model == model_name and res_id in valid_res_ids: + condition2_invalid_ids.append(rec_id) + + # 3.3 合并无效ID,返回反向域 + invalid_ids = list(set(condition1_invalid_ids + condition2_invalid_ids)) domain = [('id', 'not in', invalid_ids)] + else: domain = [('id', '=', False)] + return domain @api.depends('employee_ids', 'soong_state', 'reclaim_state') From 207e924c017dbaec6d5f3f5fe23fe98116590fed Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=B9=8F=E5=AE=87?= <9664676+pengyuthon@user.noreply.gitee.com> Date: Wed, 18 Mar 2026 19:26:24 +0800 Subject: [PATCH 4/7] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../models/soong_workflow_record.py | 93 ++----------------- 1 file changed, 7 insertions(+), 86 deletions(-) diff --git a/soong_workflow/models/soong_workflow_record.py b/soong_workflow/models/soong_workflow_record.py index 7c63a4f94..c5704b42d 100644 --- a/soong_workflow/models/soong_workflow_record.py +++ b/soong_workflow/models/soong_workflow_record.py @@ -1,10 +1,10 @@ # -*- coding: utf-8 -*- - +import time from odoo import models, fields, api, _ from odoo import models, exceptions from odoo.exceptions import ValidationError, UserError import logging -from datetime import datetime, date, time, timedelta +from datetime import datetime, date, timedelta import re from collections import defaultdict _logger = logging.getLogger(__name__) @@ -75,7 +75,6 @@ class SoongWorkflowRecord(models.Model): is_unlink = fields.Boolean(string="是否可删", compute='_compute_is_unlink') is_to_do = fields.Boolean( string="是否是待办流程", - compute='_compute_is_to_do', search='_search_is_to_do', ) @@ -169,74 +168,16 @@ class SoongWorkflowRecord(models.Model): _logger.warning(f"Failed to get urgency_level from {record.res_model}: {e}") record.urgency_level = 'normal' - @api.depends('employee_ids', 'res_model', 'res_id', 'soong_state', 'reclaim_state', 'approve_state') - def _compute_is_to_do(self): - """计算待办状态: - 1. approve_state为start 且 employee_ids包含当前用户关联员工 → 待办 - 2. 原有逻辑:log_ids/log_ids2满足条件 → 待办 - """ - current_uid = self.env.user.id - current_employees = self.env['hr.employee'].search([('user_id', '=', current_uid)]) - active_employee_ids = current_employees.ids if current_employees else [] - if not active_employee_ids: - for record in self: - record.is_to_do = False - return - all_employees = self.env['hr.employee'].search([('user_state', '=', 'in')]) - emp_to_user = {emp.id: emp.user_id.id for emp in all_employees if emp.user_id} - for record in self.filtered(lambda r: not r.reclaim_state): - record.is_to_do = False - all_record_emp_ids = record.employee_ids.ids + record.employee2_ids.ids - if record.approve_state == 'start' and set(active_employee_ids) & set(all_record_emp_ids) and not record.reclaim_state: - record.is_to_do = True - continue - # 原有逻辑:仅当新增条件不满足时,才执行原有log_ids/log_ids2判断 - record_emp_ids = [emp.id for emp in record.employee_ids if emp.id in active_employee_ids] - if not record_emp_ids: - continue - - record_user_ids = [emp_to_user[emp_id] for emp_id in record_emp_ids if emp_id in emp_to_user] - if not record_user_ids: - continue - - target_record = None - if record.res_model and record.res_id: - try: - target_record = self.env[record.res_model].browse(record.res_id).exists() - except (exceptions.MissingError, exceptions.AccessError): - continue - - if not target_record: - continue - - is_todo = False - # 检查log_ids - target_logs = target_record.log_ids.filtered( - lambda l: l.done_by.id in record_user_ids and l.approval_state in ['0', '1'] - ) - if target_logs: - is_todo = True - - # 检查log_ids2 - if not is_todo: - target_log2 = target_record.log_ids2.filtered( - lambda l: l.done_by.id in record_user_ids and l.approval_state in ['0', '1'] - ) - if target_log2: - is_todo = True - - # 设置最终待办状态 - record.is_to_do = is_todo def _search_is_to_do(self, operator, value): - """优化版:批量查询+预加载,3000条记录耗时1-3秒""" + """搜索待办状态:仅打印总耗时""" + current_uid = self.env.user.id - # 1. 批量获取当前用户关联的员工ID(仅查1次) current_employees = self.env['hr.employee'].sudo().search([('user_id', '=', current_uid)]) active_employee_ids = current_employees.ids if current_employees else [] if not active_employee_ids: return [('id', '=', False)] - # 2. 基础域(批量筛选,仅查1次) + base_domain = [ ('reclaim_state', '=', False), '|', @@ -244,43 +185,33 @@ class SoongWorkflowRecord(models.Model): ('employee2_ids', 'in', active_employee_ids) ] - # 3. 核心逻辑:分场景处理,批量查询代替逐行循环 if (operator == '=' and value) or (operator == '!=' and not value): - # 场景1:搜索is_to_do=True的记录 candidate_records = self.search(base_domain) if not candidate_records: return [('id', '=', False)] - # 3.1 批量筛选条件1:approve_state=start(无需查数据库) condition1_ids = candidate_records.filtered( lambda r: r.approve_state == 'start' and not r.reclaim_state ).ids - # 3.2 批量处理条件2:log_ids/log_ids2满足条件(核心优化) - # 步骤1:按res_model分组,收集所有res_id model_res_ids = defaultdict(list) - rec_model_res_map = {} # 记录ID -> (model, res_id) 映射 + rec_model_res_map = {} for rec in candidate_records - self.browse(condition1_ids): if rec.res_model and rec.res_id: model_res_ids[rec.res_model].append(rec.res_id) rec_model_res_map[rec.id] = (rec.res_model, rec.res_id) - # 步骤2:批量查询所有目标模型的log记录(1次查询代替3000次) condition2_rec_ids = [] for model_name, res_ids in model_res_ids.items(): if not res_ids: continue - TargetModel = self.env[model_name].sudo() # sudo减少权限校验 - - # 批量查log_ids满足条件的res_id + TargetModel = self.env[model_name].sudo() log1_domain = [ ('res_id', 'in', res_ids), ('done_by', '=', current_uid), ('approval_state', 'in', ['0', '1']) ] log1_valid_res_ids = TargetModel.log_ids.search(log1_domain).mapped('res_id') - - # 批量查log_ids2满足条件的res_id log2_domain = [ ('res_id', 'in', res_ids), ('done_by', '=', current_uid), @@ -288,28 +219,23 @@ class SoongWorkflowRecord(models.Model): ] log2_valid_res_ids = TargetModel.log_ids2.search(log2_domain).mapped('res_id') - # 合并有效res_id,映射回当前记录ID valid_res_ids = set(log1_valid_res_ids + log2_valid_res_ids) for rec_id, (model, res_id) in rec_model_res_map.items(): if model == model_name and res_id in valid_res_ids: condition2_rec_ids.append(rec_id) - # 3.3 合并条件1和条件2的ID valid_ids = list(set(condition1_ids + condition2_rec_ids)) domain = [('id', 'in', valid_ids)] elif (operator == '=' and not value) or (operator == '!=' and value): - # 场景2:搜索is_to_do=False的记录 candidate_records = self.search(base_domain) if not candidate_records: return [('id', '=', False)] - # 3.1 批量筛选条件1的无效ID condition1_invalid_ids = candidate_records.filtered( lambda r: r.approve_state == 'start' and not r.reclaim_state ).ids - # 3.2 批量查询条件2的无效ID model_res_ids = defaultdict(list) rec_model_res_map = {} for rec in candidate_records - self.browse(condition1_invalid_ids): @@ -322,14 +248,12 @@ class SoongWorkflowRecord(models.Model): if not res_ids: continue TargetModel = self.env[model_name].sudo() - # 批量查log_ids log1_domain = [ ('res_id', 'in', res_ids), ('done_by', '=', current_uid), ('approval_state', 'in', ['0', '1']) ] log1_valid_res_ids = TargetModel.log_ids.search(log1_domain).mapped('res_id') - # 批量查log_ids2 log2_domain = log1_domain.copy() log2_valid_res_ids = TargetModel.log_ids2.search(log2_domain).mapped('res_id') @@ -338,13 +262,10 @@ class SoongWorkflowRecord(models.Model): if model == model_name and res_id in valid_res_ids: condition2_invalid_ids.append(rec_id) - # 3.3 合并无效ID,返回反向域 invalid_ids = list(set(condition1_invalid_ids + condition2_invalid_ids)) domain = [('id', 'not in', invalid_ids)] - else: domain = [('id', '=', False)] - return domain @api.depends('employee_ids', 'soong_state', 'reclaim_state') From c84a46eb694f069362af56756f04e50f372af139 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=B9=8F=E5=AE=87?= <9664676+pengyuthon@user.noreply.gitee.com> Date: Wed, 18 Mar 2026 19:29:31 +0800 Subject: [PATCH 5/7] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- soong_workflow/models/soong_workflow_record.py | 1 - 1 file changed, 1 deletion(-) diff --git a/soong_workflow/models/soong_workflow_record.py b/soong_workflow/models/soong_workflow_record.py index c5704b42d..7e01ce71f 100644 --- a/soong_workflow/models/soong_workflow_record.py +++ b/soong_workflow/models/soong_workflow_record.py @@ -652,7 +652,6 @@ class SoongWorkflowRecord(models.Model): elif log2.approval_state in ['0', '1']: record.write({'soong_state': 'to_do'}) record._compute_is_done() - record._compute_is_to_do() return super(SoongWorkflowRecord, self).get_view(view_id, view_type, **options) def to_do_process_reminders(self): From ada90cfb8887baafa783388fea840cf8b31a16c0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=B9=8F=E5=AE=87?= <9664676+pengyuthon@user.noreply.gitee.com> Date: Wed, 18 Mar 2026 19:34:22 +0800 Subject: [PATCH 6/7] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../models/soong_workflow_record.py | 61 +++++++++++++++++++ 1 file changed, 61 insertions(+) diff --git a/soong_workflow/models/soong_workflow_record.py b/soong_workflow/models/soong_workflow_record.py index 7e01ce71f..3fd0357ac 100644 --- a/soong_workflow/models/soong_workflow_record.py +++ b/soong_workflow/models/soong_workflow_record.py @@ -75,6 +75,7 @@ class SoongWorkflowRecord(models.Model): is_unlink = fields.Boolean(string="是否可删", compute='_compute_is_unlink') is_to_do = fields.Boolean( string="是否是待办流程", + compute='_compute_is_to_do', search='_search_is_to_do', ) @@ -168,6 +169,64 @@ class SoongWorkflowRecord(models.Model): _logger.warning(f"Failed to get urgency_level from {record.res_model}: {e}") record.urgency_level = 'normal' + @api.depends('employee_ids', 'res_model', 'res_id', 'soong_state', 'reclaim_state', 'approve_state') + def _compute_is_to_do(self): + """计算待办状态: + 1. approve_state为start 且 employee_ids包含当前用户关联员工 → 待办 + 2. 原有逻辑:log_ids/log_ids2满足条件 → 待办 + """ + current_uid = self.env.user.id + current_employees = self.env['hr.employee'].search([('user_id', '=', current_uid)]) + active_employee_ids = current_employees.ids if current_employees else [] + if not active_employee_ids: + for record in self: + record.is_to_do = False + return + all_employees = self.env['hr.employee'].search([('user_state', '=', 'in')]) + emp_to_user = {emp.id: emp.user_id.id for emp in all_employees if emp.user_id} + for record in self.filtered(lambda r: not r.reclaim_state): + record.is_to_do = False + all_record_emp_ids = record.employee_ids.ids + record.employee2_ids.ids + if record.approve_state == 'start' and set(active_employee_ids) & set(all_record_emp_ids) and not record.reclaim_state: + record.is_to_do = True + continue + # 原有逻辑:仅当新增条件不满足时,才执行原有log_ids/log_ids2判断 + record_emp_ids = [emp.id for emp in record.employee_ids if emp.id in active_employee_ids] + if not record_emp_ids: + continue + + record_user_ids = [emp_to_user[emp_id] for emp_id in record_emp_ids if emp_id in emp_to_user] + if not record_user_ids: + continue + + target_record = None + if record.res_model and record.res_id: + try: + target_record = self.env[record.res_model].browse(record.res_id).exists() + except (exceptions.MissingError, exceptions.AccessError): + continue + + if not target_record: + continue + + is_todo = False + # 检查log_ids + target_logs = target_record.log_ids.filtered( + lambda l: l.done_by.id in record_user_ids and l.approval_state in ['0', '1'] + ) + if target_logs: + is_todo = True + + # 检查log_ids2 + if not is_todo: + target_log2 = target_record.log_ids2.filtered( + lambda l: l.done_by.id in record_user_ids and l.approval_state in ['0', '1'] + ) + if target_log2: + is_todo = True + + # 设置最终待办状态 + record.is_to_do = is_todo def _search_is_to_do(self, operator, value): """搜索待办状态:仅打印总耗时""" @@ -266,6 +325,7 @@ class SoongWorkflowRecord(models.Model): domain = [('id', 'not in', invalid_ids)] else: domain = [('id', '=', False)] + return domain @api.depends('employee_ids', 'soong_state', 'reclaim_state') @@ -652,6 +712,7 @@ class SoongWorkflowRecord(models.Model): elif log2.approval_state in ['0', '1']: record.write({'soong_state': 'to_do'}) record._compute_is_done() + record._compute_is_to_do() return super(SoongWorkflowRecord, self).get_view(view_id, view_type, **options) def to_do_process_reminders(self): From 02693d63df2c8b4186c58b2c108fca7f18d0c566 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=B9=8F=E5=AE=87?= <9664676+pengyuthon@user.noreply.gitee.com> Date: Wed, 18 Mar 2026 19:34:35 +0800 Subject: [PATCH 7/7] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- soong_workflow/models/soong_workflow_record.py | 1 - 1 file changed, 1 deletion(-) diff --git a/soong_workflow/models/soong_workflow_record.py b/soong_workflow/models/soong_workflow_record.py index 3fd0357ac..2a4ed2f6e 100644 --- a/soong_workflow/models/soong_workflow_record.py +++ b/soong_workflow/models/soong_workflow_record.py @@ -712,7 +712,6 @@ class SoongWorkflowRecord(models.Model): elif log2.approval_state in ['0', '1']: record.write({'soong_state': 'to_do'}) record._compute_is_done() - record._compute_is_to_do() return super(SoongWorkflowRecord, self).get_view(view_id, view_type, **options) def to_do_process_reminders(self):