Technical mailing list archives

technical@mail.odoo.com

Avatar

Re: Update parent field from one2many relation [Odoo V8]

by
Anass Abdelkrimi
- 2017年02月08日 10時14分53秒
Thank you Olivier, this really helped me a lot. Thanks again!

2017-02-08 13:25 GMT+00:00 Olivier Dony <odo@odoo.com>:
On 02/06/2017 04:50 PM, Abdelkrimi OctaGen wrote:
> Hi,
> I have one model with 2 one2many relations (mat_gen and rh_gen). The first
> relation has a field named "qte", i want to update the second one when the
> "qte" changes with an onchange method.
> 
> |@api.onchange('qte')defonchange_qte(self):mat
> =self.browse(self._origin.id)ifmat:mo
> =self.env["plg.ressource.rh"].browse(mat.ch.id)ifmo:temp
> =[]temp.append({'code':mo.code,'designation':mo.designation,'unite':mo.unite.id,'qte':self.qte,'aff_pr':self.aff_pr,'prixu':mo.prixu,})|
> 
> Here i've to access the parent model to update the second relation
> like |self.parent.update({'rh_gen':temp})| but obviously the parent variable
> does not exist. How can i fix this? 

Whenever you declare a one2many field, you set the inverse many2one
relationship (this is the foreign key field at the database level).

So when you are working in server-side business code, you can always reach the
"parent" record by following that inverse m2o relationship.

To take an example from standard Odoo 8 code, `account.invoice` has two o2m
relationships: `invoice_line` and `tax_line` (see [1]).
Both have an inverse `invoice_id` m2o relationship.

If you wanted to do add a new tax line to the invoice whenever the `taxes_id`
of an invoice line changes, you could define something like this on the
`account.invoice.line` model:

        @api.onchange('taxes_id')
        def onchange_taxes_ids(self):
            invoice = self.invoice_id
            line_data = {
                ... # field values for the new tax record
            }
            new_line = self.env['account.invoice.tax'].new(line_data)
            # append new line to taxes of parent invoice
            invoice.tax_line += new_line

Note the use of the inverse m2o `invoice_id` to locate the "parent" invoice.
Also note the use of the new() constructor to build the new record in the
onchange environment only, as create/write are forbidden within onchange
methods, like Gustavo said.

The framework will pick up the addition of the new record inside the
environment, and return the appropriate instructions to the UI, provided that
all the relevant fields were included in the form view.

That's more or less what the standard code is doing in Odoo 10 [2].

It's generally not a good idea to solely depend on explicit onchange methods to
guarantee the integrity of your business document, though. They will not be
triggered for direct RPC, for example.
So you should typically have a check in create(), write() or a relevant
go-to-next-stage-method to be sure that your o2m data is consistent, or fix it. [3]



[1] Odoo 8 invoice o2m: https://git.io/vDR7w
[2] Invoice Line onchange in Odoo 10 https://git.io/vDRbs [3] Invoice confirmation tax check in Odoo 10: https://git.io/vDRb1

_______________________________________________
Mailing-List: https://www.odoo.com/groups/community-framework-62
Post to: mailto:expert-framework@mail.odoo.com
Unsubscribe: https://www.odoo.com/groups?unsubscribe


Reference