到目前为止,字段都是直接存储在数据库中,并直接从数据库中检索。字段也可以计算。在这种情况下,字段的值不是从数据库中检索的,而是通过调用模型的方法实时计算的。
要创建计算字段,请创建字段并将其属性compute
设置为方法名。计算方法应该在每个记录的self
中设置要计算的字段值。
注意:
self
是一个集合
对象本身是一个记录集,即记录的有序集合。它支持集合上的标准Python操作,如len(self)
和iter(self)
,以及额外的集合操作,如recs1 + recs2
。
在self
上迭代会一个接一个地给出记录,其中每个记录本身就是一个大小为1的集合。您可以使用点符号访问/分配单个记录上的字段,比如record.name
。
import random
from odoo import models, fields, api
class ComputedModel(models.Model):
_name = 'test.computed'
name = fields.Char(compute='_compute_name')
def _compute_name(self):
for record in self:
record.name = str(random.randint(1, 1e6))
依赖
计算字段的值通常取决于记录上的其他字段的值。ORM希望开发人员使用修饰符depends()
指定对计算方法的依赖关系。每当它的一些依赖项被修改时,ORM使用给定的依赖项来触发字段的重新计算:
from odoo import models, fields, api
class ComputedModel(models.Model):
_name = 'test.computed'
name = fields.Char(compute='_compute_name')
value = fields.Integer()
@api.depends('value')
def _compute_name(self):
for record in self:
record.name = "Record with value %s" % record.value
“计算字段”练习
将占用席位的百分比添加到会话模型中
在树视图和表单视图中显示该字段
将该字段显示为进度条
将计算字段添加到会话
在会话视图中显示字段:
openacademy/models.py
course_id = fields.Many2one('openacademy.course',
ondelete='cascade', string="Course", required=True)
attendee_ids = fields.Many2many('res.partner', string="Attendees")
taken_seats = fields.Float(string="Taken seats", compute='_taken_seats')
@api.depends('seats', 'attendee_ids')
def _taken_seats(self):
for r in self:
if not r.seats:
r.taken_seats = 0.0
else:
r.taken_seats = 100.0 * len(r.attendee_ids) / r.seats
openacademy/views/openacademy.xml
<field name="start_date"/>
<field name="duration"/>
<field name="seats"/>
<field name="taken_seats" widget="progressbar"/>
</group>
</group>
<label for="attendee_ids"/>
<tree string="Session Tree">
<field name="name"/>
<field name="course_id"/>
<field name="taken_seats" widget="progressbar"/>
</tree>
</field>
</record>
默认值
可以给任何字段一个默认值。在字段定义中,添加default=X
选项,其中X
可以是Python字面值(boolean、integer、float、string),也可以是接受记录集并返回值的函数:
name = fields.Char(default="Unknown")
user_id = fields.Many2one('res.users', default=lambda self: self.env.user)
self.env
允许访问请求参数和其他有用的东西:
self.env.cr
或self._cr
是数据库游标对象;它用于查询数据库
self.env.uid
或self._uid
是当前用户的数据库id
self.env.user
是当前用户的记录
self.env.context
或self._context
是上下文字典
self.env.ref(xml_id)
返回与XML id对应的记录
self.env[model_name]
返回给定模型的实例
“活动对象——默认值”练习
将start_date的默认值定义为today。
在类会话中添加active
字段,并在默认情况下将会话设置为活动。
openacademy/models.py
_description = "OpenAcademy Sessions"
name = fields.Char(required=True)
start_date = fields.Date(default=fields.Date.today)
duration = fields.Float(digits=(6, 2), help="Duration in days")
seats = fields.Integer(string="Number of seats")
active = fields.Boolean(default=True)
instructor_id = fields.Many2one('res.partner', string="Instructor",
domain=['|', ('instructor', '=', True),
openacademy/views/openacademy.xml
<field name="course_id"/>
<field name="name"/>
<field name="instructor_id"/>
<field name="active"/>
</group>
<group string="Schedule">
<field name="start_date"/>
Odoo有内置规则
active
字段,设置为False
使记录隐藏。