Odoo新API下:从account.invoice获取销售订单详情及字段关联求助
在Odoo里,发票和销售订单的关联可以通过发票分录行间接打通——每个发票行(account.invoice.line)都自带sale_line_id字段,关联到对应的销售订单行(sale.order.line),而销售订单行又通过order_id关联到销售订单(sale.order)。
你可以用这两种方式获取:
方式一:通过发票行关联查询
如果你需要在业务逻辑里快速获取当前发票对应的所有销售订单,可以写个简单的方法:def get_related_sale_orders(self): self.ensure_one() # 遍历所有发票行,映射到对应的销售订单并去重 sale_order_ids = self.invoice_line_ids.mapped('sale_line_id.order_id') return sale_order_ids用
mapped()方法能高效遍历关联关系,直接拿到去重后的销售订单集合。方式二:直接用内置字段(部分版本支持)
不少Odoo版本的account.invoice模型已经内置了sale_order_ids字段(Many2many关联到sale.order),如果你的环境有这个字段,直接调用就能拿到销售订单详情,不用额外开发。
od_sale_order_name字段并关联销售订单失败的解决方法 你尝试创建的Many2many字段没生效,大概率是这几个原因,我帮你逐个排查:
1. 关联表的匹配问题
你手动指定的sale_order_invoice_rel是Odoo标准关联表吗?不同版本的关联表结构可能有差异,如果你的环境里这个表不存在,字段肯定生成不了。
解决办法:
不用手动指定表名,让Odoo自动生成关联表更稳妥:
saleorder_ids = fields.Many2many('sale.order', string='Sale Order')
Odoo会按照规范自动创建关联表,避免手动指定导致的匹配错误。
2. 模型继承与字段定义位置问题
你有没有正确继承account.invoice模型?自定义模块里新增字段,必须确保继承逻辑正确:
from odoo import models, fields class AccountInvoice(models.Model): _inherit = 'account.invoice' # 新API下必须用_inherit继承原有模型 od_sale_order_name = fields.Char(string='Sale Order Name', compute='_compute_sale_order_name') saleorder_ids = fields.Many2many('sale.order', string='Sale Order') def _compute_sale_order_name(self): for invoice in self: # 可以取第一个订单名称,也可以拼接多个订单名称 if invoice.saleorder_ids: invoice.od_sale_order_name = ', '.join(invoice.saleorder_ids.mapped('name')) else: invoice.od_sale_order_name = False
3. 模块升级与缓存问题
就算字段定义正确,没升级模块的话Odoo不会更新数据库结构。你需要:
- 进入Odoo应用列表,找到你的自定义模块
- 点击升级按钮,确保最新代码同步到数据库
- 清除浏览器缓存,刷新页面后再查看字段是否出现
4. 更高效的替代方案
其实你没必要手动维护Many2many关联,直接通过现有发票行的关联关系计算od_sale_order_name字段更高效:
class AccountInvoice(models.Model): _inherit = 'account.invoice' od_sale_order_name = fields.Char(string='Sale Order Name', compute='_compute_sale_order_name') def _compute_sale_order_name(self): for invoice in self: # 通过发票行关联到销售订单,去重后拼接名称 sale_orders = invoice.invoice_line_ids.mapped('sale_line_id.order_id') invoice.od_sale_order_name = ', '.join(sale_orders.mapped('name')) if sale_orders else False
这种方式不用额外维护关联表,直接利用现有数据关系计算字段值,更符合Odoo的设计逻辑。
内容的提问来源于stack exchange,提问作者HVH

