第 13 章:与其他模块交互¶
在 上一章 中,我们使用继承修改了模块的行为。在我们的房地产场景中,我们希望更进一步,能够为客户生成发票。Odoo 提供了开票模块,因此直接从房地产模块创建发票会非常方便,也就是说,一旦房产被设为“已售出”,就会在开票应用中创建一张发票。
具体示例:会计分录¶
注解
目标:本节结束时:
应创建一个新的
estate_account模块房产售出后,应为买方开具发票
每当我们要与其他模块交互时,都需要牢记模块化原则。如果我们打算把应用卖给房地产中介公司,有些公司可能想要开票功能,而另一些可能不需要。
链接模块¶
此类用例的常见做法是创建一个“链接”模块。在我们的例子中,该模块将依赖 estate 和 account,并包含房地产房产的发票创建逻辑。这样,房地产模块和会计模块就可以独立安装。当两者都安装后,链接模块便提供这项新功能。
当 estate_account 模块出现在列表中时,就可以安装它了!你会注意到开票应用也会被安装。这是意料之中的,因为你的模块依赖它。如果卸载开票应用,你的模块也会被卸载。
创建发票¶
现在是时候生成发票了。我们想为 estate.property 模型添加功能,也就是说,为房产售出时添加一些额外逻辑。听起来耳熟吗?如果不熟悉,最好回到 上一章 看看,因为你可能遗漏了一些内容 ;-)
第一步,我们需要扩展在房产上点击 “已售出”按钮 时所调用的动作。为此,我们需要在 estate_account 模块中为 estate.property 模型创建 模型继承。目前,重写后的动作只是返回 super 调用。也许一个示例能让事情更清楚:
from odoo import models
class InheritedModel(models.Model):
_inherit = ["inherited.model"]
def inherited_action(self):
return super().inherited_action()
在 此处 可以找到一个实际示例。
练习
添加创建发票的第一步。
在
estate_account模块的正确文件夹中创建estate_property.py文件。对
estate.property模型使用_inherit。重写
action_sold方法(你可能用了其他名称),使其返回super调用。
提示:为确保其生效,可在重写的方法中添加 print 或调试器断点。
它生效了吗?如果没有,请检查所有 Python 文件是否都已正确导入。
如果重写生效,我们就可以继续创建发票了。遗憾的是,在 Odoo 中没有简单的方法能知道如何创建任意对象。大多数情况下,需要查看其模型以找到必需字段并提供合适的值。
学习的一个好方法是看看其他模块是如何实现你想要的功能的。例如,销售的基本流程之一就是从销售订单创建发票。这看起来是一个很好的起点,因为它所做的正是我们想做的事。花点时间阅读并理解 _create_invoices 方法。当你因为这个看似简单的任务却异常复杂而哭完之后,我们就可以继续教程了。
要创建发票,我们需要以下信息:
一个
partner_id:客户一个
move_type:它有多个 可选值一个
journal_id:会计日记账
这足以创建一张空的发票。
练习
添加创建发票的第二步。
在 action_sold 方法的重写中创建一张空的 account.move:
partner_id取自当前的estate.propertymove_type应对应于“客户发票”
提示:
要创建对象,请使用
self.env[model_name].create(values),其中values是一个dict。create方法不接受记录集作为字段值。
当房产被设为“已售出”时,你现在应该能在 开票 / 客户 / 发票 中看到一张新建的客户发票。
显然,目前我们还没有任何发票行。要创建发票行,我们需要以下信息:
name:该行的描述quantityprice_unit
此外,发票行需要关联到发票。将发票行关联到发票最简单、最高效的方式是在创建发票时就包含所有行。为此,创建 account.move 时会包含 invoice_line_ids 字段,它是一个 One2many。One2many 和 Many2many 使用特殊的“命令”,这些命令通过 Command 命名空间变得便于阅读。该命名空间表示要在一组记录上执行的三元组命令。最初,三元组是执行这些命令的唯一方式,但现在标准做法是改用该命名空间。其格式是把它们放入一个按顺序执行的列表中。下面是一个在创建 test_model 时包含 One2many 字段 line_ids 的简单示例:
from odoo import Command
def inherited_action(self):
self.env["test_model"].create(
{
"name": "Test",
"line_ids": [
Command.create({
"field_1": "value_1",
"field_2": "value_2",
})
],
}
)
return super().inherited_action()
练习
添加创建发票的第三步。
在创建 account.move 时添加两条发票行。每套售出的房产将按照以下条件开票:
售价的 6%
额外收取 100.00 的管理费
提示:参照上面的示例,在创建时添加 invoice_line_ids。每一行都需要 name、quantity 和 price_unit。
本章可能是目前最难的一章,但它最接近实际 Odoo 开发的样子。在 下一章 中,我们将介绍 Odoo 中使用的模板机制。