[IMP] core: allow set [value] in selection ondelete
In some cases we migh want to change to a value that isn't the default one when uninstalling. For instance: when we uninstall the module `event_sale`, a product has the field `detailed_type` set to `event`, which is a subtype of `service`. So we want to update the value to `service` when uninstalling instead of the default value, which would be `consu` and wouldn't make any sense. Part-of: odoo/odoo#77876
This commit is contained in:
@@ -1435,6 +1435,8 @@ class IrModelSelection(models.Model):
|
||||
elif ondelete == 'set default':
|
||||
value = field.convert_to_write(field.default(Model), Model)
|
||||
safe_write(selection._get_records(), field.name, value)
|
||||
elif ondelete.startswith('set '):
|
||||
safe_write(selection._get_records(), field.name, ondelete[4:])
|
||||
elif ondelete == 'cascade':
|
||||
selection._get_records().unlink()
|
||||
else:
|
||||
|
||||
@@ -1179,7 +1179,7 @@ class SelectionRequiredLiteral(models.Model):
|
||||
|
||||
my_selection = fields.Selection(selection_add=[
|
||||
('bacon', "Bacon"),
|
||||
], ondelete={'bacon': lambda r: r.write({'my_selection': 'bar'})})
|
||||
], ondelete={'bacon': 'set bar'})
|
||||
|
||||
|
||||
class SelectionRequiredMultiple(models.Model):
|
||||
|
||||
@@ -315,10 +315,10 @@ class TestFields(TransactionCaseWithUserDemo):
|
||||
check_stored(discussion1)
|
||||
|
||||
# switch message from discussion, and check again
|
||||
|
||||
|
||||
# See YTI FIXME
|
||||
discussion1.invalidate_cache()
|
||||
|
||||
|
||||
discussion2 = discussion1.copy({'name': 'Another discussion'})
|
||||
message2 = discussion1.messages[0]
|
||||
message2.discussion = discussion2
|
||||
@@ -3132,6 +3132,20 @@ class TestSelectionOndeleteAdvanced(common.TransactionCase):
|
||||
with self.assertRaises(AssertionError):
|
||||
self.registry.setup_models(self.env.cr)
|
||||
|
||||
def test_ondelete_value_no_valid(self):
|
||||
class Foo(models.Model):
|
||||
_module = None
|
||||
_inherit = self.MODEL_BASE
|
||||
|
||||
my_selection = fields.Selection(selection_add=[
|
||||
('westvleteren', "Westvleteren beers is overrated"),
|
||||
], ondelete={'westvleteren': 'set foooo'})
|
||||
|
||||
Foo._build_model(self.registry, self.env.cr)
|
||||
|
||||
with self.assertRaises(AssertionError):
|
||||
self.registry.setup_models(self.env.cr)
|
||||
|
||||
def test_ondelete_required_null_explicit(self):
|
||||
class Foo(models.Model):
|
||||
_module = None
|
||||
|
||||
+13
-6
@@ -2347,6 +2347,8 @@ class Selection(Field):
|
||||
deleted along with the option itself.
|
||||
- 'set default' -- all records with this option will be
|
||||
set to the default of the field definition
|
||||
- 'set VALUE' -- all records with this option will be
|
||||
set to the given value
|
||||
- <callable> -- a callable whose first and only argument will be
|
||||
the set of records containing the specified Selection option,
|
||||
for custom processing
|
||||
@@ -2444,12 +2446,17 @@ class Selection(Field):
|
||||
"as it does not define a default! Either define one in the base "
|
||||
"field, or change the chosen ondelete policy" % self
|
||||
)
|
||||
continue
|
||||
raise ValueError(
|
||||
"%r: ondelete policy %r for selection value %r is not a valid ondelete "
|
||||
"policy, please choose one of 'set null', 'set default', 'cascade' or "
|
||||
"a callable" % (self, val, key)
|
||||
)
|
||||
elif val.startswith('set '):
|
||||
assert val[4:] in values, (
|
||||
"%s: ondelete policy of type 'set %%' must be either 'set null', "
|
||||
"'set default', or 'set value' where value is a valid selection value."
|
||||
) % self
|
||||
else:
|
||||
raise ValueError(
|
||||
"%r: ondelete policy %r for selection value %r is not a valid ondelete"
|
||||
" policy, please choose one of 'set null', 'set default', "
|
||||
"'set [value]', 'cascade' or a callable" % (self, val, key)
|
||||
)
|
||||
|
||||
values = merge_sequences(values, [kv[0] for kv in selection_add])
|
||||
labels.update(kv for kv in selection_add if len(kv) == 2)
|
||||
|
||||
Reference in New Issue
Block a user