rougail/tests/test_1_flattener.py

278 lines
9.6 KiB
Python
Raw Normal View History

from os import getcwd
2019-11-23 08:17:35 +01:00
from os.path import isfile, join, isdir
from pytest import fixture, raises
2022-11-02 22:52:50 +01:00
from os import listdir, environ, makedirs
from json import load, dumps, loads
from yaml import dump as ydump
2019-11-23 08:17:35 +01:00
2022-01-19 18:24:00 +01:00
environ['TIRAMISU_LOCALE'] = 'en'
2021-02-14 10:10:48 +01:00
from rougail import RougailConvert, RougailConfig
2020-07-20 18:13:53 +02:00
from rougail.error import DictConsistencyError
2019-11-23 08:17:35 +01:00
dico_dirs = 'tests/dictionaries'
2019-11-23 08:17:35 +01:00
test_ok = set()
test_raise = set()
for test in listdir(dico_dirs):
if isdir(join(dico_dirs, test)):
2020-07-29 08:59:40 +02:00
if isdir(join(dico_dirs, test, 'tiramisu')):
2019-11-23 08:17:35 +01:00
test_ok.add(test)
2020-07-20 18:13:53 +02:00
elif test != '__pycache__':
2019-11-23 08:17:35 +01:00
test_raise.add(test)
excludes = set([])
2022-11-02 22:52:50 +01:00
#excludes = set(['45multi_family_order'])
2019-11-23 08:17:35 +01:00
test_ok -= excludes
test_raise -= excludes
2022-11-03 22:16:52 +01:00
#test_ok = ['01base_multi_notuniq']
2020-12-22 21:11:14 +01:00
#test_ok = []
2021-01-06 22:20:33 +01:00
#test_raise = ['80auto_autofreeze']
2020-12-24 17:37:14 +01:00
#test_raise = []
2019-11-23 08:17:35 +01:00
ORI_DIR = getcwd()
2020-11-08 09:43:45 +01:00
debug = False
#debug = True
2019-11-23 08:17:35 +01:00
test_ok = list(test_ok)
test_raise = list(test_raise)
test_ok.sort()
test_raise.sort()
2022-11-03 22:16:52 +01:00
test_dirs = []
for ext in ['xml', 'yml']:
for val in test_ok:
test_dirs.append((ext, val))
@fixture(scope="module", params=test_dirs)
2019-11-23 08:17:35 +01:00
def test_dir(request):
return request.param
2022-11-03 22:16:52 +01:00
test_err_dirs = []
for ext in ['xml', 'yml']:
for val in test_raise:
test_err_dirs.append((ext, val))
@fixture(scope="module", params=test_err_dirs)
2019-11-23 08:17:35 +01:00
def test_dir_error(request):
return request.param
2022-11-02 22:52:50 +01:00
def xml_to_yaml(filename, destfilename):
import xmltodict
def reorganize_variable(value, level):
move = None
new_value = []
for type_ in ['variable', 'family']:
if type_ in value:
subvalue = value[type_]
if isinstance(subvalue, list):
values = []
2022-11-02 22:52:50 +01:00
for val in subvalue:
if 'variable' in val or 'family' in val:
move_, val = reorganize_variable(val, level + 1)
if move_:
move = move_
if filename == 'tests/dictionaries/45multi_family_order/xml/00-base.xml' and \
val['@name'] == 'variable4':
#hack
move = val
else:
values.append(val)
if values:
new_value.append({type_: values})
2022-11-02 22:52:50 +01:00
else:
if 'variable' in subvalue or 'family' in subvalue:
move_, subvalue = reorganize_variable(subvalue, level + 1)
if move_:
move = move_
new_value.append({type_: [subvalue]})
2022-11-02 22:52:50 +01:00
if level == 0:
return new_value
if level == 1 and move:
new_value.append({'variable': [move]})
2022-11-02 22:52:50 +01:00
dico = {k: v for k, v in value.items() if k not in ['variable', 'family']}
dico['variables'] = new_value
return move, dico
def _xml_to_yaml(dico, root=False):
for key, value in dict(dico).items():
del dico[key]
if root and key == 'variables':
value = reorganize_variable(value, 0)
if isinstance(value, dict):
_xml_to_yaml(value)
if isinstance(value, list):
dico[key] = value
for idx, val in enumerate(value):
if isinstance(val, dict):
_xml_to_yaml(val)
elif isinstance(val, (str, bool)):
dico[key][idx] = {'text': val}
else:
2022-11-03 22:16:52 +01:00
if value == 'True':
value = True
elif value == 'False':
value = False
2022-11-04 20:16:57 +01:00
else:
converted = False
try:
# if it's a number
nvalue = int(value)
assert str(nvalue) == value
value = nvalue
converted = True
except:
pass
if not converted:
try:
# if it's a number
nvalue = float(value)
assert str(nvalue) == value
value = nvalue
converted = True
except:
pass
2022-11-02 22:52:50 +01:00
if key.startswith('@'):
# remove @
dico[key[1:]] = value
elif key.startswith('#'):
dico[key[1:]] = value
else:
if key not in ['variable', 'family'] and not isinstance(value, list):
if not value:
if key == 'override':
dico[key] = value
elif key == 'value':
dico[key] = [{'text': value}]
2022-11-04 20:16:57 +01:00
elif isinstance(value, (str, bool, int, float)):
2022-11-02 22:52:50 +01:00
dico[key] = [{'text': value}]
else:
dico[key] = [value]
else:
dico[key] = value
with open(filename, 'rb') as fh:
dico = loads(dumps(xmltodict.parse(fh)['rougail'])) # , attr_prefix="")
_xml_to_yaml(dico, root=True)
with open(destfilename, 'w') as fh:
ydump(dico, fh, sort_keys=False)
def build_yml(test_dir, dirname):
makedirs(dirname)
for filename in listdir(join(test_dir, 'xml')):
if not isfile(join(test_dir, 'xml', filename)):
continue
xml_to_yaml(join(test_dir, 'xml', filename), join(dirname, filename[:-4] + '.yml'))
if isdir(join(test_dir, 'xml', 'subfolder')):
makedirs(join(dirname, 'subfolder'))
for filename in listdir(join(test_dir, 'xml', 'subfolder')):
xml_to_yaml(join(test_dir, 'xml', 'subfolder', filename), join(dirname, 'subfolder', filename[:-4] + '.yml'))
if isdir(join(test_dir, 'xml', 'extra_dirs')):
makedirs(join(dirname, 'extra_dirs'))
for extra in listdir(join(test_dir, 'xml', 'extra_dirs')):
subfolder = join(test_dir, 'xml', 'extra_dirs', extra)
if not isdir(subfolder):
continue
makedirs(join(dirname, 'extra_dirs', extra))
for filename in listdir(subfolder):
xml_to_yaml(join(test_dir, 'xml', 'extra_dirs', extra, filename), join(dirname, 'extra_dirs', extra, filename[:-4] + '.yml'))
def load_rougail_object(test_dir, ext):
if isfile(join(test_dir, f'no_{ext}')):
return
2022-10-01 22:27:22 +02:00
rougailconfig = RougailConfig.copy()
rougailconfig['functions_file'] = join(dico_dirs, '../eosfunc/test.py')
2022-11-02 22:52:50 +01:00
dirs = [join(test_dir, ext)]
if ext == 'yml' and not isdir(dirs[0]):
build_yml(test_dir, dirs[0])
subfolder = join(test_dir, ext, 'subfolder')
2019-11-23 08:17:35 +01:00
if isdir(subfolder):
2020-12-24 16:02:20 +01:00
dirs.append(subfolder)
2022-10-01 22:27:22 +02:00
rougailconfig['dictionaries_dir'] = dirs
rougailconfig['extra_dictionaries'] = {}
2022-11-02 22:52:50 +01:00
if isdir(join(test_dir, ext, 'extra_dirs')):
extras = listdir(join(test_dir, ext, 'extra_dirs'))
extras.sort()
for extra in extras:
2022-11-02 22:52:50 +01:00
subfolder = join(test_dir, ext, 'extra_dirs', extra)
if isdir(subfolder):
2022-10-01 22:27:22 +02:00
rougailconfig['extra_dictionaries'][extra] = [subfolder]
return RougailConvert(rougailconfig)
def launch_flattener(eolobj, path_prefix=None):
eolobj.load_dictionaries(path_prefix=path_prefix)
def save(test_dir, eolobj, multi=False):
2021-02-14 10:10:48 +01:00
tiramisu_objects = eolobj.save(None)
2020-12-24 17:37:14 +01:00
if 'children=[]' in tiramisu_objects.split('\n')[-2]:
raise Exception('empty tiramisu object?')
2020-07-29 08:59:40 +02:00
tiramisu_dir = join(test_dir, 'tiramisu')
2020-12-24 12:41:10 +01:00
if isdir(tiramisu_dir):
2022-10-01 22:27:22 +02:00
if not multi:
filename = 'base.py'
else:
filename = 'multi.py'
tiramisu_file = join(tiramisu_dir, filename)
2020-12-24 12:41:10 +01:00
if not isfile(tiramisu_file) or debug:
with open(tiramisu_file, 'w') as fh:
fh.write(tiramisu_objects)
with open(tiramisu_file, 'r') as fh:
tiramisu_objects_ori = fh.read()
assert tiramisu_objects == tiramisu_objects_ori
2019-11-23 08:17:35 +01:00
def test_dictionary(test_dir):
2022-11-03 22:16:52 +01:00
ext, test_dir_ = test_dir
assert getcwd() == ORI_DIR
test_dir_ = join(dico_dirs, test_dir_)
eolobj = load_rougail_object(test_dir_, ext)
if not eolobj:
return
launch_flattener(eolobj)
save(test_dir_, eolobj)
assert getcwd() == ORI_DIR
2022-10-01 22:27:22 +02:00
def test_dictionary_multi(test_dir):
2022-11-03 22:16:52 +01:00
ext, test_dir_ = test_dir
2022-10-01 22:27:22 +02:00
assert getcwd() == ORI_DIR
2022-11-03 22:16:52 +01:00
test_dir_ = join(dico_dirs, test_dir_)
eolobj = load_rougail_object(test_dir_, ext)
if not eolobj:
return
2022-10-01 22:27:22 +02:00
launch_flattener(eolobj, path_prefix='1')
launch_flattener(eolobj, path_prefix='2')
2022-11-03 22:16:52 +01:00
save(test_dir_, eolobj, multi=True)
assert getcwd() == ORI_DIR
2019-11-23 08:17:35 +01:00
def test_error_dictionary(test_dir_error):
2022-11-03 22:16:52 +01:00
ext, test_dir = test_dir_error
assert getcwd() == ORI_DIR
test_dir = join(dico_dirs, test_dir)
errno = 0
eolobj = load_rougail_object(test_dir, ext)
if eolobj is None:
return
for i in listdir(test_dir):
if i.startswith('errno_'):
if errno:
raise Exception('multiple errno')
errno = int(i.split('_')[1])
with raises(DictConsistencyError) as err:
launch_flattener(eolobj)
save(test_dir, eolobj)
if err.value.errno != errno:
print(f'expected errno: {errno}, errno: {err.value.errno}')
launch_flattener(eolobj)
save(test_dir, eolobj)
assert getcwd() == ORI_DIR