Odoo计算字段:无商店的工作=真,不适用于商店=真

时间:2015-08-11 14:49:42

标签: python field odoo

我在Odoo中有一个带有函数的计算字段。当我不添加商店参数时,一切正常。当我添加store参数时,它根本不会执行代码。

我的代码:

class opc_actuelewaardentags(models.Model):
    _name = 'opc_actuelewaardentags'

    unit = fields.Char(compute='changeunit')

    def changeunit(self):
        print "print"
        allrecords_actwaardent = self.search([])

        obj_taginst = self.env['opc_taginstellingen']
        allrecords_taginst = obj_taginst.search([])


        for i in allrecords_actwaardent:
            for j in allrecords_taginst:
                if i.tagnaam == j.tagnaam and i.unit != j.unit:
                    i.unit = j.unit

所以:当我这样调用代码时:

unit = fields.Char(compute='changeunit')

执行代码(显示" print")。

当我调用这样的代码时:

unit = fields.Char(compute='changeunit', store=True)

代码未执行(不显示" print")。

我的代码有什么问题吗?或者这是一个错误?对我来说似乎很奇怪......

我需要能够将值存储在数据库中,以便我可以在树视图中过滤单位。

编辑:我申请了Juan Salcedo的小费。没有工作......

我就这样做了:

unit = fields.Char(default = changeunit)    

def changeunit(self):
    print "print"
    allrecords_actwaardent = self.search([])

    obj_taginst = self.env['opc_taginstellingen']
    #Hier dan i.p.v. self werken met dat obj_taginst
    allrecords_taginst = obj_taginst.search([])


for i in allrecords_actwaardent:
    for j in allrecords_taginst:
        if i.tagnaam == j.tagnaam and i.unit != j.unit:
            i.unit = j.unit
return i.unit

给出错误:

  

NameError:name' changeunit'未定义

我也尝试将单位字段放在def changeunit(self)下面,但是也没有。

6 个答案:

答案 0 :(得分:1)

当我们设置store=True时,我们需要指定何时需要计算该函数。使用@api.depends('fields'),在更改字段值时指定字段名称,然后调用compute方法。

name = fields.Char('name')
length = fields.Integer(compute='get_length','Length',store=True)

@api.depends('name')
def get_length(self):
    self.length=len(name)

在此示例中,当您更改名称时,将调用get_length函数。

答案 1 :(得分:1)

没有@ api.depends的Store = True意味着它将在创建列/字段时只执行一次。

因此,如果没有@ api.depends,则无法使用store = True实现每次触发该方法的效果,或者您需要删除store = True,然后每次访问此字段时都会计算。

这是您在代码中更新所需的更改,但在此之前您需要从数据库中删除该列,然后重新启动服务器和升级模块之后,它将会到达那里。

class opc_actuelewaardentags(models.Model):
    _name = 'opc_actuelewaardentags'

    unit = fields.Char(compute='changeunit')

    @api.multi
    def changeunit(self):
      print "print"  
        for obj in self:
            allrecords_actwaardent = self.search([])
            obj_taginst = self.env['opc_taginstellingen']
            allrecords_taginst = obj_taginst.search([])
            for i in allrecords_actwaardent:
                for j in allrecords_taginst:
                    if i.tagnaam == j.tagnaam and i.unit != j.unit:
                       obj.unit = j.unit
                       break

另一种方式: store = False从未在数据库中存储任何值,因此如果您想将该值存储在数据库中并且不想更新(意味着它在创建或更新记录时已修复)那么您只需需要覆盖创建/写入方法,并在内部更新此字段的值。

@api.model
def create(self, vals):
    vals.update({'field':value})
    return super(class_name,self).create(vals)

答案 2 :(得分:0)

这是一个可能对您有用的解决方案,它并不完美,因为它可以在大多数时间没有真正需要的情况下经常调用该方法。

首先添加一个计算的新字段。将该字段添加到您需要它的UI中并隐藏它。没有必要展示它。你必须在ui中使用它来强制odoo来计算它。

计算字段的值时,还要更改您真正想要编辑的字段的值。由于计算方法可以更新多个字段,因此可以使用。

根据我的说法,您不必将原始字段计算为......

但是因为你正在使用sql修改某些字段,因为你承认自己并不是很好...为什么你不同时用SQL改变那个字段呢?在没有hacks的情况下在Odoo端更容易,并确保改变SQL类型的方法改变了应有的一切。这就像你正在编辑问题的一半并期望odoo自己捕获数据变化。为了实现这一点,你需要有一些方法让数据库通知odoo某些东西发生了变化......不幸的是,Postgresql没有这样做,所以确保当你从SQL更新某些东西时,你有完成更改后的一致数据。

答案 3 :(得分:0)

我也注意到了这个问题,但在我的情况下,没有必要将它存储在数据库中。所以我把它保存为store = false并且计算字段工作并且它在视图中有一个值,这是重要的,只是在视图中有值..

所以当你设置store = true时,只有新记录在计算字段中有一个值,而旧数据在计算字段中没有值

因此,您必须重置字段计算中使用的字段的值(依赖字段)

通过在compute函数中编写一个write语句,再次将这些字段重新分配给自己的值,就像它们刚刚被创建一样

for record in self.env['class'].search([]):
    record.field= record.field

record.field - >>>字段计算中使用的字段或api.depends(字段)

答案 4 :(得分:0)

这不是问题,因为Store = True(按照建议的方式)告诉odoo当你计算字段时它将它的值存储到数据库中,所以当你下次调用这个记录时,框架将从数据库,当在数据库或UI中更新depends注释中的任何字段时,将重新计算此值。

所以代码没有结果,因为当你在创建值后指定store = True时,值将为False,odoo将不会重新计算它,直到你更改触发该函数的其中一个字段。

您需要使用查询手动计算此字段,以设置数据库中现有记录的值,不必担心odoo将计算和存储值的新记录。

  

所以store = True。意味着计算并存储数据库中的值,并且在编辑其中一个字段之前不再计算它,您需要首次手动计算现有记录的值。

答案 5 :(得分:0)

实现计算字段和存储到数据库中的一种方法是添加一个与计算字段相关的附加字段。

field_name = fields.Monetary(string='Name', compute='_compute_anything')
field_name_store = fields.Monetary(related='field_name', string='Name', store=True)

@api.multi
def _compute_anything(self):
    variable = (field1+field2)
    update({'field_name':variable})