diff --git a/CHANGELOG b/CHANGELOG index 94a2fcfebf..25071177a6 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -1,3 +1,4 @@ +* Add support for properties to fields.depends * Allow combining authentication methods together * Add context to export CSV route diff --git a/trytond/model/modelview.py b/trytond/model/modelview.py index 28a12b879d..4088af6144 100644 --- a/trytond/model/modelview.py +++ b/trytond/model/modelview.py @@ -150,7 +150,11 @@ class ModelView(Model): if not parent_meth: continue for attr in ['depends', 'depend_methods', 'change']: - parent_value = getattr(parent_meth, attr, None) + if isinstance(parent_meth, property): + parent_value = getattr(parent_meth.fget, attr, set()) + parent_value |= getattr(parent_meth.fset, attr, set()) + else: + parent_value = getattr(parent_meth, attr, set()) if parent_value: methods[attr][name] |= parent_value @@ -174,8 +178,9 @@ class ModelView(Model): meth_done = set() while meth_names: meth_name = meth_names.pop() - assert callable(getattr(cls, meth_name)), \ - "%s.%s not callable" % (cls, meth_name) + method = getattr(cls, meth_name) + assert callable(method) or isinstance(method, property), \ + "%s.%s not callable or property" % (cls, meth_name) set_methods(meth_name) setattr(field, attribute, getattr(field, attribute) | methods['depends'][meth_name]) diff --git a/trytond/tests/test_field_depends.py b/trytond/tests/test_field_depends.py index e16a5be814..07588bfa5a 100644 --- a/trytond/tests/test_field_depends.py +++ b/trytond/tests/test_field_depends.py @@ -170,6 +170,34 @@ class FieldDependsTestCase(unittest.TestCase): set(Model.name.definition(Model, 'en')['on_change']), {'foo', 'bar', 'id'}) + def test_property_depends(self): + "Tests depends on a property" + + class Model(ModelView): + "ModelView Property Depends" + __name__ = 'test.modelview.property_depends' + + foo = fields.Char("Foo") + bar = fields.Char("Bar") + + @property + @fields.depends('foo') + def len_foo(self): + return len(self.foo) + + @len_foo.setter + @fields.depends('bar') + def len_foo(self, value): + pass + + @fields.depends(methods=['len_foo']) + def on_change_bar(self): + pass + + Model.__setup__() + + self.assertEqual(Model.bar.on_change, {'foo', 'bar'}) + def suite(): return unittest.TestLoader().loadTestsFromTestCase(FieldDependsTestCase)