valid default/callback value in consistencies
authorEmmanuel Garette <egarette@cadoles.com>
Sun, 8 Mar 2015 11:03:49 +0000 (12:03 +0100)
committerEmmanuel Garette <egarette@cadoles.com>
Sun, 8 Mar 2015 11:03:49 +0000 (12:03 +0100)
ChangeLog
test/test_option_consistency.py
tiramisu/option/baseoption.py
tiramisu/value.py

index 8217a81..3ebf62d 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,6 @@
+Sun Mar  8 12:02:17 2015 +0200 Emmanuel Garette <egarette@cadoles.com>
+       * valid default/callback value in consistencies
+
 Sun Dec  7 14:37:32 2014 +0200 Emmanuel Garette <egarette@cadoles.com>
        * mandatory master/slave's consistency with default value as slave
        * test uppercase character before valid domain name for better error
index 8a6f797..c419f7e 100644 (file)
@@ -302,6 +302,41 @@ def test_consistency_network_netmask_multi_slave_default():
     c.read_only()
     assert c.a == [u'192.168.1.0']
     assert c.b == [u'255.255.255.0']
+    c.read_write()
+    raises(ValueError, "c.a[0] = u'192.168.1.2'")
+    raises(ValueError, "c.a.append(u'192.168.1.1')")
+    raises(ValueError, "c.a = [u'192.168.1.0', u'192.168.1.1']")
+    c.a.append()
+    c.b = [u'255.255.255.0', u'255.255.255.255']
+    c.a = [u'192.168.1.0', u'192.168.1.1']
+
+
+def return_netmask(*args, **kwargs):
+    return u'255.255.255.0'
+
+
+def test_consistency_network_netmask_multi_slave_callback():
+    a = NetworkOption('a', '', multi=True, properties=('mandatory',))
+    b = NetmaskOption('b', '', callback=return_netmask, multi=True, properties=('mandatory',))
+    od = OptionDescription('a', '', [a, b])
+    od.impl_set_group_type(groups.master)
+    b.impl_add_consistency('network_netmask', a)
+    c = Config(od)
+    c.read_write()
+    c.cfgimpl_get_settings().remove('cache')
+    assert c.a == []
+    assert c.b == []
+    c.a.append(u'192.168.1.0')
+    c.read_only()
+    assert c.a == [u'192.168.1.0']
+    assert c.b == [u'255.255.255.0']
+    c.read_write()
+    raises(ValueError, "c.a[0] = u'192.168.1.2'")
+    raises(ValueError, "c.a.append(u'192.168.1.1')")
+    raises(ValueError, "c.a = [u'192.168.1.0', u'192.168.1.1']")
+    c.a.append()
+    c.b = [u'255.255.255.0', u'255.255.255.255']
+    c.a = [u'192.168.1.0', u'192.168.1.1']
 
 
 def test_consistency_ip_netmask_multi_master():
index 04cd2a8..d9eb6c2 100644 (file)
@@ -454,18 +454,32 @@ class Option(OnlyOption):
                 elif self.impl_is_submulti():
                     try:
                         all_cons_vals.append(opt_value[index][submulti_index])
-                    except IndexError:
+                    except IndexError, err:
+                        log.debug('indexerror in submulti opt in _launch_consistency: {0}'.format(err))
                         #value is not already set, could be higher index
                         #so return if no value
                         return
                 else:
                     try:
                         all_cons_vals.append(opt_value[index])
-                    except IndexError:
+                    except IndexError, err:
+                        log.debug('indexerror in _launch_consistency: {0}'.format(err))
                         #value is not already set, could be higher index
-                        #so return if no value
-                        return
+                        #so return if no value and not default_value
+                        if context is not undefined:
+                            if isinstance(opt, DynSymLinkOption):
+                                path = opt.impl_getpath(context)
+                            else:
+                                path = descr.impl_get_path_by_opt(opt)
+                            default_value = context.cfgimpl_get_values()._getvalue(opt, path, True, index=index)
+                        else:
+                            default_value = opt.impl_getdefault_multi()
+                        if default_value is not None:
+                            all_cons_vals.append(default_value)
+                        else:
+                            return
             except PropertiesOptionError as err:
+                log.debug('propertyerror in _launch_consistency: {0}'.format(err))
                 if transitive:
                     raise err
                 else:
index 6cd635e..ea60508 100644 (file)
@@ -333,9 +333,8 @@ class Values(object):
         setting_properties = context.cfgimpl_get_settings()._getproperties()
         opt.impl_validate(value, context,
                           'validator' in setting_properties)
-        if opt.impl_is_multi():
-            if opt.impl_is_master_slaves():
-                opt.impl_get_master_slaves().setitem(self, opt, value, path)
+        if opt.impl_is_master_slaves():
+            opt.impl_get_master_slaves().setitem(self, opt, value, path)
         self._setvalue(opt, path, value, force_permissive=force_permissive,
                        is_write=is_write,
                        setting_properties=setting_properties)
@@ -631,10 +630,9 @@ class Multi(list):
         """the list value can be updated (appened)
         only if the option is a master
         """
-        if not force:
-            if self.opt.impl_is_master_slaves('slave'):  # pragma: optional cover
-                raise SlaveError(_("cannot append a value on a multi option {0}"
-                                   " which is a slave").format(self.opt.impl_getname()))
+        if not force and self.opt.impl_is_master_slaves('slave'):  # pragma: optional cover
+            raise SlaveError(_("cannot append a value on a multi option {0}"
+                               " which is a slave").format(self.opt.impl_getname()))
         index = self.__len__()
         if value is undefined:
             try: