master/slave, multi... in the glossary
This commit is contained in:
parent
a894a5e27b
commit
b92c087cfc
281
doc/config.txt
281
doc/config.txt
|
@ -267,8 +267,12 @@ and of course, :meth:`~config.SubConfig.make_dict()` can be called in a subtree:
|
||||||
the owners
|
the owners
|
||||||
~~~~~~~~~~~
|
~~~~~~~~~~~
|
||||||
|
|
||||||
When a value is set on an option, an owner is set too, that's why one can know
|
.. glossary::
|
||||||
at any time if a value is a default value or not. Let's create a tree::
|
|
||||||
|
owner
|
||||||
|
|
||||||
|
When a value is set on an option, an owner is set too, that's why one can know
|
||||||
|
at any time if a value is a default value or not. Let's create a tree::
|
||||||
|
|
||||||
>>> var1 = UnicodeOption('var1', '', u'oui')
|
>>> var1 = UnicodeOption('var1', '', u'oui')
|
||||||
>>> od1 = OptionDescription('od1', '', [var1])
|
>>> od1 = OptionDescription('od1', '', [var1])
|
||||||
|
@ -399,183 +403,134 @@ Furthermore, let's retrieve the properties, delete and add the `hidden` property
|
||||||
tiramisu.error.PropertiesOptionError: trying to access to an option named:
|
tiramisu.error.PropertiesOptionError: trying to access to an option named:
|
||||||
var1 with properties ['hidden']
|
var1 with properties ['hidden']
|
||||||
|
|
||||||
The requirements
|
|
||||||
~~~~~~~~~~~~~~~~~~
|
|
||||||
|
|
||||||
Let's create an option wich has requirements::
|
.. _multi-option:
|
||||||
|
|
||||||
>>> from tiramisu.option import *
|
The multi-options
|
||||||
>>> from tiramisu.config import *
|
~~~~~~~~~~~~~~~~~~~~~
|
||||||
>>> var2 = UnicodeOption('var2', '', u'oui')
|
|
||||||
>>> var1 = UnicodeOption('var1', '', u'value', requires=[{'option':var2, 'expected':u'non', 'action':'hidden'}])
|
|
||||||
>>> var3 = UnicodeOption('var3', '', u'value', requires=[{'option':var2, 'expected':u'non', 'action':'hidden'}, {'option':var2, 'expected':u'non', 'action':'disabled'}])
|
|
||||||
>>> var4 = UnicodeOption('var4', '', u'oui')
|
|
||||||
>>> od1 = OptionDescription('od1', '', [var1, var2, var3])
|
|
||||||
>>> od2 = OptionDescription('od2', '', [var4], requires=[{'option':od1.var2, 'expected':u'oui', 'action':'hidden', 'inverse':True}])
|
|
||||||
>>> rootod = OptionDescription('rootod', '', [od1, od2])
|
|
||||||
>>> c = Config(rootod)
|
|
||||||
>>> c.read_write()
|
|
||||||
|
|
||||||
The requirement here is the dict `{'option':var2, 'expected':u'non',
|
.. glossary::
|
||||||
'action':'hidden'}` wich means that is the option `'od1.var2'` is set to
|
|
||||||
`'non'`, the option `'od1.var1'` is gonna be hidden. On the other hand, if the
|
|
||||||
option `'od1.var2'` is different from `'non'`, the option `'od1.var1'` is not
|
|
||||||
hidden any more::
|
|
||||||
|
|
||||||
>>> print c.cfgimpl_get_settings()[rootod.od1.var1]
|
multi-option
|
||||||
[]
|
|
||||||
>>> print c.od1.var1
|
|
||||||
value
|
|
||||||
>>> print c.od1.var2
|
|
||||||
oui
|
|
||||||
>>> c.od1.var2 = u'non'
|
|
||||||
>>> print c.cfgimpl_get_settings()[rootod.od1.var1]
|
|
||||||
['hidden']
|
|
||||||
>>> print c.od1.var1
|
|
||||||
Traceback (most recent call last):
|
|
||||||
[...]
|
|
||||||
tiramisu.error.PropertiesOptionError: trying to access to an option named:
|
|
||||||
var1 with properties ['hidden']
|
|
||||||
>>> c.od1.var2 = u'oui'
|
|
||||||
>>> print c.cfgimpl_get_settings()[rootod.od1.var1]
|
|
||||||
[]
|
|
||||||
>>> print c.od1.var1
|
|
||||||
value
|
|
||||||
|
|
||||||
The requirement on `od2` is `{'option':od1.var2, 'expected':u'oui',
|
Multi-options are normal options that have list of values (multiple values)
|
||||||
'action':'hidden', 'inverse':True}`, which means that if the option `od1.var2`
|
instead of values::
|
||||||
is set to `oui`, the option is not hidden (because of the `True` at the end of
|
|
||||||
the tuple wich means 'inverted', take a look at the :doc:`consistency`
|
|
||||||
document.)::
|
|
||||||
|
|
||||||
>>> print c.od2.var4
|
>>> var1 = UnicodeOption('var1', '', [u'val1', u'val2'], multi=True)
|
||||||
oui
|
>>> od1 = OptionDescription('od1', '', [var1])
|
||||||
>>> c.od1.var2 = u'non'
|
|
||||||
>>> print c.od2.var4
|
|
||||||
Traceback (most recent call last):
|
|
||||||
[...]
|
|
||||||
tiramisu.error.PropertiesOptionError: trying to access to an option named: od2 with properties ['hidden']
|
|
||||||
>>> c.od1.var2 = u'oui'
|
|
||||||
>>> print c.od2.var4
|
|
||||||
oui
|
|
||||||
|
|
||||||
Requirements can be accumulated
|
|
||||||
|
|
||||||
>>> print c.cfgimpl_get_settings()[rootod.od1.var3]
|
|
||||||
[]
|
|
||||||
>>> c.od1.var2 = u'non'
|
|
||||||
>>> print c.cfgimpl_get_settings()[rootod.od1.var3]
|
|
||||||
['disabled', 'hidden']
|
|
||||||
>>> c.od1.var2 = u'oui'
|
|
||||||
>>> print c.cfgimpl_get_settings()[rootod.od1.var3]
|
|
||||||
[]
|
|
||||||
|
|
||||||
Requirements can be accumulated for different or identical properties (inverted
|
|
||||||
or not)::
|
|
||||||
|
|
||||||
>>> a = UnicodeOption('var3', '', u'value', requires=[{'option':od1.var2,
|
|
||||||
'expected':'non', 'action':'hidden'}, {'option':od1.var1, 'expected':'oui',
|
|
||||||
'action':'hidden'}])
|
|
||||||
>>> a = UnicodeOption('var3', '', u'value', requires=[{'option':od1.var2,
|
|
||||||
'expected':'non', 'action':'hidden'}, {'option':od1.var1, 'excepted':'oui',
|
|
||||||
'action':'disabled', 'inverse':True}])
|
|
||||||
|
|
||||||
But it is not possible to have inverted requirements on the same property.
|
|
||||||
Here is an impossible situation::
|
|
||||||
|
|
||||||
>>> a = UnicodeOption('var3', '', u'value', requires=[{'option':od1.var2,
|
|
||||||
'expected':'non', 'action':'hidden'}, {'option':od1.var1, 'expected':'oui',
|
|
||||||
'hidden', True}])
|
|
||||||
|
|
||||||
Traceback (most recent call last):
|
|
||||||
[...]
|
|
||||||
ValueError: inconsistency in action types for option: var3 action: hidden
|
|
||||||
|
|
||||||
The calculations
|
|
||||||
~~~~~~~~~~~~~~~~~
|
|
||||||
|
|
||||||
Let's create four calculation functions::
|
|
||||||
|
|
||||||
def return_calc():
|
|
||||||
#return an unicode value
|
|
||||||
return u'calc'
|
|
||||||
|
|
||||||
def return_value(value):
|
|
||||||
return value
|
|
||||||
|
|
||||||
def return_value_param(param=u''):
|
|
||||||
return param
|
|
||||||
|
|
||||||
def return_no_value_if_non(value):
|
|
||||||
#if value is not u'non' return value
|
|
||||||
if value == u'non':
|
|
||||||
return None
|
|
||||||
else:
|
|
||||||
return value
|
|
||||||
|
|
||||||
Then we create four options using theses functions::
|
|
||||||
|
|
||||||
>>> var1 = UnicodeOption('var1', '', callback=return_calc)
|
|
||||||
>>> var2 = UnicodeOption('var2', '', callback=return_value, callback_params={'': (u'value',)})
|
|
||||||
>>> var3 = UnicodeOption('var3', '', callback=return_value_param, callback_params={'param': (u'value_param',)})
|
|
||||||
>>> var4 = UnicodeOption('var4', '', callback=return_no_value_if_non, callback_params={'': (('od1.var5', False),)})
|
|
||||||
>>> var5 = UnicodeOption('var5', '', u'oui')
|
|
||||||
>>> od1 = OptionDescription('od1', '', [var1, var2, var3, var4, var5])
|
|
||||||
>>> rootod = OptionDescription('rootod', '', [od1])
|
>>> rootod = OptionDescription('rootod', '', [od1])
|
||||||
>>> c = Config(rootod)
|
>>> c = Config(rootod)
|
||||||
>>> c.read_write()
|
>>> c.read_write()
|
||||||
|
|
||||||
The first option `var1` returns the result of the `return_calc` function, wich
|
A multi-option's value can be manipulated like a list::
|
||||||
is `u'calc'`::
|
|
||||||
|
|
||||||
>>> print c.od1.var1
|
>>> print c.od1.var1
|
||||||
calc
|
[u'val1', u'val2']
|
||||||
|
>>> c.od1.var1 = [u'var1']
|
||||||
The second option `var2` returns the result of the `return_value` fucntion,
|
|
||||||
wich is `value`. The parameter `u'value'` is passed to this function::
|
|
||||||
|
|
||||||
>>> print c.od1.var2
|
|
||||||
value
|
|
||||||
|
|
||||||
The third option `var3` returns the result of the function `return_value_param`
|
|
||||||
with the named parameter `param` and the value `u'value_param'`::
|
|
||||||
|
|
||||||
>>> print c.od1.var3
|
|
||||||
value_param
|
|
||||||
|
|
||||||
The fourth option `var4` returns the reslut of the function `return_no_value_if_non`
|
|
||||||
that is the value of `od1.var5` exceptif the value is u`non`::
|
|
||||||
|
|
||||||
>>> print c.od1.var4
|
|
||||||
oui
|
|
||||||
>>> c.od1.var5 = u'new'
|
|
||||||
>>> print c.od1.var4
|
|
||||||
new
|
|
||||||
>>> c.od1.var5 = u'non'
|
|
||||||
>>> print c.od1.var4
|
|
||||||
None
|
|
||||||
|
|
||||||
The calculation replaces the default value.
|
|
||||||
If we modify the value, the calculation is not carried out any more::
|
|
||||||
|
|
||||||
>>> print c.od1.var1
|
>>> print c.od1.var1
|
||||||
calc
|
[u'var1']
|
||||||
>>> c.od1.var1 = u'new_value'
|
>>> c.od1.var1.append(u'val3')
|
||||||
>>> print c.od1.var1
|
>>> print c.od1.var1
|
||||||
new_value
|
[u'var1', u'val3']
|
||||||
|
>>> c.od1.var1.pop(1)
|
||||||
To force the calculation to be carried out in some cases, one must add the
|
u'val3'
|
||||||
`frozen` and the `force_default_on_freeze` properties::
|
|
||||||
|
|
||||||
>>> c.cfgimpl_get_settings()[rootod.od1.var1].append('frozen')
|
|
||||||
>>> c.cfgimpl_get_settings()[rootod.od1.var1].append('force_default_on_freeze')
|
|
||||||
>>> print c.od1.var1
|
>>> print c.od1.var1
|
||||||
calc
|
[u'var1']
|
||||||
>>> c.cfgimpl_get_settings()[rootod.od1.var1].remove('frozen')
|
|
||||||
>>> c.cfgimpl_get_settings()[rootod.od1.var1].remove('force_default_on_freeze')
|
|
||||||
>>> print c.od1.var1
|
|
||||||
new_value
|
|
||||||
|
|
||||||
|
But it is not possible to set a value to a multi-option wich is not a list::
|
||||||
|
|
||||||
|
>>> c.od1.var1 = u'error'
|
||||||
|
Traceback (most recent call last):
|
||||||
|
[...]
|
||||||
|
ValueError: invalid value error for option var1 which must be a list
|
||||||
|
|
||||||
|
|
||||||
|
The master/slave groups
|
||||||
|
~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||||
|
|
||||||
|
|
||||||
|
.. glossary::
|
||||||
|
|
||||||
|
master/slave
|
||||||
|
|
||||||
|
A master/slave group is an :class:`~tiramisu.option.OptionDescription` and the
|
||||||
|
options that lives inside.
|
||||||
|
|
||||||
|
Inside this group, a special option, named master option, has the same name as
|
||||||
|
the group. The group (the option description) is set to type `master`.
|
||||||
|
All options in a master group is a multi-option (see :ref:`multi-option`).
|
||||||
|
The slave options have a `default_multi` attribute set to `True`::
|
||||||
|
|
||||||
|
>>> from tiramisu.setting import groups
|
||||||
|
>>> from tiramisu.config import Config
|
||||||
|
>>> from tiramisu.option import UnicodeOption, OptionDescription
|
||||||
|
>>>
|
||||||
|
>>> var1 = UnicodeOption('master', '', multi=True)
|
||||||
|
>>> var2 = UnicodeOption('slave1', '', multi=True)
|
||||||
|
>>> var3 = UnicodeOption('slave2', '', multi=True, default_multi=u"default")
|
||||||
|
>>>
|
||||||
|
>>> od1 = OptionDescription('master', '', [var1, var2, var3])
|
||||||
|
>>> od1.impl_set_group_type(groups.master)
|
||||||
|
>>>
|
||||||
|
>>> rootod = OptionDescription('rootod', '', [od1])
|
||||||
|
>>> c = Config(rootod)
|
||||||
|
>>> c.read_write()
|
||||||
|
|
||||||
|
The length of the lists can be modified::
|
||||||
|
|
||||||
|
>>> print c.master
|
||||||
|
master = []
|
||||||
|
slave1 = []
|
||||||
|
slave2 = []
|
||||||
|
>>> c.master.master.append(u'oui')
|
||||||
|
>>> print c.master
|
||||||
|
master = [u'oui']
|
||||||
|
slave1 = [None]
|
||||||
|
slave2 = [u'default']
|
||||||
|
>>> c.master.master = [u'non']
|
||||||
|
>>> print c.master
|
||||||
|
master = [u'non']
|
||||||
|
slave1 = [None]
|
||||||
|
slave2 = [u'default']
|
||||||
|
>>>
|
||||||
|
>>> c.master.master = [u'oui', u'non']
|
||||||
|
>>> print c.master
|
||||||
|
master = [u'oui', u'non']
|
||||||
|
slave1 = [None, None]
|
||||||
|
slave2 = [u'default', u'default']
|
||||||
|
|
||||||
|
But it is forbidden to change the lenght of a slave::
|
||||||
|
|
||||||
|
>>> c.master.slave1[0] = u'super'
|
||||||
|
>>> print c.master
|
||||||
|
master = [u'oui', u'non']
|
||||||
|
slave1 = [u'super', None]
|
||||||
|
slave2 = [u'default', u'default']
|
||||||
|
>>> c.master.slave1 = [u'new1', u'new2']
|
||||||
|
>>> print c.master
|
||||||
|
master = [u'oui', u'non']
|
||||||
|
slave1 = [u'new1', u'new2']
|
||||||
|
slave2 = [u'default', u'default']
|
||||||
|
>>> c.master.slave1 = [u'new1']
|
||||||
|
Traceback (most recent call last):
|
||||||
|
[...]
|
||||||
|
tiramisu.error.SlaveError: invalid len for the slave: slave1 which has master.master as master
|
||||||
|
>>> c.master.slave1 = [u'new1', u'new2', u'new3']
|
||||||
|
[...]
|
||||||
|
tiramisu.error.SlaveError: invalid len for the slave: slave1 which has master.master as master
|
||||||
|
|
||||||
|
you have to call the `pop` function on the master::
|
||||||
|
|
||||||
|
>>> c.master.master = [u'oui']
|
||||||
|
Traceback (most recent call last):
|
||||||
|
[...]
|
||||||
|
tiramisu.error.SlaveError: invalid len for the master: master which has slave1 as slave with greater len
|
||||||
|
>>> c.master.master.pop(0)
|
||||||
|
u'oui'
|
||||||
|
>>> print c.master
|
||||||
|
master = [u'non']
|
||||||
|
slave1 = [u'new2']
|
||||||
|
slave2 = [u'default']
|
||||||
|
|
||||||
Configuration's interesting methods
|
Configuration's interesting methods
|
||||||
------------------------------------------
|
------------------------------------------
|
||||||
|
|
|
@ -72,6 +72,96 @@ callback's action name (`hide`, `show`...), wich is a
|
||||||
:class:`~setting.Property()`. Requirements are validated in
|
:class:`~setting.Property()`. Requirements are validated in
|
||||||
:class:`setting.Setting`.
|
:class:`setting.Setting`.
|
||||||
|
|
||||||
|
|
||||||
|
Let's create an option wich has requirements::
|
||||||
|
|
||||||
|
>>> from tiramisu.option import *
|
||||||
|
>>> from tiramisu.config import *
|
||||||
|
>>> var2 = UnicodeOption('var2', '', u'oui')
|
||||||
|
>>> var1 = UnicodeOption('var1', '', u'value', requires=[{'option':var2, 'expected':u'non', 'action':'hidden'}])
|
||||||
|
>>> var3 = UnicodeOption('var3', '', u'value', requires=[{'option':var2, 'expected':u'non', 'action':'hidden'}, {'option':var2, 'expected':u'non', 'action':'disabled'}])
|
||||||
|
>>> var4 = UnicodeOption('var4', '', u'oui')
|
||||||
|
>>> od1 = OptionDescription('od1', '', [var1, var2, var3])
|
||||||
|
>>> od2 = OptionDescription('od2', '', [var4], requires=[{'option':od1.var2, 'expected':u'oui', 'action':'hidden', 'inverse':True}])
|
||||||
|
>>> rootod = OptionDescription('rootod', '', [od1, od2])
|
||||||
|
>>> c = Config(rootod)
|
||||||
|
>>> c.read_write()
|
||||||
|
|
||||||
|
The requirement here is the dict `{'option':var2, 'expected':u'non',
|
||||||
|
'action':'hidden'}` wich means that is the option `'od1.var2'` is set to
|
||||||
|
`'non'`, the option `'od1.var1'` is gonna be hidden. On the other hand, if the
|
||||||
|
option `'od1.var2'` is different from `'non'`, the option `'od1.var1'` is not
|
||||||
|
hidden any more::
|
||||||
|
|
||||||
|
>>> print c.cfgimpl_get_settings()[rootod.od1.var1]
|
||||||
|
[]
|
||||||
|
>>> print c.od1.var1
|
||||||
|
value
|
||||||
|
>>> print c.od1.var2
|
||||||
|
oui
|
||||||
|
>>> c.od1.var2 = u'non'
|
||||||
|
>>> print c.cfgimpl_get_settings()[rootod.od1.var1]
|
||||||
|
['hidden']
|
||||||
|
>>> print c.od1.var1
|
||||||
|
Traceback (most recent call last):
|
||||||
|
[...]
|
||||||
|
tiramisu.error.PropertiesOptionError: trying to access to an option named:
|
||||||
|
var1 with properties ['hidden']
|
||||||
|
>>> c.od1.var2 = u'oui'
|
||||||
|
>>> print c.cfgimpl_get_settings()[rootod.od1.var1]
|
||||||
|
[]
|
||||||
|
>>> print c.od1.var1
|
||||||
|
value
|
||||||
|
|
||||||
|
The requirement on `od2` is `{'option':od1.var2, 'expected':u'oui',
|
||||||
|
'action':'hidden', 'inverse':True}`, which means that if the option `od1.var2`
|
||||||
|
is set to `oui`, the option is not hidden (because of the `True` at the end of
|
||||||
|
the tuple wich means 'inverted', take a look at the :doc:`consistency`
|
||||||
|
document.)::
|
||||||
|
|
||||||
|
>>> print c.od2.var4
|
||||||
|
oui
|
||||||
|
>>> c.od1.var2 = u'non'
|
||||||
|
>>> print c.od2.var4
|
||||||
|
Traceback (most recent call last):
|
||||||
|
[...]
|
||||||
|
tiramisu.error.PropertiesOptionError: trying to access to an option named: od2 with properties ['hidden']
|
||||||
|
>>> c.od1.var2 = u'oui'
|
||||||
|
>>> print c.od2.var4
|
||||||
|
oui
|
||||||
|
|
||||||
|
Requirements can be accumulated
|
||||||
|
|
||||||
|
>>> print c.cfgimpl_get_settings()[rootod.od1.var3]
|
||||||
|
[]
|
||||||
|
>>> c.od1.var2 = u'non'
|
||||||
|
>>> print c.cfgimpl_get_settings()[rootod.od1.var3]
|
||||||
|
['disabled', 'hidden']
|
||||||
|
>>> c.od1.var2 = u'oui'
|
||||||
|
>>> print c.cfgimpl_get_settings()[rootod.od1.var3]
|
||||||
|
[]
|
||||||
|
|
||||||
|
Requirements can be accumulated for different or identical properties (inverted
|
||||||
|
or not)::
|
||||||
|
|
||||||
|
>>> a = UnicodeOption('var3', '', u'value', requires=[{'option':od1.var2,
|
||||||
|
'expected':'non', 'action':'hidden'}, {'option':od1.var1, 'expected':'oui',
|
||||||
|
'action':'hidden'}])
|
||||||
|
>>> a = UnicodeOption('var3', '', u'value', requires=[{'option':od1.var2,
|
||||||
|
'expected':'non', 'action':'hidden'}, {'option':od1.var1, 'excepted':'oui',
|
||||||
|
'action':'disabled', 'inverse':True}])
|
||||||
|
|
||||||
|
But it is not possible to have inverted requirements on the same property.
|
||||||
|
Here is an impossible situation::
|
||||||
|
|
||||||
|
>>> a = UnicodeOption('var3', '', u'value', requires=[{'option':od1.var2,
|
||||||
|
'expected':'non', 'action':'hidden'}, {'option':od1.var1, 'expected':'oui',
|
||||||
|
'hidden', True}])
|
||||||
|
|
||||||
|
Traceback (most recent call last):
|
||||||
|
[...]
|
||||||
|
ValueError: inconsistency in action types for option: var3 action: hidden
|
||||||
|
|
||||||
Validation upon a whole configuration object
|
Validation upon a whole configuration object
|
||||||
----------------------------------------------
|
----------------------------------------------
|
||||||
|
|
||||||
|
@ -87,6 +177,36 @@ Other hooks are availables to validate upon a whole configuration at any time,
|
||||||
for example the consistency between two options (typically, an
|
for example the consistency between two options (typically, an
|
||||||
:class:`IPOption` and a :class:`NetworkOption`).
|
:class:`IPOption` and a :class:`NetworkOption`).
|
||||||
|
|
||||||
|
Let's define validator (wich is a normal python function)::
|
||||||
|
|
||||||
|
>>> def valid_a(value, letter=''):
|
||||||
|
... return value.startswith(letter)
|
||||||
|
|
||||||
|
Here is an option wich uses this validator::
|
||||||
|
|
||||||
|
>>> var1 = UnicodeOption('var1', '', u'oui', validator=valid_a, validator_args={'letter': 'o'})
|
||||||
|
>>>
|
||||||
|
>>> od1 = OptionDescription('od1', '', [var1])
|
||||||
|
>>>
|
||||||
|
>>> rootod = OptionDescription('rootod', '', [od1])
|
||||||
|
>>>
|
||||||
|
>>> c = Config(rootod)
|
||||||
|
>>> c.read_write()
|
||||||
|
|
||||||
|
The validation is applied at the modification time::
|
||||||
|
|
||||||
|
>>> c.od1.var1 = u'non'
|
||||||
|
Traceback (most recent call last):
|
||||||
|
[...]
|
||||||
|
ValueError: invalid value non for option var1
|
||||||
|
>>> c.od1.var1 = u'oh non'
|
||||||
|
|
||||||
|
Il est possible de désactiver la validation :
|
||||||
|
|
||||||
|
>>> c.cfgimpl_get_settings().remove('validator')
|
||||||
|
>>> c.od1.var1 = u'non'
|
||||||
|
|
||||||
|
|
||||||
Values that are calculated
|
Values that are calculated
|
||||||
--------------------------------
|
--------------------------------
|
||||||
|
|
||||||
|
@ -111,3 +231,84 @@ attribute.
|
||||||
attribute `force_store_value` enabled is considered to be modified at
|
attribute `force_store_value` enabled is considered to be modified at
|
||||||
the first calculation
|
the first calculation
|
||||||
|
|
||||||
|
Let's create four calculation functions::
|
||||||
|
|
||||||
|
def return_calc():
|
||||||
|
#return an unicode value
|
||||||
|
return u'calc'
|
||||||
|
|
||||||
|
def return_value(value):
|
||||||
|
return value
|
||||||
|
|
||||||
|
def return_value_param(param=u''):
|
||||||
|
return param
|
||||||
|
|
||||||
|
def return_no_value_if_non(value):
|
||||||
|
#if value is not u'non' return value
|
||||||
|
if value == u'non':
|
||||||
|
return None
|
||||||
|
else:
|
||||||
|
return value
|
||||||
|
|
||||||
|
Then we create four options using theses functions::
|
||||||
|
|
||||||
|
>>> var1 = UnicodeOption('var1', '', callback=return_calc)
|
||||||
|
>>> var2 = UnicodeOption('var2', '', callback=return_value, callback_params={'': (u'value',)})
|
||||||
|
>>> var3 = UnicodeOption('var3', '', callback=return_value_param, callback_params={'param': (u'value_param',)})
|
||||||
|
>>> var4 = UnicodeOption('var4', '', callback=return_no_value_if_non, callback_params={'': (('od1.var5', False),)})
|
||||||
|
>>> var5 = UnicodeOption('var5', '', u'oui')
|
||||||
|
>>> od1 = OptionDescription('od1', '', [var1, var2, var3, var4, var5])
|
||||||
|
>>> rootod = OptionDescription('rootod', '', [od1])
|
||||||
|
>>> c = Config(rootod)
|
||||||
|
>>> c.read_write()
|
||||||
|
|
||||||
|
The first option `var1` returns the result of the `return_calc` function, wich
|
||||||
|
is `u'calc'`::
|
||||||
|
|
||||||
|
>>> print c.od1.var1
|
||||||
|
calc
|
||||||
|
|
||||||
|
The second option `var2` returns the result of the `return_value` fucntion,
|
||||||
|
wich is `value`. The parameter `u'value'` is passed to this function::
|
||||||
|
|
||||||
|
>>> print c.od1.var2
|
||||||
|
value
|
||||||
|
|
||||||
|
The third option `var3` returns the result of the function `return_value_param`
|
||||||
|
with the named parameter `param` and the value `u'value_param'`::
|
||||||
|
|
||||||
|
>>> print c.od1.var3
|
||||||
|
value_param
|
||||||
|
|
||||||
|
The fourth option `var4` returns the reslut of the function `return_no_value_if_non`
|
||||||
|
that is the value of `od1.var5` exceptif the value is u`non`::
|
||||||
|
|
||||||
|
>>> print c.od1.var4
|
||||||
|
oui
|
||||||
|
>>> c.od1.var5 = u'new'
|
||||||
|
>>> print c.od1.var4
|
||||||
|
new
|
||||||
|
>>> c.od1.var5 = u'non'
|
||||||
|
>>> print c.od1.var4
|
||||||
|
None
|
||||||
|
|
||||||
|
The calculation replaces the default value.
|
||||||
|
If we modify the value, the calculation is not carried out any more::
|
||||||
|
|
||||||
|
>>> print c.od1.var1
|
||||||
|
calc
|
||||||
|
>>> c.od1.var1 = u'new_value'
|
||||||
|
>>> print c.od1.var1
|
||||||
|
new_value
|
||||||
|
|
||||||
|
To force the calculation to be carried out in some cases, one must add the
|
||||||
|
`frozen` and the `force_default_on_freeze` properties::
|
||||||
|
|
||||||
|
>>> c.cfgimpl_get_settings()[rootod.od1.var1].append('frozen')
|
||||||
|
>>> c.cfgimpl_get_settings()[rootod.od1.var1].append('force_default_on_freeze')
|
||||||
|
>>> print c.od1.var1
|
||||||
|
calc
|
||||||
|
>>> c.cfgimpl_get_settings()[rootod.od1.var1].remove('frozen')
|
||||||
|
>>> c.cfgimpl_get_settings()[rootod.od1.var1].remove('force_default_on_freeze')
|
||||||
|
>>> print c.od1.var1
|
||||||
|
new_value
|
||||||
|
|
Loading…
Reference in New Issue