Search code examples
odooodoo-14

Odoo Create Model Programmatically and Add/Append to One2many Field


So I have a Sale model and SaleLine model. Sale model have a field sale_line_ids as One2many from SaleLine model.

Sale

class Sale(models.Model):
    _name = 'store.sale'
    _description = 'Store Sale'

    ...
    sale_line_ids = fields.One2many('store.sale_line', 'sale_id', string='Sale Lines')
    ...

Sale Line

class SaleLine(models.Model):
    _name = 'store.sale_line'
    _description = 'Store Sale Line'

    sale_id = fields.Many2one('store.sale', string='Sale Reference', ondelete='cascade', index=True)
    product_id = fields.Many2one('store.product', string='Product', required=True)
    quantity = fields.Integer(string='Quantity', required=True)

I want to create SaleLine model programmatically and add that model to sale_line_ids field. How can I do that?


Solution

  • This answer is what I actually want to implement. However, the model is immediately saved to a database. I need to create a SaleLine model using env[].create({}) method.

    self.env['store.sale_line'].create({
        'sale_id': rec.id,
        'product_id': id_from_another_model,
        'quantity': quantity_from_another_model,
    })
    

    After that, I need to commit in order to save the data in a database.

    self.env.cr.commit()
    

    UPDATE

    The previous answer required record to store directly. The best answer to solve the problem is to create temporary record that only saved when user click the save button.

    Syntax

    (0, 0,  { values })
    

    First create sale_line list

    sale_line = []
    for data in list_of_data:
        sale_line.append([0, 0, {
            'sale_id': data['sale_id'],
            'product_id': data['product_id'],
            'quantity': data['quantity'],
        }])
    

    Assign sale_line list to sale_line_ids field

    self.write({'sale_line_ids': sale_line})
    

    And override the create method to commit the change

    @api.model
    def create(self, values):
        self.env.cr.commit() # This is the important part
    
        return super(Sale, self).create(values)