This question has been flagged
3 Replies
6342 Views

I have a class hr_calc() that have one field Many2one referenced with hr_employee, this field have an method onchange_employee_id() when change the employee this need give me two values of fields from hr_employee, this work fine. The problem is when I save, this two field of hr_calc() turn null and not save nothing.

What I do wrong ?

This is the hr_calc() class:

 class hr_py_calc_hours(models.Model):
    _name = 'hr.py.calc.hours'
 
    state = fields.Selection([('draft','Draft'),('done','Done')], default='draft', string='Status', select=True, readonly=True, copy=False)
    employee = fields.Many2one('hr.employee', string='Employee', required=True)
    date_from = fields.Date(string='Period', required=True, readonly=True, states={'draft': [('readonly', False)]})
    date_to = fields.Date(string='-', required=True, readonly=True, states={'draft': [('readonly', False)]})
    office = fields.Char(string='Office', readonly=True)
    matricu = fields.Char('Matric', readonly=True)
 
    def confirm_hours(self, cr, uid, ids, context=None):
        self.write(cr, uid, ids, {'state': 'done'}, context=context)
        return True
 
    def onchange_employee_id(self, cr, uid, ids, employee, context=None):
        if not employee:
            return {'value': {'office': ' '}}
        emp_obj = self.pool.get('hr.employee').browse(cr, uid, employee)
        department = matri = ' '
        if emp_obj.department_id:
            department = emp_obj.department_id.name
        if emp_obj.id_inter:
            matri = emp_obj.id_inter 
        return {'value': {'office': department,'matricu': matri}}

This is the view:

<form string="Horas Extras">
                    <header>
                        <button string="Aprobar" name="confirm_hours" states="draft" class="oe_highlight oe_inline"/>
                        <field name="state" widget="statusbar" statusbar_visible="draft,done"/>
                    </header>
                    <sheet>
                        <div class="oe_title">
                            <label for="employee" class="oe_edit_only"/>
                            <h1>
                                <field name="employee" on_change="onchange_employee_id(employee)"/>
                            </h1>                            
                        </div>
                        <div class="oe_right">
                            <label for="date_from" class="oe_edit_only"/>
                            <h3>
                                <field name="date_from" class="oe_inline"/><label for="date_to">-</label><field name="date_to" class="oe_inline"/>
                            </h3>                            
                        </div>
                        <group col="2">
                            <field name="office"/>
                            <field name="matricu"/>
                        </group>
                    </sheet>
</form>
Avatar
Discard
Best Answer

Hi,

zbik said right (see all his recommandations) :

but I have some differences for v8 coding, see after :

when you use @api.multi, you should loop on self :


@api.multi

def confirm_hours(self):

    for record in self:

         record.state = 'done'


but for a button which is not multi, use @api.one


@api.one

def confirm_hours(self):

     self.state = 'done'


with api v8, no need to test if field value for complete object notation path  exists :


@api.onchange('employee')

def do_employee(self):

    self.office = self.employee.department_id.name or ' '

    self.matri = self.employee.id_inter or ' '

bye

Avatar
Discard
Best Answer
  1. In new api you use @api.onchange decorator

  2. You remove readonly=True for stored fields

try like this:

in xml

<field name="employee"/>

in py

office = fields.Char(string='Office')

matricu = fields.Char('Matric')


@api.onchange('employee')

def do_employee(self):

   if not self.employee:

     self.office = ' '

   else:

     if self.employee.department_id:

       self.office = self.employee.department_id.name or ' '

     if self.employee.id_inter:

       self.matri = self.employee.id_inter or ' '


@api.multi

def confirm_hours(self):

   self.state = 'done'

Avatar
Discard
Author Best Answer

Thanks. Work fine and I know more and better about api's. Thanks

Avatar
Discard