You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
calculate-utils-4-lib/tests/vars/test_alt_vars.py

372 lines
16 KiB

import pytest
from calculate.vars.alt_datavars import NamespaceNode, VariableNode,\
Namespace, Variable, Dependence,\
CyclicVariableError, HashType,\
StringType, IntegerType, VariableType,\
VariableError, TableType
from calculate.utils.files import stderr_devnull
@pytest.mark.alt_vars
class TestNamespace:
# Сначала тестируем классы и методы необходимые для построения дерева
# переменных и пространств имен.
def test_if_NamespaceNode_just_initialized_with_its_name__the_NamespaceNode_object_contains_empty_namespaces_and_variables_dictionaries_and_fullname_method_returns_only_the_namespace_s_name(self):
namespace_1 = NamespaceNode('namespace_1')
assert namespace_1.namespaces == dict()
assert namespace_1.variables == dict()
assert namespace_1.fullname == 'namespace_1'
def test_if_namespace_node_added_in_an_other_namespace_node__a_parent_namespace_node_contains_child_namespace_in_its_namespaces_dictionary_and_child_namespace_object_has_parent_namespace_in_its_parent_attribute_and_its_fullname_method_returns_names_of_both_namespaces(self):
namespace_1 = NamespaceNode('namespace_1')
namespace_2 = NamespaceNode('namespace_2')
namespace_1.add_namespace(namespace_2)
assert namespace_1.namespaces == {'namespace_2': namespace_2}
assert namespace_1.variables == dict()
assert namespace_1.fullname == 'namespace_1'
assert namespace_1.namespace_2 == namespace_2
assert namespace_1['namespace_2'] == namespace_2
assert namespace_2.namespaces == dict()
assert namespace_2.variables == dict()
assert namespace_2.parent == namespace_1
assert namespace_2.fullname == 'namespace_1.namespace_2'
def test_if_two_VariableNode_objects_are_initialized_and_added_to_a_namespace__the_NamespaceNode_object_contains_this_variables_and_can_be_used_to_get_variables_values_and_variables_have_namespace_name_in_their_fullnames(self):
namespace_1 = NamespaceNode('namespace_1')
variable_1 = VariableNode('var_1', namespace_1, source='value_1')
variable_2 = VariableNode('var_2', namespace_1, source='value_2')
assert namespace_1.namespaces == dict()
assert namespace_1.variables == {'var_1': variable_1,
'var_2': variable_2}
assert namespace_1.fullname == 'namespace_1'
assert namespace_1.var_1 == 'value_1'
assert namespace_1['var_1'] == variable_1
assert namespace_1.var_2 == 'value_2'
assert namespace_1['var_2'] == variable_2
assert namespace_1['var_1'].fullname == 'namespace_1.var_1'
assert namespace_1['var_2'].fullname == 'namespace_1.var_2'
def test_find_vars(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
Variable('var_1', source='val_1')
Variable('var_2', source=2, type=IntegerType)
Variable('var_3', source=4, type=IntegerType)
with Namespace('namespace_1_1'):
Variable('var_1', source='val_1')
assert Dependence._find_variable('.var_1') ==\
datavars.namespace_1.namespace_1_1['var_1']
assert Dependence._find_variable('..var_3') ==\
datavars.namespace_1['var_3']
with Namespace('namespace_2'):
assert Dependence._find_variable('namespace_1.var_2') ==\
datavars.namespace_1['var_2']
def test_compare_two_dependencies_equal(self):
namespace_1 = NamespaceNode('namespace_1')
variable_1 = VariableNode('var_1', namespace_1, source=2,
variable_type=IntegerType)
variable_2 = VariableNode('var_2', namespace_1, source=4,
variable_type=IntegerType)
dependence_1 = Dependence(
variable_1, variable_2, depend=lambda arg_1, arg_2:
'greater' if arg_1.value > arg_2.value else 'less')
dependence_2 = Dependence(
variable_1, variable_2, depend=lambda var_1, var_2:
'greater' if var_1.value > var_2.value else 'less')
assert dependence_1 == dependence_2
def test_compare_two_dependencies_equal_but_one_is_function_and_other_is_lambda(self):
namespace_1 = NamespaceNode('namespace_1')
variable_1 = VariableNode('var_1', namespace_1, source=2,
variable_type=IntegerType)
variable_2 = VariableNode('var_2', namespace_1, source=4,
variable_type=IntegerType)
dependence_1 = Dependence(
variable_1, variable_2, depend=lambda arg_1, arg_2:
'greater' if arg_1.value > arg_2.value else 'less')
def comparator(var_1, var_2):
if var_1.value > var_2.value:
return 'greater'
else:
return 'less'
dependence_2 = Dependence(variable_1, variable_2, depend=comparator)
assert dependence_1 == dependence_2
def test_compare_two_dependencies_not_equal(self):
namespace_1 = NamespaceNode('namespace_1')
variable_1 = VariableNode('var_1', namespace_1, source=2,
variable_type=IntegerType)
variable_2 = VariableNode('var_2', namespace_1, source=4,
variable_type=IntegerType)
dependence_1 = Dependence(
variable_1, variable_2, depend=lambda arg_1, arg_2:
'less' if arg_1.value > arg_2.value else 'greater')
dependence_2 = Dependence(
variable_1, variable_2, depend=lambda var_1, var_2:
'greater' if var_1.value > var_2.value else 'less')
assert dependence_1 != dependence_2
def test_compare_two_dependencies_not_equal_but_one_is_function_and_other_is_lambda(self):
namespace_1 = NamespaceNode('namespace_1')
variable_1 = VariableNode('var_1', namespace_1, source=2,
variable_type=IntegerType)
variable_2 = VariableNode('var_2', namespace_1, source=4,
variable_type=IntegerType)
dependence_1 = Dependence(
variable_1, variable_2, depend=lambda arg_1, arg_2:
'greater' if arg_1.value > arg_2.value else 'less')
def comparator(var_1, var_2):
if var_1 > var_2:
return 'less'
else:
return 'greater'
dependence_2 = Dependence(variable_1, variable_2, depend=comparator)
assert dependence_1 != dependence_2
def test_if_a_variable_subscribed_to_two_other_variables_using_set_function__the_(self):
namespace_1 = NamespaceNode('namespace_1')
variable_1 = VariableNode('var_1', namespace_1, source=2,
variable_type=IntegerType)
variable_2 = VariableNode('var_2', namespace_1, source=4,
variable_type=IntegerType)
namespace_2 = NamespaceNode('namespace_2')
variable = VariableNode('var_1', namespace_2)
variable.source = Dependence(
variable_1, variable_2, depend=lambda var_1, var_2:
'greater' if var_1.value > var_2.value else 'less')
assert namespace_2.var_1 == 'less'
namespace_1['var_1'].source = 5
assert namespace_2.var_1 == 'greater'
# Теперь тестируем интерфейс создания переменных.
def test_api(self):
Namespace.reset()
with Namespace('namespace_1'):
Variable('var_1', source='val_1')
var_2 = Variable('var_2', source=2, type=IntegerType)
Variable('var_3', source=4, type=IntegerType)
with Namespace('namespace_2'):
Variable('var_1', source=Dependence(
var_2, '..namespace_1.var_3', depend=lambda arg_1, arg_2:
'greater' if arg_1.value > arg_2.value else 'less'))
with Namespace('namespace_2_1'):
Variable('var_1', source='val_1')
datavars = Namespace.datavars
assert datavars.namespace_1.var_1 == 'val_1'
assert datavars.namespace_1.var_2 == 2
assert datavars.namespace_1.var_3 == 4
assert datavars.namespace_2.var_1 == 'less'
assert datavars.namespace_2.namespace_2_1.var_1 == 'val_1'
datavars.namespace_1['var_2'].source = 5
assert datavars.namespace_2.var_1 == 'greater'
def test_rewriting_if_source_changed_to_a_value(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
var_1 = Variable('var_1', source='value_1')
Variable('var_2', source=Dependence(
var_1, depend=lambda arg_1:
'from var_1: {}'.format(arg_1.value)))
assert datavars.namespace_1.var_1 == 'value_1'
assert datavars.namespace_1.var_2 == 'from var_1: value_1'
with Namespace('namespace_1'):
Variable('var_1', source='value_2')
assert datavars.namespace_1.var_1 == 'value_2'
assert datavars.namespace_1.var_2 == 'from var_1: value_2'
def test_rewriting_if_source_changed_to_a_dependence(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
Variable('var_1', source='value_1')
Variable('var_2', source=Dependence(
'.var_1', depend=lambda arg_1:
'from var_1: {}'.format(arg_1.value)))
Variable('var_3', source='value_3')
assert datavars.namespace_1.var_1 == 'value_1'
assert datavars.namespace_1.var_2 == 'from var_1: value_1'
with Namespace('namespace_1'):
Variable('var_2', source=Dependence(
'.var_3', depend=lambda arg_1:
'from var_3: {}'.format(arg_1.value)))
assert datavars.namespace_1.var_2 == 'from var_3: value_3'
def test_cyclic_dependence(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
Variable('var_1', source='value_1')
Variable('var_2', source=Dependence(
'namespace_1.var_1', depend=lambda arg_1:
'from var_1: {}'.format(arg_1.value)))
def comparator(arg_1):
return 'from var_2: {}'.format(arg_1.value)
Variable('var_3', source=Dependence('.var_2', depend=comparator))
Variable('var_1',
source=Dependence('.var_3', depend=lambda arg_1:
'from var_3: {}'.format(arg_1.value)))
with pytest.raises(CyclicVariableError):
datavars.namespace_1.var_3
def test_hash(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
Variable('var_1', source='value_1', type=StringType)
Variable('var_2', type=HashType, source={'key_1': 'value_1',
'key_2': 'value_2'})
Variable('var_3', source='value_3', type=StringType)
def depend_hash(arg_1, arg_2):
return {'key_1': 'value',
'key_2': arg_1.value,
'key_3': arg_2.value}
Variable('var_4', type=HashType,
source=Dependence('.var_1', '.var_2.key_1',
depend=depend_hash))
assert datavars.namespace_1.var_2.key_1 == 'value_1'
assert datavars.namespace_1.var_4.key_1 == 'value'
assert datavars.namespace_1.var_4.key_2 == 'value_1'
assert datavars.namespace_1.var_4.key_3 == 'value_1'
with Namespace('namespace_1'):
Variable('var_1', source='other_value', type=StringType)
Variable('var_2', source={'key_1': 'another_value',
'key_2': 'value_2'})
assert datavars.namespace_1.var_2.key_1 == 'another_value'
assert datavars.namespace_1.var_4.key_2 == 'other_value'
assert datavars.namespace_1.var_4.key_3 == 'another_value'
def test_getting_all_hash_to_depend_function(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
Variable('var_1', source='value_1', type=StringType)
Variable('var_2', type=HashType, source={'key_1': 'value_1',
'key_2': 'value_2'})
Variable('var_3', source='value_3', type=StringType)
def depend_hash(arg_1):
return arg_1.value['key_1']
Variable('var_4', type=StringType,
source=Dependence('.var_2', depend=depend_hash))
assert datavars.namespace_1.var_4 == 'value_1'
def test_readonly(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
Variable('var_1', source='value_1', type=StringType, readonly=True)
with Namespace('namespace_1'):
print('namespace_1:')
for name, namespace in datavars.namespaces.items():
print(namespace.fullname)
for name, variable in datavars.variables.items():
print(variable.fullname)
with pytest.raises(VariableError):
Variable('var_1', source='value_2', type=StringType)
def test_source_function_without_vars(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
def source_function():
return 'value_from_function'
Variable('var', source=Dependence(depend=source_function),
type=VariableType)
assert datavars.namespace_1.var == 'value_from_function'
def test_source_function_with_dynamic_subscription(self):
Namespace.reset()
datavars = Namespace.datavars
with Namespace('namespace_1'):
Variable('var_1', source=5, type=IntegerType)
Variable('var_2', source='less')
Variable('var_3', source='greater')
def solver(arg_1, arg_2, arg_3):
if arg_1.value < 6:
return arg_2.value
else:
return arg_3.value
Variable('var_4', type=StringType,
source=Dependence('.var_1', '.var_2', '.var_3',
depend=solver))
assert datavars.namespace_1['var_4'].value is None
def test_tables(self):
Namespace.reset()
# datavars = Namespace.datavars
with Namespace('main'):
Variable('chroot', source='/', type=StringType, readonly=True)
with Namespace('os'):
def source_function(chroot_path):
from portage.package.ebuild.config import config
if chroot_path == '/':
with stderr_devnull():
return config()
Variable('config', source=Dependence('main.chroot',
depend=source_function),
type=VariableType)
Variable('var_1', source='value_1', type=StringType)
Variable('var_2', type=TableType, source=[{'name': 'name_1',
'value': 'value_1'},
{'name': 'name_2',
'value': 'value_2'},
{'name': 'name_3',
'value': 'value_3'}])