0
votes

I have the next table in Odoo, named relationship, which comes from the relation between the table girl and the table boy:

| girl_id | boy_id | relationship_type |

| 1 | 2 | friends |

| 1 | 3 | siblings |

| 2 | 7 | lovers |

So:

  • In the table girl there's a field relationships which is a one2many pointing to the table relationship.
  • In the table boy there's a field relationships which is a one2many pointing to the table relationship.
  • In the table relationship there are two fields, girl_id and boy_id, both pointing to the tables girl and boy respectively.

Scenario:

In the forms of girl and boy there's the field relationships. When I add a new relationship for a girl or a boy, a form is opened to fill in the fields of the table relationship (girl_id, boy_id and relationship_type). Imagine I'm in the form of a girl, I click on add a new relationship and the form is opened. I implemented this in order not to see the girl_id (it's invisible but it contains the ID of the current girl). So I can see only two fields (boy_id and relationship_type).

What I want:

Keeping on with the example, if I open the dropdown of boy_id, I'll see all boys, even the ones who are already related to this girl. For example, if I'm adding a relationship to the girl with id 1, I must not see boys with ids 2 and 3, if the girl is the one with id 2, I must not see the boy with id 7.

My attempt

I've created two fields in the table relationships, named boys_of_the_girl (one2many related to 'girl_id.relationships') and girls_of_the_boy (one2many related to 'boy_id.relationships').

My code: (Example: creating a relationship for a girl)

<field name="girl_id" invisible="1"/>
<field name="boys_of_the_girl" invisible="1"/>
<field name="boy_id" domain="[('id', 'not in', boys_of_the_girl)]"/>
<field name="relationship_type"/>

The error:

RuntimeError: maximum recursion depth exceeded while calling a Python object

Can anyone help me, please? Thank you!

EDIT

Table boy

relationships = fields.One2many(comodel_name='relationship',
                                inverse_name='boy_id',
                                string='Relationships')

Table girl

relationships = fields.One2many(comodel_name='relationship', inverse_name='girl_id', string='Relationships')

Table relationship

boy_id = fields.Many2one(comodel_name='boy', string='Boy', required=True)
girl_id = fields.Many2one(comodel_name='girl', string='Girl', required=True)
relationship_type = fields.Char(string='Relationship type')
1
I think you need to take many2many instead of one2many, and m2m default provides what you want.Emipro Technologies Pvt. Ltd.
Thank you @EmiproTechnologies. But a many2many field generates a table with only the foreign IDs, it's not possible to add more columns to it (like in this case, relationship_type)forvas
Can you please show me the fields structure of all these models ?.Emipro Technologies Pvt. Ltd.
@EmiproTechnologies I've edited my post to show the structure of the models.forvas
@forvas can you help me to fixed this issue stackoverflow.com/questions/32919104/…DASADIYA CHAITANYA

1 Answers

1
votes

Well, finally I found out that it's not possible to manage this through XML code, but it's possible to achieve the same purpose through Python:

Only with this function (and another one similar for the domain of girl_id in the other form):

@api.onchange('girl_id')
def on_change_girl_id(self):
    current_girl_id = self.env.context.get('default_girl_id', False)
    relationship_recordset = self.search([('girl_id', '=', current_girl_id)])
    boy_recordset = relationship_recordset.mapped('boy_id')
    boy_ids = boy_recordset.mapped('id')
    boy_id_domain = [
        ('id', 'not in', boy_ids)
    ]
    result = {
        'domain': {
            'boy_id': boy_id_domain,
        },
    }
    return result

And this way it's not necessary to add any domain to the field boy_id in the XML form. This function will affect the form where you set a relationship for a girl, as I wrote above, another similar function must be declared to manage the right behaviour when setting a relationship for a boy.