[FIX] fields: in many2many fields, avoid inserting duplicate entries in table
This commit is contained in:
parent
4f1bd899ef
commit
ece592dbf7
|
@ -761,6 +761,15 @@ class many2many(_column):
|
|||
return
|
||||
rel, id1, id2 = self._sql_names(model)
|
||||
obj = model.pool.get(self._obj)
|
||||
|
||||
def link(ids):
|
||||
# beware of duplicates when inserting
|
||||
query = """ INSERT INTO {rel} ({id1}, {id2})
|
||||
(SELECT %s, unnest(%s)) EXCEPT (SELECT {id1}, {id2} FROM {rel} WHERE {id1}=%s)
|
||||
""".format(rel=rel, id1=id1, id2=id2)
|
||||
for sub_ids in cr.split_for_in_conditions(ids):
|
||||
cr.execute(query, (id, list(sub_ids), id))
|
||||
|
||||
for act in values:
|
||||
if not (isinstance(act, list) or isinstance(act, tuple)) or not act:
|
||||
continue
|
||||
|
@ -774,10 +783,7 @@ class many2many(_column):
|
|||
elif act[0] == 3:
|
||||
cr.execute('delete from '+rel+' where ' + id1 + '=%s and '+ id2 + '=%s', (id, act[1]))
|
||||
elif act[0] == 4:
|
||||
# following queries are in the same transaction - so should be relatively safe
|
||||
cr.execute('SELECT 1 FROM '+rel+' WHERE '+id1+' = %s and '+id2+' = %s', (id, act[1]))
|
||||
if not cr.fetchone():
|
||||
cr.execute('insert into '+rel+' ('+id1+','+id2+') values (%s,%s)', (id, act[1]))
|
||||
link([act[1]])
|
||||
elif act[0] == 5:
|
||||
cr.execute('delete from '+rel+' where ' + id1 + ' = %s', (id,))
|
||||
elif act[0] == 6:
|
||||
|
@ -789,8 +795,7 @@ class many2many(_column):
|
|||
d1 = ''
|
||||
cr.execute('delete from '+rel+' where '+id1+'=%s AND '+id2+' IN (SELECT '+rel+'.'+id2+' FROM '+rel+', '+','.join(tables)+' WHERE '+rel+'.'+id1+'=%s AND '+rel+'.'+id2+' = '+obj._table+'.id '+ d1 +')', [id, id]+d2)
|
||||
|
||||
for act_nbr in act[2]:
|
||||
cr.execute('insert into '+rel+' ('+id1+','+id2+') values (%s, %s)', (id, act_nbr))
|
||||
link(act[2])
|
||||
|
||||
#
|
||||
# TODO: use a name_search
|
||||
|
|
Loading…
Reference in New Issue