This community is for professionals and enthusiasts of our products and services.
Share and discuss the best content and new marketing ideas, build your professional profile and become a better marketer together.


Override onchange method in old API with new API


I am working on a custom module for Odoo 9 that interacts HR contract (model hr.contract).
My situation is that I want raise onchange event on employee_id field but the onchange method was originally written in old API with the combination of a Python method and XML definition as below:

    def onchange_employee_id(self, cr, uid, ids, employee_id, context=None):
        if not employee_id:
            return {'value': {'job_id': False, 'department_id': False}}
        emp_obj = self.pool.get('hr.employee').browse(cr, uid, employee_id, context=context)
        job_id = dept_id = False
        if emp_obj.job_id:
            job_id =
        if emp_obj.department_id:
            dept_id =
        return {'value': {'job_id': job_id, 'department_id': dept_id}}

<field name="employee_id" on_change="onchange_employee_id(employee_id)"/>

I have a custom field name last_contract_id (many2one to hr.contract) and I want it to be loaded automatically on change of employee_id (just to show the contracts that owned by the selected employee.

My aim is to override it using new API which I can reuse later in Odoo 10, 11, …

How can I do it, plz?
1 Answer
David Tran
Best Answer

Firstly, you need to replace the xml definition of the employee_id field so that it will not call the onchange_employee_id method anymore. You can do in your inherited view, e.g.

		<record model="ir.ui.view" id="your_inherited_view_id">
			<field name="name">hr.contract.form</field>
			<field name="model">hr.contract</field>
			<field name="inherit_id" ref="hr_contract.hr_contract_view_form" />
			<field name="arch" type="xml">
				<xpath expr="//field[@name='employee_id']" position="replace">
					<field name="employee_id" /> <!– you can add something else here depending on your needs –>

In your model which inherit hr.contract, just make something like this:
    def onchange_employee_id(self):
        # override onchange in old API to make it compatible with new API
        res = super(hr_contract, self).onchange_employee_id(
        if type(res) is dict and res.has_key('value'):
            for field, value in res.get('value').items():
                if hasattr(self, field):
                    setattr(self, field, value)
        #after this line, things are totally in new API style
        #filter data for last_contract_id field to just list contracts belong to the selected employee
        if self.employee_id:
            res['domain'] = {'last_contract_id':[('employee_id', '=',]}
        return res[/code]
Restart your Odoo and upgrade your module.
Let me know if it works.
1 Comment

It works perfectly. Tks!

Your Answer

Please try to give a substantial answer. If you wanted to comment on the question or answer, just use the commenting tool. Please remember that you can always revise your answers - no need to answer the same question twice. Also, please don't forget to vote - it really helps to select the best questions and answers!