Added formats

packages
commit fce2667231

@ -0,0 +1,5 @@
install:
sudo python ./setup.py install --single-version-externally-managed --root=/
test: install
pytest

@ -0,0 +1,189 @@
# vim: fileencoding=utf-8
#
from collections import OrderedDict
from jinja2 import Environment, PackageLoader
from pprint import pprint
try:
from lxml.etree.ElementTree import fromstring
except ImportError:
from xml.etree.ElementTree import fromstring
class BaseFormat():
def __init__(self, processing_methods):
self._processing_methods = processing_methods
self._document_dictionary = OrderedDict()
self._item_to_add = OrderedDict()
self._format = 'none'
self.TEMPLATES_DIRECTORY = 'templates'
self._fatal_error_flag = False
self._ready_to_update = False
self._match = False
self._need_finish = False
self._comments_processing = False
self._join_before = False
self._join_before_in_areas = False
# для отладки.
self._line_timer = 0
def _lines_to_dictionary(self, document_lines):
# print('Lines processing...')
for line in document_lines:
# print(self._line_timer, '\t', line)
for processing_method in self._processing_methods:
processing_method(line)
if self._fatal_error_flag:
# Действия если файл невозможно разобрать.
print('Can not parse file.')
self._document_dictionary = OrderedDict()
return
if self._is_match():
if self._is_ready_to_update():
self._document_dictionary.update(self._item_to_add)
break
else:
# Действия если не удалось разобрать строку.
print('Line', self._line_timer,
'is not correct. Can not parse file.')
self._document_dictionary = OrderedDict()
return
self._line_timer += 1
if self._need_finish:
self._finish_method()
def _parse_xml_to_dictionary(self, xml_document_text):
root = fromstring(xml_document_text)
self._document_dictionary = self._processing_methods[root.tag](root)
def print_dictionary(self):
pprint(self._document_dictionary)
def join_template(self, template):
self._join(self._document_dictionary,
template._document_dictionary,
self._join_before)
def _get_list_of_logic_lines(self, text):
list_of_lines = []
lines_to_join = []
for line in text.splitlines():
line = line.strip()
if line == '':
continue
if not line.endswith("\\"):
lines_to_join.append(line)
joined_line = "".join(lines_to_join)
list_of_lines.append(joined_line)
lines_to_join = []
else:
lines_to_join.append(line[:-1])
return list_of_lines
def _join(self, original, template, join_before):
if template == OrderedDict():
return
if join_before:
forwarded_items = OrderedDict()
for key_value in template:
if key_value[0] == '!':
# Удаление соответствующего элемента из original.
if isinstance(key_value, tuple):
item_to_delete = ('',) + key_value[1:]
elif isinstance(key_value, str):
item_to_delete = key_value[1:]
if item_to_delete in original.keys():
original.pop(item_to_delete)
elif key_value[0] == '-':
# Замена соответствующего элемента из original.
if isinstance(key_value, tuple):
item_to_replace = ('',) + key_value[1:]
elif isinstance(key_value, str):
item_to_replace = key_value[1:]
if item_to_replace not in original.keys():
continue
if isinstance(template[key_value], dict) and\
template[key_value] == OrderedDict():
original.pop(item_to_replace)
continue
if self._comments_processing:
if '#' in original[item_to_replace]:
replaced = OrderedDict({'#':
original[item_to_replace]['#']}
)
replaced.update(template[key_value])
else:
replaced = template[key_value]
original[item_to_replace] = replaced
else:
original[item_to_replace] = template[key_value]
elif key_value not in original.keys():
if isinstance(template[key_value], dict):
dictionary_to_add = OrderedDict()
self._join(dictionary_to_add,
template[key_value],
self._join_before_in_areas)
if dictionary_to_add != OrderedDict():
if not join_before:
original[key_value] = dictionary_to_add
else:
forwarded_items[key_value] = dictionary_to_add
else:
if not join_before:
original[key_value] = template[key_value]
else:
forwarded_items[key_value] = template[key_value]
else:
if isinstance(original[key_value], dict) and \
isinstance(template[key_value], dict):
self._join(original[key_value],
template[key_value],
self._join_before_in_areas)
else:
if self._comments_processing:
original[key_value][-1] = template[key_value][-1]
else:
original[key_value] = template[key_value]
if join_before:
for key_value in reversed(forwarded_items.keys()):
original[key_value] = forwarded_items[key_value]
original.move_to_end(key_value, last=False)
def get_document_text(self):
file_loader = PackageLoader('calculate.templates.format',
self.TEMPLATES_DIRECTORY)
formats_environment = Environment(loader=file_loader,
trim_blocks=True,
lstrip_blocks=True)
formats_environment.globals.update(zip=zip)
formats_environment.add_extension('jinja2.ext.do')
template = formats_environment.get_template(self._format)
document_text = template.render(
document_dictionary=self._document_dictionary
)
return document_text
def _finish_method(self):
pass
def _is_ready_to_update(self):
is_ready, self._match = self._ready_to_update, False
return is_ready
def _is_match(self):
is_match, self._match = self._match, False
return is_match

@ -0,0 +1,293 @@
# vim: fileencoding=utf-8
#
# ToDo: добавить проверку того, полностью ли парсился документ. Если отпарсился
# не весь файл -- выдаем ошибку.
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import originalTextFor, OneOrMore, Word, alphanums, Literal,\
ZeroOrMore, Forward, Optional, Group, restOfLine,\
cppStyleComment, Keyword, printables, nums, SkipTo
class BINDFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = []
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._format = 'bind'
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
self._parse_text(document_text)
def _initialize_parser(self):
left_brace = Literal('{')
right_brace = Literal('}')
semicolon = Literal(';')
action_symbols = (Literal('!') |
Literal('-'))
plain_allow = Keyword('allow')
drop_allow = Keyword('!allow')
replace_allow = Keyword('-allow')
allow = (plain_allow | drop_allow | replace_allow)
keys = Keyword('keys')
inet = Keyword('inet')
statement = originalTextFor(
Word(alphanums+'_-',
excludeChars='{};')
)
statement_name = originalTextFor(
Word(printables,
excludeChars='{};')
)
statement_class = originalTextFor(
Word(printables,
excludeChars='{};')
)
parameter_value = originalTextFor(
Word(printables,
excludeChars='{};')
)('parameter')
ip_value = originalTextFor(
Word(nums+':./',
excludeChars=';{}')
)
# Будущий парсер блока.
block = Forward()
# Для парсинга директивы inet_spec.
allow_item = (ip_value | statement_name) + semicolon.suppress()
key_item = statement_name + semicolon.suppress()
allow_group = Group(Group(Optional(action_symbols,
default='')('action')
+ allow)
+ Group(left_brace.suppress()
+ ZeroOrMore(allow_item)
+ right_brace.suppress()))
keys_group = Group(Group(Optional(action_symbols, default='')('action')
+ keys)
+ Group(left_brace.suppress()
+ ZeroOrMore(key_item)
+ right_brace.suppress()))
inet_spec = (Group(Optional(action_symbols, default='')('action')
+ inet + originalTextFor(SkipTo(allow,
include=False)
)('parameter')
)('name')
+ Group(allow_group
+ Optional(keys_group)
+ semicolon.suppress())('content')
).setParseAction(
self._add_inet_specline
)
# Для парсинга комментариев.
python_style_comment = originalTextFor(Literal('#') + restOfLine)
comments = (cppStyleComment |
python_style_comment).setParseAction(
self._create_comment_list
)
# Для парсинга директивы include.
include_line = (Optional(action_symbols, default='')('action')
+ Keyword('include')
+ Word(printables, excludeChars=';{}')
+ Optional(semicolon.suppress())
).setParseAction(
self._add_include_line
)
# Для парсинга простых директив состоящих из одного
# или двух параметров.
plain_line = (Group(Optional(action_symbols, default='')('action')
+ statement)('name')
+ Optional(parameter_value)
+ Optional(semicolon.suppress())).setParseAction(
self._add_plain_line
)
# Метод для парсинга IP адресов.
ip_line = (Group(Optional(action_symbols, default='')('action')
+ ip_value
+ Optional(semicolon.suppress()))('IP')
).setParseAction(self._add_ipline)
# Парсеры параметров.
param_line = (include_line |
ip_line |
plain_line)
# Парсер блока параметров.
param_block = (Group(Optional(action_symbols, default='')('action')
+ statement + Optional(statement_name)
+ Optional(statement_class))('name')
+ block('content')
+ Optional(semicolon.suppress())).setParseAction(
self._add_param_block
)
# Виды блочных директив.
block_types = (inet_spec | param_block)
# Парсер параметров с комментариями.
# Note: Применение parser.ignore(comments) является причиной странного
# поведения парсера, при котором невозможно многократное повторное
# применение формата после установки флага ignore_comments.
if self._ignore_comments:
param_line_with_comments = (ZeroOrMore(comments).suppress()(
'comments'
)
+ param_line('value')
).setParseAction(
self._add_comments_to_paramline
)
else:
param_line_with_comments = (ZeroOrMore(comments)('comments')
+ param_line('value')
).setParseAction(
self._add_comments_to_paramline
)
# Парсер блока с комментариями.
if self._ignore_comments:
param_block_with_comments = (ZeroOrMore(comments).suppress()(
'comments'
)
+ block_types('value')
).setParseAction(
self._add_comments_to_block
)
else:
param_block_with_comments = (ZeroOrMore(comments)('comments')
+ block_types('value')
).setParseAction(
self._add_comments_to_block
)
# Парсер содержимого блоков.
block_item = (param_block_with_comments |
param_line_with_comments)
# Для парсинга всего блока с любым содержимым.
block << Group(left_brace.suppress() + ZeroOrMore(block_item)
+ right_brace.suppress())
# Парсер всего документа.
self._document_parser = OneOrMore(block_item)
def _parse_text(self, text):
parsing_result = self._document_parser.parseString(text, parseAll=True)
list_of_elements = parsing_result.asList()
for part in list_of_elements:
self._join_dictionary(self._document_dictionary,
part)
def _join_dictionary(self, out_dictionary, dictionary_to_add):
for key in dictionary_to_add:
if dictionary_to_add == OrderedDict():
return
if key in out_dictionary and\
isinstance(dictionary_to_add[key], OrderedDict) and\
isinstance(out_dictionary[key], OrderedDict):
self._join_dictionary(out_dictionary[key],
dictionary_to_add[key])
else:
out_dictionary[key] = dictionary_to_add[key]
def _add_plain_line(self, current_parse):
name = tuple(current_parse.name.asList())
if not current_parse.parameter == '':
value = current_parse.parameter
else:
if current_parse.name.action == '-':
return OrderedDict()
value = ''
return OrderedDict({name: [value]})
def _add_include_line(self, current_parse):
name = current_parse.asList()
return OrderedDict({tuple(name): ['']})
def _add_ipline(self, current_parse):
ip_value = current_parse.IP
return OrderedDict({tuple(ip_value): ['']})
def _add_inet_specline(self, current_parse):
# Удаляем пробельные символы из второго параметра директивы.
current_parse.name.parameter = current_parse.name.parameter.strip()
block_name = tuple(current_parse.name.asList())
block_content = current_parse.content.asList()
content = OrderedDict({'#': []})
for item in block_content:
current_keyword, values = item
current_keyword = tuple(current_keyword)
content[current_keyword] = values
return OrderedDict({block_name: content})
def _add_param_block(self, current_parse):
block_name = tuple(current_parse.name.asList())
block_content = current_parse.content.asList()
content = OrderedDict({'#': []})
for item in block_content:
self._join_dictionary(content, item)
return OrderedDict({block_name: content})
def _add_comments_to_paramline(self, current_parse):
[parameter] = current_parse.value.asList()
comments = current_parse.comments
if parameter == OrderedDict():
if not comments == '':
self._last_comments_list.extend(comments.asList())
return OrderedDict()
name = next(iter(parameter))
value = parameter[name]
if not comments == '':
comments_list = comments.asList()
parameter[name] = (self._last_comments_list
+ comments_list + value)
self._last_comments_list = []
return parameter
def _add_comments_to_block(self, current_parse):
[value] = current_parse.value
[block_name] = value
block = value[block_name]
if not current_parse.comments == '':
block['#'] = (self._last_comments_list
+ current_parse.comments.asList())
self._last_comments_list = []
else:
block.pop('#')
return value
def _create_comment_list(self, current_parse):
comments_list = []
comments = current_parse.asList()
for comment in comments:
lines = comment.splitlines()
for line in lines:
comments_list.append(line.strip())
return comments_list

@ -0,0 +1,150 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import originalTextFor, Literal, ZeroOrMore, Word, printables,\
OneOrMore, alphanums, ParseException, restOfLine,\
pyparsing_unicode, Group, Optional
class CompizFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_section_line,
self._parse_parameter_line,
self._parse_to_delete_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._need_finish = True
self._format = 'compiz'
self._current_section = OrderedDict()
self._current_section_name = ''
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
section_name = originalTextFor(
OneOrMore(Word(alphanums+'_'))
)
action_symbols = (Literal('!') | Literal('-'))
self._section_line = (Literal('[').suppress()
+ Optional(action_symbols, default='')('action')
+ section_name('name')
+ Literal(']').suppress())('section_name')
parameter_name = originalTextFor(
OneOrMore(Word(printables,
excludeChars='='))
)
parameter_value = Word(printables)
self._parameter_line = (Group(Optional(action_symbols,
default='')('action')
+ parameter_name('name')
)('parameter_name')
+ Literal('=').suppress()
+ parameter_value('parameter_value'))
self._parameter_to_delete = (action_symbols('action')
+ parameter_name('name')
+ restOfLine.suppress())('parameter_name')
self._comment_line = originalTextFor(
Literal('#')
+ ZeroOrMore(Word(printables
+ pyparsing_unicode.alphanums))
)('comment')
def _parse_section_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._section_line.parseString(line)
self._match = True
if self._current_section_name != '':
if self._current_section_name in \
self._document_dictionary.keys():
self._document_dictionary[self._current_section_name].\
update(self._current_section)
self._current_section = OrderedDict()
else:
self._item_to_add[self._current_section_name] = \
self._current_section
self._current_section = OrderedDict()
self._ready_to_update = True
self._current_section_name = tuple(
parsing_result.section_name.asList()
)
if self._last_comments_list != []:
self._current_section['#'] = self._last_comments_list
self._last_comments_list = []
except ParseException:
return
def _parse_parameter_line(self, line):
try:
parsing_result = self._parameter_line.parseString(line)
self._match = True
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = parsing_result.parameter_value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._current_section[key_value] = parameter_value
except ParseException:
return
def _parse_to_delete_line(self, line):
try:
parsing_result = self._parameter_to_delete.parseString(line)
self._match = True
if parsing_result.action == '-':
return
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = self._last_comments_list
self._last_comments_list = []
self._current_section[key_value] = parameter_value
except ParseException:
return
def _parse_comment_line(self, line):
try:
parsing_result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(parsing_result.comment)
except ParseException:
return
def _finish_method(self):
if self._current_section_name in self._document_dictionary.keys():
self._document_dictionary[self._current_section_name].update(
self._current_section
)
else:
self._item_to_add[self._current_section_name] =\
self._current_section
self._document_dictionary.update(self._item_to_add)
self._current_section = OrderedDict()

@ -0,0 +1,62 @@
# vim: fileencoding=utf-8
#
from calculate.utils.files import Process
from os import path
class DiffFormat():
def __init__(self, document_text: str):
self._patch_text = document_text
self._root_path = ''
self._last_level = 0
# вынести в более общий класс или куда-то еще.
self._changed_files_list = []
def execute_format(self, root_path):
if path.exists(root_path):
self._root_path = root_path
else:
# Какая-то обработка ошибки.
error_message = 'Root path does not exist.'
print(error_message)
return False
if self._patch_text:
return self._patch_document()
else:
# Какая-то обработка ошибки.
error_message = 'Empty patch file.'
print(error_message)
return False
def _patch_document(self):
for level in range(0, 4):
patch_dry_run = Process('patch', '--dry-run',
'-p{}'.format(level), cwd=self._root_path)
patch_dry_run.write(self._patch_text)
if patch_dry_run.success():
break
patch_dry_run = Process('patch', '-R', '--dry-run',
'-p{}'.format(level), cwd=self._root_path)
patch_dry_run.write(self._patch_text)
if patch_dry_run.success():
return ''
else:
# Какая-то обработка ошибки.
error_message = 'Correction failed.'
print(error_message)
return False
self._last_level = level
patch_run = Process('patch', '-p{}'.format(level), cwd=self._root_path)
patch_run.write(self._patch_text)
if patch_run.success():
for line in patch_run:
if line.startswith('patching file'):
self._changed_files_list.append(line[13:].strip())
return patch_run.read()
else:
return ''

@ -0,0 +1,229 @@
# vim: fileencoding=utf-8
#
# ToDo: написать счетчик скобок для финальной оценки корректности
# документа.
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import originalTextFor, Literal, ZeroOrMore, Word, printables,\
OneOrMore, alphanums, ParseException, pyparsing_unicode,\
Group, Optional, alphas, lineEnd, lineStart, Keyword
class DovecotFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_section_start_line,
self._parse_include_line,
self._parse_section_end_line,
self._parse_parameter_line,
self._parse_parameter_to_delete_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._need_finish = True
self._comments_processing = True
self._format = 'dovecot'
self._section_stack = OrderedDict()
self._current_section_name = ''
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
# Знаки пунктуации и действий.
left_brace = Literal('{')
right_brace = Literal('}')
action_symbols = (Literal('!') | Literal('-'))
self._comment_line_parser = originalTextFor(
Literal('#')
+ ZeroOrMore(Word(
printables
+ pyparsing_unicode.alphanums)
)
)('comment')
# Для парсинга строк с началом секций.
section = Word(alphas, alphanums+'-_', excludeChars='{}')
section_name = Word(printables, excludeChars='{}')
self._section_start_parser = Group(Optional(action_symbols,
default='')('action')
+ section
+ Optional(section_name)
+ left_brace.suppress())('name')
# Для парсинга строк, указывающих конец секций.
self._section_end_parser = lineStart() + right_brace + lineEnd()
# Для парсинга строк, содержащих параметры.
parameter_name = Word(alphas, alphanums+'_-', excludeChars='{}=')
parameter_value = OneOrMore(Word(printables))
self._parameter_line_parser = (Group(Optional(action_symbols,
default='')('action')
+ parameter_name)('name')
+ Literal('=').suppress()
+ originalTextFor(
parameter_value
)('value'))
# Для парсинга строк с параметрами, подлежащими удалению.
self._parameter_to_delete_parser = (action_symbols('action')
+ parameter_name
+ Optional(Literal('=')).suppress()
)
# Для парсинга строк, содержащих директиву !include.
include = Keyword('!include') | Keyword('!include_try')
include_line_plain = (Optional(~action_symbols, default='')('action')
+ include('keyword') + Word(printables)('value'))
include_line_to_delete = (action_symbols('action') + include('keyword')
+ Word(printables)('value'))
self._include_line_parser = (include_line_plain |
include_line_to_delete)
def _parse_section_start_line(self, line):
try:
parsing_result = self._section_start_parser.parseString(line)
self._match = True
section_name = tuple(parsing_result.name.asList())
if not self._last_comments_list == []:
section_content = OrderedDict({'#': self._last_comments_list})
self._last_comments_list = []
else:
section_content = OrderedDict()
new_section = OrderedDict({section_name: section_content})
if self._section_stack == OrderedDict():
if section_name in self._document_dictionary:
new_section = OrderedDict(
{section_name:
self._document_dictionary[section_name]}
)
else:
if section_name in \
self._section_stack[self._current_section_name]:
new_section = OrderedDict({
section_name:
self._section_stack[self._current_section_name]
[section_name]
})
else:
self._section_stack[self._current_section_name].update(
new_section
)
self._section_stack.update(new_section)
self._current_section_name = section_name
except ParseException:
return
def _parse_section_end_line(self, line):
try:
self._section_end_parser.parseString(line)
self._match = True
last_section_name, last_section = self._section_stack.popitem()
if self._section_stack == OrderedDict():
self._item_to_add = OrderedDict({last_section_name:
last_section})
self._ready_to_update = True
self._current_section_name = ''
else:
self._current_section_name = next(reversed(
self._section_stack
))
except ParseException:
return
def _parse_parameter_line(self, line):
try:
parsing_result = self._parameter_line_parser.parseString(line)
self._match = True
parameter_name = tuple(parsing_result.name.asList())
parameter_value = (self._last_comments_list
+ [parsing_result.value.strip()])
self._last_comments_list = []
parameter = OrderedDict({parameter_name: parameter_value})
if self._section_stack == OrderedDict():
self._item_to_add = parameter
self._ready_to_update = True
else:
self._section_stack[self._current_section_name].update(
parameter
)
except ParseException:
return
def _parse_parameter_to_delete_line(self, line):
try:
parsing_result = self._parameter_to_delete_parser.parseString(line)
self._match = True
parameter_name = tuple(parsing_result.asList())
parameter_value = self._last_comments_list + ['']
self._last_comments_list = []
parameter = OrderedDict({parameter_name: parameter_value})
if self._section_stack == OrderedDict():
self._item_to_add = parameter
self._ready_to_update = True
else:
self._section_stack[self._current_section_name].update(
parameter
)
except ParseException:
return
def _parse_include_line(self, line):
try:
parsing_result = self._include_line_parser.parseString(line)
self._match = True
parameter_name = tuple(parsing_result.asList())
if parsing_result.action == '-':
return
parameter_value = self._last_comments_list + ['']
self._last_comments_list = []
include_item = OrderedDict({parameter_name: parameter_value})
if self._section_stack == OrderedDict():
self._item_to_add = include_item
self._ready_to_update = True
else:
self._section_stack[self._current_section_name].update(
include_item
)
except ParseException:
return
def _parse_comment_line(self, line):
try:
parsing_result = self._comment_line_parser.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(parsing_result.comment)
except ParseException:
return

@ -0,0 +1,26 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
import json
class JSONFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = []
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._format = 'json'
if document_text == '':
self._document_dictionary = OrderedDict()
else:
self._text_to_dictionary(document_text)
def _text_to_dictionary(self, json_file_text):
self._document_dictionary = json.loads(json_file_text,
object_pairs_hook=OrderedDict)
def get_document_text(self):
json_file_text = json.dumps(self._document_dictionary, indent=4)
return json_file_text

@ -0,0 +1,155 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import originalTextFor, Literal, ZeroOrMore, Word, printables,\
OneOrMore, alphanums, ParseException, restOfLine,\
pyparsing_unicode, Group, Optional
class KDEFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_section_line,
self._parse_parameter_line,
self._parse_to_delete_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._need_finish = True
self._format = 'kde'
self._current_section = OrderedDict()
self._current_section_name = ''
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
action_symbols = (Literal('!') | Literal('-'))
section_name_part_content = originalTextFor((OneOrMore(
Word(alphanums+':'))))
section_name_part = (Literal('[').suppress()
+ section_name_part_content
+ Literal(']').suppress())
self._section_line = (Literal('[').suppress()
+ Optional(action_symbols, default='')('action')
+ section_name_part_content
+ Literal(']').suppress()
+ ZeroOrMore(section_name_part))('section_name')
parameter_name = originalTextFor(
OneOrMore(Word(printables,
excludeChars='='))
)('parameter_name')
parameter_value = originalTextFor(OneOrMore(Word(
pyparsing_unicode.alphanums
+ printables))
)('parameter_value')
self._parameter_line = (Group(Optional(action_symbols,
default='')('action')
+ parameter_name)('parameter_name')
+ Literal('=').suppress()
+ parameter_value('parameter_value'))
self._parameter_to_delete = (action_symbols('action')
+ parameter_name('name')
+ restOfLine.suppress())('parameter_name')
self._comment_line = originalTextFor(
Literal('#')
+ ZeroOrMore(Word(printables
+ pyparsing_unicode.alphanums))
)('comment')
def _parse_section_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._section_line.parseString(line)
self._match = True
if self._current_section_name != '':
if self._current_section_name in \
self._document_dictionary.keys():
self._document_dictionary[self._current_section_name].\
update(self._current_section)
self._current_section = OrderedDict()
else:
self._item_to_add[self._current_section_name] = \
self._current_section
self._current_section = OrderedDict()
self._ready_to_update = True
self._current_section_name = tuple(
parsing_result.section_name.asList()
)
if self._last_comments_list != []:
self._current_section['#'] = self._last_comments_list
self._last_comments_list = []
except ParseException:
return
def _parse_parameter_line(self, line):
try:
parsing_result = self._parameter_line.parseString(line)
self._match = True
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = parsing_result.parameter_value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._current_section[key_value] = parameter_value
except ParseException:
return
def _parse_to_delete_line(self, line):
try:
parsing_result = self._parameter_to_delete.parseString(line)
self._match = True
if parsing_result.action == '-':
return
key_value = tuple(parsing_result.parameter_name)
parameter_value = self._last_comments_list
self._last_comments_list = []
self._current_section[key_value] = parameter_value
except ParseException:
return
def _parse_comment_line(self, line):
try:
parsing_result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(parsing_result.comment)
except ParseException:
return
def _finish_method(self):
if self._current_section_name in self._document_dictionary.keys():
self._document_dictionary[self._current_section_name].update(
self._current_section
)
else:
self._item_to_add[self._current_section_name] =\
self._current_section
self._document_dictionary.update(self._item_to_add)
self._current_section = OrderedDict()

@ -0,0 +1,100 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import Word, Literal, alphanums, printables, originalTextFor,\
ZeroOrMore, OneOrMore, ParseException, restOfLine,\
pyparsing_unicode, Group, Optional
class KernelFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_parameter_line,
self._parse_to_delete_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._format = 'kernel'
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
documentLines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(documentLines)
def _initialize_parser(self):
parameter_name = Word(alphanums+'_')('parameter_name')
parameter_value = originalTextFor(
OneOrMore(Word(printables))
)('parameter_value')
action_symbols = (Literal('!') | Literal('-'))
self._parameter_line = (Group(Optional(action_symbols,
default='')('action')
+ parameter_name('name')
)('parameter_name')
+ Literal('=').suppress()
+ parameter_value('parameter_value'))
self._parameter_to_delete = (Group(action_symbols('action')
+ parameter_name('name')
)('parameter_name')
+ restOfLine.suppress())
self._comment_line = originalTextFor(
Literal('#').suppress()
+ ZeroOrMore(Word(printables
+ pyparsing_unicode.alphanums))
)('Comment')
def _parse_parameter_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._parameter_line.parseString(line)
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = parsing_result.parameter_value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._item_to_add[key_value] = parameter_value
self._ready_to_update = True
self._match = True
except ParseException:
return
def _parse_to_delete_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._parameter_to_delete.parseString(line)
if parsing_result.action == '-':
return
key_value = (parsing_result.parameter_name.action,
parsing_result.parameter_name.name.upper())
parameter_value = self._last_comments_list
self._last_comments_list = []
self._item_to_add[key_value] = parameter_value
self._ready_to_update = True
self._match = True
except ParseException:
return
def _parse_comment_line(self, line):
try:
result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(result.Comment)
except ParseException:
return

@ -0,0 +1,522 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import originalTextFor, Literal, ZeroOrMore, Word, printables,\
OneOrMore, alphanums, ParseException, restOfLine,\
pyparsing_unicode, nums, delimitedList, Optional,\
Keyword, SkipTo, Group
class LDAPFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_type_line,
self._parse_access_line,
self._parse_access_line_to_delete,
self._parse_syncrepl_line,
self._parse_syncrepl_line_to_delete,
self._parse_notunique_line,
self._parse_index_line,
self._parse_index_line_to_delete,
self._parse_plain_directive_line,
self._parse_plain_directive_line_to_delete]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._need_finish = True
self._format = 'ldap'
if self._ignore_comments:
self._current_type_section = OrderedDict()
else:
self._current_type_section = OrderedDict({'#': []})
self._current_type = ('', 'global')
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
self._comment_line = originalTextFor(
Literal('#')
+ ZeroOrMore(Word(printables
+ pyparsing_unicode.alphanums))
)('comment')
action_symbols = (Literal('!') | Literal('-'))
assignment = Literal('=')
# Для парсинга строк c директивами неуникальными для секции.
not_unique_directives = originalTextFor(
Keyword('include') |
Keyword('moduleload')
)
not_unique_value = originalTextFor(
OneOrMore(Word(printables))
)('value')
self._not_unique_parser = (Optional(action_symbols,
default='')('action')
+ not_unique_directives
+ not_unique_value + restOfLine.suppress())
# Для выделения областей global, backend и database.
type_sections_keywords = originalTextFor(
Keyword('backend') |
Keyword('database')
)
type_value = originalTextFor(Word(alphanums))
self._type_line = (Optional(action_symbols, default='')('action')
+ type_sections_keywords
+ type_value
+ restOfLine.suppress())
# Для парсинга конструкции syncrepl rid=<replica ID> <parameters>
content_without_spaces = Word(printables, excludeChars='"')
content_with_spaces = (Literal('"')
+ OneOrMore(Word(printables,
excludeChars='"'))
+ Literal('"'))
parameter_without_spaces = (Word(printables, excludeChars='"=')
+ assignment.suppress()
+ content_without_spaces)
parameter_with_spaces = (Word(printables, excludeChars='"=')
+ assignment.suppress()
+ content_with_spaces)
values = OneOrMore(originalTextFor(parameter_with_spaces |
parameter_without_spaces))('Values')
syncrepl_replica_id = originalTextFor(Literal('rid')
+ assignment.suppress()
+ Word(nums))('replicaID')
self._syncrepl_line_parser = (Group(Optional(action_symbols,
default='')('action')
+ Keyword('syncrepl')
+ syncrepl_replica_id)('name')
+ values('Values')
+ restOfLine.suppress())
self._syncrepl_value_parser = (Group(Optional(action_symbols,
default='')('action')
+ originalTextFor(
Word(
printables,
excludeChars='"='
)
))('name')
+ assignment.suppress()
+ originalTextFor(
OneOrMore(
Word(printables)
)
)('value'))
self._syncrepl_line_to_delete_parser = (Group(Optional(
action_symbols,
default=''
)('action')
+ Keyword('syncrepl')
+ syncrepl_replica_id)('name')
+ restOfLine.suppress())
# Для парсинга конструкции
# access to <what> by <who>|<access level>|<control>
access_keyword = originalTextFor(Literal('access to'))('keyword')
value = originalTextFor(parameter_with_spaces |
parameter_without_spaces |
content_without_spaces |
content_with_spaces)
self._access_line_parser = (Group(Optional(action_symbols,
default='')('action')
+ access_keyword
+ value)('name')
+ Keyword('by').suppress()
+ delimitedList(
originalTextFor(value +
SkipTo(
Keyword('by'),
include=False) |
restOfLine
),
delim='by'
)('Values'))
self._access_value_parser = (Group(Optional(action_symbols,
default='')('action')
+ originalTextFor(value))('name')
+ originalTextFor(
Optional(Word(alphanums))
)('value'))
self._access_line_to_delete_parser = (Group(action_symbols('action')
+ access_keyword
+ value
+ restOfLine.suppress())('name'))
# Для парсинга строк с директивами index.
self._index_line_parser = (Group(Optional(action_symbols,
default='')('action')
+ Keyword('index')
+ originalTextFor(Word(printables))
)('name')
+ originalTextFor(
OneOrMore(Word(printables))
)('value'))
self._index_line_to_delete_parser = (Group(action_symbols('action')
+ Keyword('index')
+ originalTextFor(
Word(printables)
))('name'))
# Для парсинга остальных директив.
self._directive_line_parser = (Group(Optional(action_symbols,
default='')('action')
+ originalTextFor(
Word(printables)
))('name')
+ originalTextFor(
OneOrMore(Word(
printables
)
))('value'))
self._directive_line_to_delete_parser = (action_symbols('action')
+ originalTextFor(
Word(printables)
))('name')
def _get_list_of_logic_lines(self, text):
list_of_lines = []
lines_to_join = []
for line in text.splitlines():
if line.strip() == '':
continue
if not line.startswith(' ') and not line.startswith('\t'):
joined_line = "".join(lines_to_join)
if joined_line != '':
list_of_lines.append(joined_line)
lines_to_join = []
line.strip()
else:
line = ' ' + line.strip()
lines_to_join.append(line)
joined_line = "".join(lines_to_join)
list_of_lines.append(joined_line)
return list_of_lines
def _parse_type_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._type_line.parseString(line)
self._match = True
type_name = tuple(parsing_result.asList())
if self._current_type in self._document_dictionary.keys():
self._document_dictionary[self._current_type].update(
self._current_type_section
)
else:
self._item_to_add[self._current_type] =\
self._current_type_section
self._ready_to_update = True
# Если глобальная область пуста -- передаем ее комментарии
# следующей за ней области.
if self._current_type == ('', 'global') and\
list(self._current_type_section.keys()) == ['#']:
self._last_comments_list = self._current_type_section['#']
self._item_to_add[self._current_type] = OrderedDict()
self._current_type_section = OrderedDict()
self._current_type = type_name
if self._last_comments_list != []:
self._current_type_section['#'] = self._last_comments_list
self._last_comments_list = []
except ParseException:
return
def _parse_notunique_line(self, line):
'''Метод для парсинга строк c директивами неуникальными для секции.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
self._item_to_add = OrderedDict()
parsing_result = self._not_unique_parser.parseString(line)
self._match = True
parsing_result.value = parsing_result.value.strip()
not_unique_name = tuple(parsing_result.asList())
parameter_value = ['']
parameter_value = self._last_comments_list + parameter_value
self._last_comments_list = []
self._current_type_section[not_unique_name] = parameter_value
except ParseException:
return
def _parse_access_line(self, line):
'''Метод для парсинга строк содержащих конструкцию
access to <what> by <who>|<access level>|<control>.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._access_line_parser.parseString(line)
self._match = True
values = [value.strip() for value in
parsing_result.Values.asList()]
values.reverse()
parameter_name = tuple(parsing_result.name)
value_dictionary = OrderedDict()
if self._last_comments_list != []:
value_dictionary['#'] = self._last_comments_list
self._last_comments_list = []
for value in values:
try:
value_parsing = self._access_value_parser.\
parseString(value)
param_name = tuple(value_parsing.name)
param_value = value_parsing.value
value_dictionary[param_name] = [param_value]
except ParseException:
continue
parameter_value = value_dictionary
if parameter_name in self._current_type_section.keys():
self._current_type_section[parameter_name].update(
value_dictionary
)
else:
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_access_line_to_delete(self, line):
'''Метод для парсинга строк, предписывающих удаление конструкций
access to, если указано только ее название и значение What.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._access_line_to_delete_parser.parseString(
line
)
self._match = True
parameter_name = tuple(parsing_result.name.asList())
if parsing_result.name.action == '-':
return
parameter_value = OrderedDict({'#': self._last_comments_list})
self._last_comments_list = []
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_syncrepl_line(self, line):
'''Метод для парсинга строк содержащих конструкцию syncrepl
rep=<ReplicaID>.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._syncrepl_line_parser.parseString(line)
self._match = True
values = [value.strip() for value in parsing_result.Values.asList()]
parameter_name = tuple(parsing_result.name.asList())
value_dictionary = OrderedDict()
if self._last_comments_list != []:
value_dictionary['#'] = self._last_comments_list
self._last_comments_list = []
for value in values:
try:
value_parsing = self._syncrepl_value_parser.parseString(
value
)
param_name = tuple(value_parsing.name.asList())
param_value = value_parsing.value
value_dictionary[param_name] = [param_value]
except ParseException:
continue
parameter_value = value_dictionary
if parameter_name in self._current_type_section.keys():
self._current_type_section[parameter_name].update(
value_dictionary
)
else:
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_syncrepl_line_to_delete(self, line):
'''Метод для парсинга строк, предписывающих удаление конструкций
syncrepl rid=<ReplicaID>, если указано только ее название и значение
ReplicaID.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._syncrepl_line_to_delete_parser.parseString(
line
)
self._match = True
parameter_name = tuple(parsing_result.name.asList())
if parsing_result.name.action == '-':
return
parameter_value = OrderedDict({'#': self._last_comments_list})
self._last_comments_list = []
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_index_line(self, line):
'''Метод для парсинга строк с директивами index.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._index_line_parser.parseString(line)
self._match = True
parameter_name = tuple(parsing_result.name.asList())
parameter_value = parsing_result.value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_index_line_to_delete(self, line):
'''Метод для парсинга строк, предписывающих удаление директив index,
если указано только из имя, но отсутвует значение.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._index_line_to_delete_parser.parseString(line)
self._match = True
parameter_name = tuple(parsing_result.name.asList())
if parsing_result.name.action == '-':
return
parameter_value = self._last_comments_list
self._last_comments_list = []
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_plain_directive_line(self, line):
'''Метод для парсинга строк с простыми уникальными для секции
директивами.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._directive_line_parser.parseString(line)
self._match = True
parameter_name = tuple(parsing_result.name.asList())
parameter_value = parsing_result.value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_plain_directive_line_to_delete(self, line):
'''Метод для парсинга строк, предписывающих удаление простых уникальных
директив, если указано только их имя, но отсутствует значение.
Аргументы: line -- строка, которую нужно распарсить.
'''
try:
parsing_result = self._directive_line_to_delete_parser.parseString(
line
)
self._match = True
parameter_name = tuple(parsing_result.name.asList())
if parsing_result.action == '-':
return
parameter_value = self._last_comments_list
self._last_comments_list = []
self._current_type_section[parameter_name] = parameter_value
except ParseException:
return
def _parse_comment_line(self, line):
'''Метод для парсинга строк с комментариями и добавления их в список
комментариев _last_comments_list, предназначенный для сбора
комментариев и последующего их присваивания параметрам и секциям.
Аргументы: line -- строка, которую нужно распарсить.'''
try:
parsing_result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
# До того, как первый элемент встречен -- все комментарии
# должны быть присвоены глобальной области.
if self._current_type == ('', 'global') and\
list(self._current_type_section.keys()) == ['#']:
self._current_type_section['#'].append(
parsing_result.comment
)
else:
self._last_comments_list.append(parsing_result.comment)
except ParseException:
return
def _finish_method(self):
self._item_to_add = OrderedDict()
if self._current_type in self._document_dictionary.keys():
self._document_dictionary[self._current_type].update(
self._current_type_section
)
else:
self._item_to_add[self._current_type] = self._current_type_section
self._document_dictionary.update(self._item_to_add)
self._item_to_add = OrderedDict()
self._current_type_section = OrderedDict()

@ -0,0 +1,99 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import Word, Literal, printables, originalTextFor, ZeroOrMore,\
OneOrMore, ParseException, restOfLine,\
pyparsing_unicode, Group, Optional
class OpenRCFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_parameter_line,
self._parse_to_delete_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._format = 'openrc'
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
parameter_name = Word(printables, excludeChars='=')
parameter_value = originalTextFor(OneOrMore(Word(printables)))
action_symbols = (Literal('!') | Literal('-'))
self._parameter_line = (Group(Optional(action_symbols,
default='')('action')
+ parameter_name('name'))('parameter_name')
+ Literal('=').suppress()
+ parameter_value('parameter_value'))
self._parameter_to_delete = (Group(action_symbols('action')
+ parameter_name('name')
)('parameter_name')
+ restOfLine.suppress())
self._comment_line = originalTextFor(
Literal('#')
+ ZeroOrMore(Word(printables
+ pyparsing_unicode.alphanums))
)('comment')
def _parse_parameter_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._parameter_line.parseString(line)
key_value = (parsing_result.parameter_name.action,
parsing_result.parameter_name.name.lower())
parameter_value = parsing_result.parameter_value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._item_to_add[key_value] = parameter_value
self._ready_to_update = True
self._match = True
except ParseException:
return
def _parse_to_delete_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._parameter_to_delete.parseString(line)
if parsing_result.parameter_name.action == '-':
return
key_value = (parsing_result.parameter_name.action,
parsing_result.parameter_name.name.lower())
parameter_value = self._last_comments_list
self._last_comments_list = []
self._item_to_add[key_value] = parameter_value
self._ready_to_update = True
self._match = True
except ParseException:
return
def _parse_comment_line(self, line):
try:
result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(result.comment)
except ParseException:
return

@ -0,0 +1,177 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
import re
try:
from lxml.etree.ElementTree import fromstring
except ImportError:
from xml.etree.ElementTree import fromstring
class PatchFormat(BaseFormat):
def __init__(self, document_text: str, multiline=False, dotall=False):
processing_methods = OrderedDict()
super().__init__(processing_methods)
self._format = 'patch'
self._multiline_flag = multiline
self._dotall_flag = dotall
self._parsed_patch = None
self._document_to_patch = ''
self._FLAG_VALUES = {'True': True,
'False': False,
'true': True,
'false': False,
'1': True,
'0': False}
self._XML_ROOT_LINE = '<?xml version="1.0" encoding="utf-8"?>\
<patch>{0}</patch>'
if not self._parse_patch(document_text):
# Какая-то обработка ошибки.
print('Error: Can not parse patch document.')
def _parse_patch(self, patch_text):
xml_patch = self._XML_ROOT_LINE.format(patch_text.strip())
try:
self._parsed_patch = fromstring(xml_patch)
return True
except Exception:
# Какая-то обработка ошибки.
print('Error: Incorrect text of the template.')
return False
def execute_format(self, document_to_patch):
if not document_to_patch.strip() == '':
self._document_to_patch = document_to_patch
if self._parse_patch is None:
return False
else:
if not self._patch_document(document_to_patch):
error_message = 'Error: Can not run patch.'
print(error_message)
return False
else:
after_patch = self._document_to_patch
self._document_to_patch = ''
return after_patch
def _patch_document(self, document_to_patch):
patch_iterator = self._parsed_patch.getiterator()
PATCH_DOCUMENT_TAGS = ('reg', 'text')
patch_element = next(patch_iterator, False)
if not patch_element or not patch_element.tag == 'patch':
print('Error: Incorrect text of the template.')
return False
while True:
for patch_tag in PATCH_DOCUMENT_TAGS:
patch_element = next(patch_iterator, None)
if patch_element is None:
if patch_tag == 'text':
print('Error: Last <text>Text</text> '
'object is missed.')
return False
else:
break
if patch_element.tag == patch_tag:
if patch_element.text is not None:
element_text = patch_element.text.strip()
if element_text == '':
error_message = 'Error: Incorrect text of the \
template: <{0}>%s</{0}>'.format(
patch_tag
)
print(error_message)
return False
else:
error_message = 'Error: Incorrect text of the \
template: <{0}></{0}>'.format(
patch_tag
)
print(error_message)
return False
if patch_tag == 'reg':
dotall = patch_element.attrib.get('dotall', False)
regex_flags = 0
if 'multiline' in patch_element.attrib:
multiline = patch_element.attrib['multiline']
if multiline not in self._FLAG_VALUES:
error_message = ('Error: Invalid multiline '
'value.')
print(error_message)
return False
else:
multiline = self._FLAG_VALUES[multiline]
# Если глобально флаг MULTILINE включен, но в
# атрибутах тэга <reg> этот флаг присутствует со
# значением False -- для этого регулярного
# выражения этот флаг также будет False.
multiline_global = self._multiline_flag & multiline
else:
multiline = False
multiline_global = self._multiline_flag
if multiline_global or multiline:
regex_flags |= re.MULTILINE
if 'dotall' in patch_element.attrib:
dotall = patch_element.attrib['dotall']
if dotall not in self._FLAG_VALUES:
error_message = 'Error: Invalid dotall value.'
print(error_message)
return False
else:
dotall = self._FLAG_VALUES[dotall]
# Если глобально флаг DOTALL включен, но в
# атрибутах тэга <reg> этот флаг присутствует со
# значением False -- для этого регулярного
# выражения этот флаг также будет False.
dotall_global = self._dotall_flag & dotall
else:
dotall = False
dotall_global = self._dotall_flag
if dotall_global or dotall:
regex_flags |= re.DOTALL
regex_expression = re.compile(element_text,
regex_flags)
else:
text_for_replace = element_text
else:
if patch_element.tag in PATCH_DOCUMENT_TAGS:
error_message = 'Error: <{0}> is expected, \
<{1}> instead.'.format(
patch_tag,
patch_element.tag
)
print(error_message)
else:
error_message = 'Error: Unknown tag: {0}'.format(
patch_element.tag
)
print(error_message)
# Какая-то обработка ошибки.
error_message = 'Error: Incorrect text of the template.'
print(error_message)
return False
else:
self._document_to_patch = re.sub(regex_expression,
text_for_replace,
self._document_to_patch)
continue
return True

@ -0,0 +1,98 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import Word, Literal, alphanums, printables, originalTextFor,\
ZeroOrMore, OneOrMore, ParseException,\
pyparsing_unicode, Group, Optional
class PostfixFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_parameter_line,
self._parse_to_delete_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._format = 'postfix'
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
parameter_name = Word(alphanums+'_')
parameter_value = originalTextFor(OneOrMore(Word(printables)))
action_symbols = (Literal('!') | Literal('-'))
assignment = Literal('=')
self._parameter_line = (Group(Optional(action_symbols,
default='')('action')
+ parameter_name)('parameter_name')
+ assignment.suppress()
+ parameter_value('parameter_value'))
self._parameter_to_delete = (action_symbols('action')
+ parameter_name('Name')
)('parameter_name')
self._comment_line = originalTextFor(
Literal('#')
+ ZeroOrMore(Word(printables
+ pyparsing_unicode.alphanums))
)('comment')
def _parse_parameter_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._parameter_line.parseString(line)
self._match = True
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = parsing_result.parameter_value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._item_to_add[key_value] = parameter_value
self._ready_to_update = True
except ParseException:
return
def _parse_to_delete_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._parameter_to_delete.parseString(line)
self._match = True
if parsing_result.action == '-':
return
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = self._last_comments_list
self._last_comments_list = []
self._item_to_add[key_value] = parameter_value
self._ready_to_update = True
except ParseException:
return
def _parse_comment_line(self, line):
try:
parsing_result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(parsing_result.comment)
except ParseException:
return

@ -0,0 +1,99 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import Word, Literal, alphanums, printables, originalTextFor,\
ZeroOrMore, OneOrMore, ParseException, restOfLine,\
pyparsing_unicode, Group, Optional
class ProcmailFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_parameter_line,
self._parse_to_delete_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._comments_processing = True
self._format = 'procmail'
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
parameter_name = Word(alphanums+'_.')
parameter_value = originalTextFor(OneOrMore(Word(printables)))
action_symbols = (Literal('!') | Literal('-'))
self._parameter_line = (Group(Optional(action_symbols,
default='')('action')
+ parameter_name('Name')
)('parameter_name')
+ Literal('=').suppress()
+ parameter_value('parameter_value'))
self._parameter_to_delete = (Group(action_symbols('action')
+ parameter_name('Name')
)('parameter_name')
+ restOfLine.suppress())
self._comment_line = originalTextFor(
Literal('#')
+ ZeroOrMore(
Word(printables
+ pyparsing_unicode.alphanums)
)
)('comment')
def _parse_parameter_line(self, line):
try:
parsing_result = self._parameter_line.parseString(line)
self._match = True
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = parsing_result.parameter_value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._item_to_add = OrderedDict({key_value: parameter_value})
self._ready_to_update = True
except ParseException:
return
def _parse_to_delete_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._parameter_to_delete.parseString(line)
self._match = True
if parsing_result.parameter_name.action == '-':
return
key_value = tuple(parsing_result.parameter_name.asList())
parameter_value = self._last_comments_list
self._last_comments_list = []
self._item_to_add = OrderedDict({key_value: parameter_value})
self._ready_to_update = True
except ParseException:
return
def _parse_comment_line(self, line):
try:
parsing_result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(parsing_result.comment)
except ParseException:
return

@ -0,0 +1,411 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from jinja2 import Environment, PackageLoader
from collections import OrderedDict
from pyparsing import originalTextFor, Literal, ZeroOrMore, Word, printables,\
OneOrMore, alphanums, ParseException, pyparsing_unicode,\
Group, Optional, alphas, Keyword
class ProFTPDFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = [self._parse_comment_line,
self._parse_section_start_line,
self._parse_section_end_line,
self._parse_single_key_directive_line,
self._parse_double_key_directive_line,
self._parse_to_delete_double_key_directive_line,
self._parse_full_key_directive_line,
self._parse_plain_directive_line,
self._parse_to_delete_plain_directive_line]
super().__init__(processing_methods)
self._ignore_comments = ignore_comments
self._need_finish = True
self._comments_processing = True
self._format = 'proftpd'
self._section_stack = []
self._actions_stack = []
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
left_angle_bracket = Literal('<')
right_angle_bracket = Literal('>')
slash = Literal('/')
action_symbols = (Literal('!') |
Literal('-'))
directive = Word(alphas, alphanums)
section_value = Word(printables, excludeChars='<>')
directive_value = Word(printables)
self._section_start_parser = (left_angle_bracket.suppress()
+ Optional(action_symbols,
default='')('action')
+ Group(directive('name')
+ originalTextFor(
OneOrMore(section_value)
)('value')
)('directive')
+ right_angle_bracket.suppress())
self._section_end_parser = (left_angle_bracket.suppress()
+ slash.suppress()
+ directive('directive')
+ right_angle_bracket.suppress())
self._plain_directive_parser = (Optional(action_symbols)('action')
+ Group(directive('name')
+ originalTextFor(
OneOrMore(directive_value)
)('value')
)('directive')
)
self._delete_plain_directive_parser = (action_symbols('action')
+ directive('directive'))
single_key_directive = (Keyword('AllowAll') |
Keyword('DenyAll') |
Keyword('AccessDenyMsg') |
Keyword('AccessGrantMsg') |
Keyword('ByteRatioErrMsg') |
Keyword('LeechRatioMsg') |
Keyword('CwdRatioMsg') |
Keyword('FileRatioErrMsg'))
self._single_key_directive_parser = (Optional(action_symbols)('action')
+ single_key_directive(
'directive'
))
double_key_directive = (Keyword('AccessDenyMsg') |
Keyword('AccessGrantMsg') |
Keyword('ByteRatioErrMsg') |
Keyword('Allow from') | Keyword('Allow') |
Keyword('AllowFilter') |
Keyword('AnonymousGroup') |
Keyword('AuthPAMConfig') |
Keyword('Bind') |
Keyword('CDPath') |
Keyword('Define') |
Keyword('Deny from') | Keyword('Deny') |
Keyword('DenyFilter') |
Keyword('DisplayChdir') |
Keyword('ExtendedLog') |
Keyword('AnonRatio') |
Keyword('GroupRatio') |
Keyword('HideGroup') |
Keyword('HideUser') |
Keyword('HostRatio') |
Keyword('Include') |
Keyword('LDAPAttr') |
Keyword('LeechRatioMsg') |
Keyword('CwdRatioMsg') |
Keyword('FileRatioErrMsg') |
Keyword('LogFormat') |
Keyword('MaxClientsPerClass') |
Keyword('PIDFile') |
Keyword('RewriteMap') |
Keyword('RewriteRule') |
Keyword('SetEnv') |
Keyword('SQLConnectInfo') |
Keyword('SQLGroupWhereClause') |
Keyword('SQLLog') |
Keyword('SQLNamedQuery') |
Keyword('SQLShowInfo') |
Keyword('SQLUserInfo') |
Keyword('SQLUserWhereClause') |
Keyword('LoadModule') |
Keyword('LoadFile') |
Keyword('TransferRate') |
Keyword('UnsetEnv') |
Keyword('UserPassword') |
Keyword('UserRatio') |
Keyword('ModuleControlsACLs') |
Keyword('ControlsACLs'))
self._double_key_directive_parser = (Optional(action_symbols)('action')
+ Group((double_key_directive
+ directive_value
)('name')
+ originalTextFor(
ZeroOrMore(
directive_value
)
)('value')
)('directive')
)
self._delete_double_key_directive_parser = (action_symbols('action')
+ Group(
(
double_key_directive
+ directive_value
)('name')
)('directive')
)
full_key_directive = (Keyword('AllowClass') |
Keyword('AllowGroup') |
Keyword('AllowUser') |
Keyword('Class') |
Keyword('DenyClass') |
Keyword('DenyGroup') |
Keyword('DenyUser') |
Keyword('DirFakeGroup') |
Keyword('DirFakeUser') |
Keyword('HideFiles') |
Keyword('MaxRetrieveFileSize') |
Keyword('MaxStoreFileSize') |
Keyword('RewriteCondition') |
Keyword('RewriteLock') |
Keyword('TimeoutSession') |
Keyword('UserAlias'))
self._full_key_directive_parser = (Optional(action_symbols)('action')
+ Group(full_key_directive
+ OneOrMore(
directive_value
)
)('directive')
)
self._comment_line = originalTextFor(
Literal('#')
+ ZeroOrMore(Word(printables
+ pyparsing_unicode.alphanums))
)('comment')
def _parse_section_start_line(self, line):
try:
parsing_result = self._section_start_parser.parseString(line)
self._match = True
section_name = tuple(parsing_result.directive.asList())
self._actions_stack.append(parsing_result.action)
self._section_stack.append(section_name)
except ParseException:
return
def _parse_section_end_line(self, line):
try:
parsing_result = self._section_end_parser.parseString(line)
self._match = True
current_section = self._section_stack.pop()
self._actions_stack.pop()
directive = tuple(parsing_result.directive)
if not current_section[1] != directive:
# Здесь будет кидаться исключение.
self._fatal_error_flag = True
return
except ParseException:
return
def _parse_plain_directive_line(self, line):
try:
parsing_result = self._plain_directive_parser.parseString(line)
self._match = True
for action_item in self._actions_stack:
if not action_item == '':
action = (action_item, )
break
else:
action = (parsing_result.action, )
if not self._section_stack == []:
context = (tuple(self._section_stack), )
else:
context = ('', )
directive = (parsing_result.directive.name, )
directive_value = [parsing_result.directive.value]
directive_name = action + context + directive
directive_value = self._last_comments_list + directive_value
self._last_comments_list = []
self._item_to_add = OrderedDict({directive_name: directive_value})
self._ready_to_update = True
except ParseException:
return
def _parse_to_delete_plain_directive_line(self, line):
try:
parsing_result = self._delete_plain_directive_parser.parseString(
line
)
self._match = True
action = (parsing_result.action, )
if not self._section_stack == []:
context = (tuple(self._section_stack), )
else:
context = ('', )
directive = (parsing_result.directive, )
directive_name = action + context + directive
directive_value = self._last_comments_list + ['']
self._last_comments_list = []
self._item_to_add = OrderedDict({directive_name: directive_value})
self._ready_to_update = True
except ParseException:
return
def _parse_single_key_directive_line(self, line):
try:
parsing_result = self._single_key_directive_parser.parseString(
line
)
self._match = True
for action_item in self._actions_stack:
if not action_item == '':
action = (action_item, )
break
else:
action = (parsing_result.action, )
if not self._section_stack == []:
context = (tuple(self._section_stack), )
else:
context = ('', )
directive = (parsing_result.directive, )
directive_value = ['']
directive_name = action + context + directive
directive_value = self._last_comments_list + directive_value
self._last_comments_list = []
self._item_to_add = OrderedDict({directive_name: directive_value})
self._ready_to_update = True
except ParseException:
return
def _parse_double_key_directive_line(self, line):
try:
parsing_result = self._double_key_directive_parser.parseString(
line
)
self._match = True
for action_item in self._actions_stack:
if not action_item == '':
action = (action_item, )
break
else:
action = (parsing_result.action, )
if not self._section_stack == []:
context = (tuple(self._section_stack), )
else:
context = ('', )
directive = tuple(parsing_result.directive.name.asList())
directive_value = [parsing_result.directive.value]
directive_name = action + context + directive
directive_value = self._last_comments_list + directive_value
self._last_comments_list = []
self._item_to_add = OrderedDict({directive_name: directive_value})
self._ready_to_update = True
except ParseException:
return
def _parse_to_delete_double_key_directive_line(self, line):
try:
parsing_result = self._delete_double_key_directive_parser.\
parseString(line)
self._match = True
action = (parsing_result.action, )
if not self._section_stack == []:
context = (tuple(self._section_stack), )
else:
context = ('', )
directive = tuple(parsing_result.directive.name.asList())
directive_name = action + context + directive
directive_value = self._last_comments_list + ['']
self._last_comments_list = []
self._item_to_add = OrderedDict({directive_name: directive_value})
self._ready_to_update = True
except ParseException:
return
def _parse_full_key_directive_line(self, line):
try:
parsing_result = self._full_key_directive_parser.parseString(line)
self._match = True
for action_item in self._actions_stack:
if not action_item == '':
action = (action_item, )
break
else:
action = (parsing_result.action, )
if not self._section_stack == []:
context = (tuple(self._section_stack), )
else:
context = ('', )
directive = tuple(parsing_result.directive.asList())
directive_value = ['']
directive_name = action + context + directive
directive_value = self._last_comments_list + directive_value
self._last_comments_list = []
self._item_to_add = OrderedDict({directive_name: directive_value})
self._ready_to_update = True
except ParseException:
return
def _parse_comment_line(self, line):
try:
result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(result.comment)
except ParseException:
return
def get_document_text(self):
file_loader = PackageLoader('calculate.templates.format',
self.TEMPLATES_DIRECTORY)
formats_environment = Environment(loader=file_loader)
formats_environment.globals.update(zip=zip)
formats_environment.add_extension('jinja2.ext.do')
template = formats_environment.get_template(self._format)
document_text = template.render(
document_dictionary=self._document_dictionary
)
return document_text

@ -0,0 +1,163 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from collections import OrderedDict
from pyparsing import originalTextFor, Literal, ZeroOrMore, Word, printables,\
OneOrMore, alphanums, ParseException, pyparsing_unicode,\
Optional, Group
class SambaFormat(BaseFormat):
def __init__(self, document_text: str,
ignore_comments=False,
join_before=False):
processing_methods = [self._parse_comment_line,
self._parse_section_line,
self._parse_parameter_line,
self._parse_to_delete_line]
super().__init__(processing_methods)
self._current_section = OrderedDict()
self._current_section_name = ''
self._ignore_comments = ignore_comments
self._need_finish = True
self._comments_processing = True
self._join_before = join_before
self._format = 'samba'
self._last_comments_list = []
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
document_lines = self._get_list_of_logic_lines(document_text)
self._lines_to_dictionary(document_lines)
def _initialize_parser(self):
action_symbols = (Literal('!') | Literal('-'))
comment_symbols = (Literal('#') | Literal(';'))
assignment_symbol = Literal('=')
section_name = originalTextFor(OneOrMore(Word(alphanums+'_')))
self._section_line = (Literal('[').suppress()
+ Optional(action_symbols, default='')('action')
+ section_name('name') + Literal(']').suppress()
)('section_name')
parameter_name = originalTextFor(
OneOrMore(Word(printables,
excludeChars='='))
)
parameter_value = originalTextFor(
OneOrMore(Word(printables))
)
self._parameter_line = (Group(Optional(action_symbols('action'),
default='')
+ parameter_name('name')
)('parameter_name')
+ assignment_symbol.suppress()
+ parameter_value('parameter_value'))
self._parameter_to_delete = (action_symbols('action')
+ parameter_name('name')
)('parameter_name')
self._comment_line = originalTextFor(
comment_symbols
+ ZeroOrMore(Word(
printables
+ pyparsing_unicode.alphanums))
)('comment')
def _parse_section_line(self, line):
try:
self._item_to_add = OrderedDict()
parsing_result = self._section_line.parseString(line)
self._match = True
if self._current_section_name != '':
if self._current_section_name in \
self._document_dictionary.keys():
self._document_dictionary[self._current_section_name].\
update(self._current_section)
else:
self._item_to_add[self._current_section_name] = \
self._current_section
self._ready_to_update = True
self._current_section = OrderedDict()
self._current_section_name = (parsing_result.action,
parsing_result.name.lower())
if self._last_comments_list != []:
self._current_section['#'] = self._last_comments_list
self._last_comments_list = []
except ParseException:
return
def _parse_parameter_line(self, line):
try:
parsing_result = self._parameter_line.parseString(line)
self._match = True
key_value = (parsing_result.parameter_name.action,
parsing_result.parameter_name.name.lower())
parameter_value = parsing_result.parameter_value
parameter_value = self._last_comments_list + [parameter_value]
self._last_comments_list = []
self._current_section[key_value] = parameter_value
except ParseException:
return
def _parse_to_delete_line(self, line):
try:
parsing_result = self._parameter_to_delete.parseString(line)
self._match = True
if parsing_result.action == '-':
return
key_value = (parsing_result.action,
parsing_result.name.lower())
parameter_value = self._last_comments_list
self._last_comments_list = []
self._current_section[key_value] = parameter_value
except ParseException:
return
def _parse_comment_line(self, line):
try:
parsing_result = self._comment_line.parseString(line)
self._match = True
if not self._ignore_comments:
self._last_comments_list.append(parsing_result.comment)
except ParseException:
return
def _finish_method(self):
self._item_to_add = OrderedDict()
if self._current_section_name in self._document_dictionary.keys():
self._document_dictionary[self._current_section_name].update(
self._current_section
)
else:
self._item_to_add[self._current_section_name] =\
self._current_section
self._document_dictionary.update(self._item_to_add)
self._item_to_add = OrderedDict()
self._current_section = OrderedDict()

@ -0,0 +1,27 @@
{% for item_name, item_value in document_dictionary.items() recursive %}
{% if item_name != '#' %}
{% if item_value is mapping %}
{% if not loop.first %}
{% endif %}
{% if '#' in item_value %}
{% for comment in item_value['#'] %}
{{ comment }}
{% endfor %}
{% endif %}
{% if item_name[1] == 'inet' %}
{{ item_name[1:] | join(' ') }}
{%- for keyword in item_value %}
{%- if keyword != '#' %} {{ keyword[1] }} { {{ item_value[keyword] | join('; ')}}; }{% endif %}{% endfor %};
{% else %}
{{ item_name[1:] | join(' ') }} {
{{ loop(item_value.items()) | indent}}};
{% endif %}
{% else %}
{% for comment in item_value[:-1] %}
{{ comment }}
{% endfor %}
{{ item_name[1:] | join(' ') }}{% if not item_value[-1] == '' %} {{ item_value[-1] }}{% endif%};
{% endif %}
{% endif %}
{% endfor %}

@ -0,0 +1,17 @@
{% for section_name in document_dictionary.keys() %}
{% if '#' in document_dictionary[section_name].keys() %}
{% for comment in document_dictionary[section_name]['#'] %}
{{ comment }}
{% endfor %}
{% endif %}
[{{ section_name[1] }}]
{% for parameter_name in document_dictionary[section_name].keys() %}
{% if parameter_name != '#' %}
{% for comment in document_dictionary[section_name][parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1] }}={{ document_dictionary[section_name][parameter_name][-1] }}
{% endif %}
{% endfor %}
{% endfor %}

@ -0,0 +1,28 @@
{% for item_name, item_value in document_dictionary.items() recursive %}
{% if item_name != '#' %}
{% if item_value is mapping %}
{% if '#' in item_value %}
{% for comment in item_value['#'] %}
{{ comment }}
{% endfor %}
{% endif %}
{{ item_name[1:] | join(' ') }} {
{{ loop(item_value.items()) | indent}}}
{% else %}
{% for comment in item_value[:-1] %}
{{ comment }}
{% endfor %}
{{ item_name[1:] | join(' ') }}{%- if not item_value[-1] == '' %} = {{ item_value[-1] }}
{% else %}
{%- if not loop.last%}
{% endif %}
{% endif %}
{% endif %}
{% if not loop.last%}
{% endif %}
{% endif %}
{% endfor %}

@ -0,0 +1,19 @@
{% for section_name in document_dictionary.keys() %}
{% if '#' in document_dictionary[section_name].keys() %}
{% for comment in document_dictionary[section_name]['#'] %}
{{ comment }}
{% endfor %}
{% endif %}
{% for section_part in section_name[1:] %}
[{{ section_part }}]{% endfor %}
{% for parameter_name in document_dictionary[section_name].keys() %}
{% if parameter_name != '#' %}
{% for comment in document_dictionary[section_name][parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1] }}={{ document_dictionary[section_name][parameter_name][-1] }}
{% endif %}
{% endfor %}
{% endfor %}

@ -0,0 +1,6 @@
{% for parameter_name in document_dictionary.keys() %}
{% for comment in document_dictionary[parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1] }}={{ document_dictionary[parameter_name][-1] }}
{% endfor %}

@ -0,0 +1,59 @@
{% for section_type in document_dictionary.keys() %}
{% if '#' in document_dictionary[section_type] %}
{% for comment in document_dictionary[section_type]['#']%}
{{ comment }}
{% endfor %}
{% endif %}
{% if section_type != ('', 'global')%}
{{ section_type[1] }} {{ section_type[2] }}
{% endif %}
{% for directive in document_dictionary[section_type].keys() if directive[1] == 'include' %}
{% for comment in document_dictionary[section_type][directive][:-1] %}
{{ comment }}
{% endfor %}
{{ directive[1] }} {{ directive[2] }}
{% endfor %}
{% for directive in document_dictionary[section_type].keys() %}
{% if directive != '#' and directive[1] != 'include' %}
{% set directive_value = document_dictionary[section_type][directive] %}
{% if directive[1] == 'access to' %}
{% set access_values = directive_value.keys()|list %}
{% if '#' in directive_value %}
{% for comment in directive_value['#'] %}
{{ comment }}
{% endfor %}
{% set access_values = access_values[1:] %}
{% endif %}
{% if access_values|length == 1 %}
{{ directive[1] }} {{ directive[2] }} by {{ access_values[0][1] }} {{ directive_value[access_values[0]][0] }}
{% else %}
{{ directive[1] }} {{ directive[2] }}
{% for value in access_values|reverse %}
by {{ value[1] }} {{ directive_value[value][0] }}
{% endfor %}
{% endif %}
{% elif directive[1] == 'syncrepl' %}
{% set syncrepl_values = directive_value.keys()|list%}
{% if '#' in directive_value %}
{% for comment in directive_value['#'] %}
{{ comment }}
{% endfor %}
{% set syncrepl_values = syncrepl_values[1:]%}
{% endif %}
{{ directive[1] }} {{ directive[2] }}
{% for value in syncrepl_values %}
{{ value[1] }}={{ directive_value[value][0] }}
{% endfor %}
{% else %}
{% for comment in directive_value[:-1] %}
{{ comment }}
{% endfor %}
{{ directive[1:]|join(' ') }}{% if directive_value[-1] != '' %} {{ directive_value[-1] }}
{% else %}
{% endif %}
{% endif %}
{% endif %}
{% endfor %}
{% endfor %}

@ -0,0 +1,7 @@
{% for parameter_name in document_dictionary.keys() %}
{% for comment in document_dictionary[parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1] }}={{ document_dictionary[parameter_name][-1] }}
{% endfor %}

@ -0,0 +1,8 @@
{% for parameter_name in document_dictionary.keys() %}
{% for comment in document_dictionary[parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1] }} = {{ document_dictionary[parameter_name][-1] }}
{% endfor %}

@ -0,0 +1,7 @@
{% for parameter_name in document_dictionary.keys() %}
{% for comment in document_dictionary[parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1] }}={{ document_dictionary[parameter_name][-1] }}
{% endfor %}

@ -0,0 +1,38 @@
{%- set section_stack = [] -%}
{%- set counters = namespace(level=0,indent=0) -%}
{%- for item_name, item_value in document_dictionary.items() -%}
{%- set count_flag = True -%}
{%- set counters.level = 0 -%}
{%- for item_level, current_level in zip(item_name[1], section_stack) -%}
{%- if not item_level == current_level -%}
{%- set count_flag = False -%}
{%- elif count_flag -%}
{%- set counters.level = counters.level + 1 -%}
{%- endif -%}
{%- endfor -%}
{%- for section_name in section_stack[counters.level: ] | reverse -%}
{%- set counters.indent = counters.indent - 1 -%}
{{- ' ' * counters.indent }}</{{ section_name[0] }}>
{% if loop.last %}
{% endif -%}
{% do section_stack.pop() -%}
{%- endfor -%}
{%- for comment in item_value[:-1] -%}
{% if loop.first %}
{% endif -%}
{{ ' ' * counters.indent }}{{ comment }}
{% endfor -%}
{%- for section_name in item_name[1][counters.level: ] -%}
{{ ' ' * counters.indent }}<{{ section_name | join(' ') }}>
{% set counters.indent = counters.indent + 1 -%}
{%- do section_stack.append(section_name) -%}
{%- endfor -%}
{{ ' ' * counters.indent }}{{ item_name[2:] | join(' ') }}{% if not item_value[-1] == '' %} {{ item_value[-1] }}{% endif %}
{% endfor -%}
{%- for section_name in section_stack | reverse -%}
{%- set counters.indent = counters.indent - 1 -%}
{{ ' ' * counters.indent }}</{{ section_name[0] }}>
{%- if not loop.last %}
{% endif -%}
{%- endfor %}

@ -0,0 +1,16 @@
{% for section_name in document_dictionary.keys() %}
{% if '#' in document_dictionary[section_name].keys() %}
{% for comment in document_dictionary[section_name]['#'] %}
{{ comment }}
{% endfor %}
{% endif %}
[{{ section_name[1] }}]
{% for parameter_name in document_dictionary[section_name].keys() %}
{% if parameter_name != '#' %}
{% for comment in document_dictionary[section_name][parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1] }} = {{ document_dictionary[section_name][parameter_name][-1] }}
{% endif %}
{% endfor %}
{% endfor %}

@ -0,0 +1,14 @@
{% for parameter_name, parameter_value in document_dictionary.items() %}
{% for comment in document_dictionary[parameter_name][:-1]%}
{{ comment }}
{% endfor %}
{{ parameter_name[1:] | join(' ') }}{%- if not parameter_value[-1] == '' %} {{ parameter_value[-1] }}
{% else %}
{%- if not loop.last%}
{% endif %}
{% endif %}
{% endfor %}

@ -0,0 +1,223 @@
# vim: fileencoding=utf-8
#
from pyparsing import originalTextFor, Literal, Word, printables, OneOrMore,\
Optional
from .base_format import BaseFormat
from collections import OrderedDict
try:
from lxml.etree import Element, SubElement, ElementTree, tostring
except ImportError:
from xml.etree.ElementTree import Element, SubElement, ElementTree, \
tostring
class XMLGConfFormat(BaseFormat):
def __init__(self, document_text: str):
processing_methods = OrderedDict({'gconf': self._gconf,
'entry': self._entry,
'dir': self._dir,
'stringvalue': self._stringvalue,
'default': self._default,
'local_schema': self._local_schema,
'li': self._li,
'longdesc': self._longdesc,
'unknown': self._unknown})
super().__init__(processing_methods)
self._format = 'xml_gconf'
self._initialize_parser()
self._parse_xml_to_dictionary(document_text)
def _initialize_parser(self):
action_symbols = (Literal('!') | Literal('-'))
name = originalTextFor(OneOrMore(Word(printables)))
self._node_name = Optional(action_symbols)('action') + name('name')
def _entry(self, xml_element):
try:
element_items = OrderedDict(xml_element.attrib)
name = element_items.pop('name')
parsing_result = self._node_name.parseString(name)
if 'value' in element_items:
entry_value = element_items.pop('value')
elif 'ltype' in element_items:
entry_value = []
for child in xml_element:
item_to_add = self._processing_methods.get(child.tag,
self._unknown
)(child)
entry_value.append(item_to_add)
else:
entry_value = OrderedDict()
for child in xml_element:
item_to_add = self._processing_methods.get(child.tag,
self._unknown
)(child)
entry_value.update(item_to_add)
element_name = (parsing_result.action,
xml_element.tag,
('name', parsing_result.name),
*element_items.items())
return OrderedDict({element_name: entry_value})
except Exception:
# Какая-то обработка ошибки.
return OrderedDict()
def _gconf(self, xml_element):
output_dictionary = OrderedDict()
element_name = ('', xml_element.tag)
for child in xml_element:
item_to_add = self._processing_methods.get(child.tag,
self._unknown)(child)
output_dictionary.update(item_to_add)
return OrderedDict({element_name: output_dictionary})
def _dir(self, xml_element):
output_dictionary = OrderedDict()
try:
parsing_result = self._node_name.parseString(
xml_element.attrib['name']
)
element_name = (parsing_result.action,
xml_element.tag,
('name', parsing_result.name))
except Exception:
# Какая-то обработка ошибки.
return OrderedDict()
for child in xml_element:
item_to_add = self._processing_methods.get(child.tag,
self._unknown)(child)
output_dictionary.update(item_to_add)
return OrderedDict({element_name: output_dictionary})
def _longdesc(self, xml_element):
element_name = ('', 'longdesc')
description = xml_element.text
if description is not None:
return OrderedDict({element_name: description})
else:
# Пустая строка. Возможно ошибка.
# Какая-то обработка ошибки.
return OrderedDict({element_name: ''})
def _local_schema(self, xml_element):
output_dictionary = OrderedDict()
try:
element_name = ('', xml_element.tag,
*xml_element.items())
except Exception:
# Какая-то обработка ошибки.
return OrderedDict()
for child in xml_element:
item_to_add = self._processing_methods.get(child.tag,
self._unknown)(child)
output_dictionary.update(item_to_add)
return OrderedDict({element_name: output_dictionary})
def _stringvalue(self, xml_element):
element_name = ('', 'stringvalue')
value = xml_element.text
if value is not None:
return OrderedDict({element_name: value})
else:
# Пустая строка. Возможно ошибка.
# Какая-то обработка ошибки.
return OrderedDict({element_name: ''})
def _default(self, xml_element):
output_dictionary = OrderedDict()
element_name = ('', xml_element.tag, *xml_element.items())
for child in xml_element:
item_to_add = self._processing_methods.get(child.tag,
self._unknown)(child)
output_dictionary.update(item_to_add)
return OrderedDict({element_name: output_dictionary})
def _li(self, xml_element):
child = next(iter(xml_element))
list_element = self._processing_methods.get(child.tag,
self._unknown)(child)
# Единственным возможным типом списковых значений пока является string.
string_value = next(iter(list_element.values()))
return string_value
def _unknown(self, xml_element):
# Действия если элемент неизвестен.
element_name = ('', Element.tag)
return OrderedDict({element_name: 'Unknown element'})
def get_document_text(self):
gconf_header = next(iter(self._document_dictionary))
root = Element('gconf')
self._build_section(root, self._document_dictionary[gconf_header])
document_tree = ElementTree(root)
xml_document = tostring(document_tree,
encoding="UTF-8",
xml_declaration=True,
pretty_print=True).decode()
return xml_document
def _build_section(self, current_element, dictionary):
for dict_element in dictionary.keys():
element_tag = dict_element[1]
element_attributes = OrderedDict({key: value for key, value in
dict_element[2:]})
if element_tag == 'dir' or element_tag == 'local_schema'\
or element_tag == 'default':
include_element = SubElement(current_element,
element_tag,
**element_attributes)
self._build_section(include_element,
dictionary[dict_element])
elif element_tag == 'entry':
if isinstance(dictionary[dict_element], OrderedDict):
include_element = SubElement(current_element,
element_tag,
**element_attributes)
self._build_section(include_element,
dictionary[dict_element])
elif 'ltype' in element_attributes:
if element_attributes['ltype'] == 'string':
entry_element = SubElement(current_element,
element_tag,
**element_attributes)
for value in dictionary[dict_element]:
list_element = SubElement(entry_element,
'li', type='string')
include_element = SubElement(list_element,
'stringvalue')
include_element.text = value
else:
include_element = SubElement(current_element,
element_tag,
**element_attributes,
value=dictionary[dict_element]
)
elif element_tag == 'longdesc' or element_tag == 'stringvalue':
include_element = SubElement(current_element,
element_tag)
include_element.text = dictionary[dict_element]

@ -0,0 +1,164 @@
# vim: fileencoding=utf-8
#
from .base_format import BaseFormat
from pyparsing import originalTextFor, Literal, Word, printables, OneOrMore,\
Optional
from collections import OrderedDict
try:
from lxml.etree import Element, SubElement, ElementTree, tostring
except ImportError:
from xml.etree.ElementTree import Element, SubElement, ElementTree, \
tostring
class XMLXfceFormat(BaseFormat):
def __init__(self, document_text: str, ignore_comments=False):
processing_methods = OrderedDict({'channel': self._channel,
'property': self._property,
'value': self._value,
'unknown': self._unknown})
super().__init__(processing_methods)
self._format = 'xml_xfce'
self._initialize_parser()
if document_text == '':
self._document_dictionary = OrderedDict()
else:
self._parse_xml_to_dictionary(document_text)
def _initialize_parser(self):
action_symbols = (Literal('!') | Literal('-'))
name = originalTextFor(OneOrMore(Word(printables)))
self._node_name = Optional(action_symbols)('action') + name('name')
# Кортежи с названиями атрибутов различных элементов.
self._ELEMENT_ATTRIBUTES = ('tag', 'name', 'type', 'value')
self._CHANNEL_ATTRIBUTES = ('tag', 'name', 'version')
self._VALUE_ATTRIBUTES = ('tag', 'type', 'value')
def _property(self, xml_element):
try:
parsing_result = self._node_name.parseString(
xml_element.attrib['name']
)
element_name = (parsing_result.action,
xml_element.tag,
parsing_result.name,
xml_element.attrib['type'])
except Exception:
# Какая-то обработка ошибки.
return OrderedDict()
if xml_element.attrib['type'] == 'empty':
output = OrderedDict()
for child in xml_element:
child_value = self._processing_methods.get(child.tag,
self._unknown
)(child)
output.update(child_value)
elif xml_element.attrib['type'] == 'array':
output = []
for child in xml_element:
child_value = self._processing_methods.get(child.tag,
self._unknown
)(child)
output.append(child_value)
else:
try:
output = xml_element.attrib['value']
except KeyError:
# Какая-то обработка ошибки.
return OrderedDict()
return OrderedDict({element_name: output})
def _value(self, xml_element):
try:
value = (xml_element.tag,
xml_element.attrib['type'],
xml_element.attrib['value'])
except KeyError:
# Какая-то обработка ошибки.
return ('',)
return value
def _channel(self, xml_element):
output_dictionary = OrderedDict()
try:
parsing_result = self._node_name.parseString(
xml_element.attrib['name']
)
element_name = (parsing_result.action,
xml_element.tag,
parsing_result.name,
xml_element.attrib['version'])
except Exception:
# Какая-то обработка ошибки.
return OrderedDict()
for child in xml_element:
item_to_add = self._processing_methods.get(child.tag,
self._unknown)(child)
output_dictionary.update(item_to_add)
return OrderedDict({element_name: output_dictionary})
def _unknown(self, xml_element):
# Действия если элемент неизвестен.
element_name = ('', xml_element.tag)
return OrderedDict({element_name: 'Unknown element'})
def get_document_text(self):
channel = next(iter(self._document_dictionary.keys()))
channel_head = OrderedDict(
{key: value for key, value in
zip(self._CHANNEL_ATTRIBUTES, channel[1:])}
)
root = Element(channel_head.pop('tag'), **channel_head)
self._build_section(root, self._document_dictionary[channel])
document_tree = ElementTree(root)
xml_document = tostring(document_tree,
encoding="UTF-8",
xml_declaration=True,
pretty_print=True).decode()
return xml_document
def _build_section(self, current_element, dictionary):
for dict_element in dictionary.keys():
element_head = OrderedDict({key: value for key, value in
zip(self._ELEMENT_ATTRIBUTES,
dict_element[1:])})
if element_head['type'] == 'empty':
include_element = SubElement(current_element,
element_head.pop('tag'),
**element_head)
self._build_section(include_element,
dictionary[dict_element])
elif element_head['type'] == 'array':
include_element = SubElement(current_element,
element_head.pop('tag'),
**element_head)
for list_element in dictionary[dict_element]:
list_element_head = OrderedDict(
{key: value for key, value in
zip(self._VALUE_ATTRIBUTES,
list_element)}
)
SubElement(include_element,
list_element_head.pop('tag'),
**list_element_head)
else:
SubElement(current_element,
element_head.pop('tag'),
**element_head,
value=dictionary[dict_element])

@ -0,0 +1,261 @@
# vim: fileencoding=utf-8
#
from subprocess import Popen, PIPE
from io import TextIOWrapper
from os import path
import os
class FilesError(Exception):
pass
class PipeProcess():
def _get_stdout(self):
return PIPE
def close(self):
pass
@property
def shell_command(self):
return ''
class KeyboardInputProcess():
def _get_stdout(self):
return None
def close(self):
pass
@property
def shell_command(self):
return ''
class Process():
def __init__(self, command, *parameters, **kwargs):
if 'stdin' not in kwargs:
self._stdin = PipeProcess()
elif kwargs['stdin'] == PIPE:
self._stdin = PipeProcess()
elif kwargs['stdin'] is None:
self._stdin = KeyboardInputProcess()
else:
self._stdin = kwargs['stdin']
self._stdout = kwargs.get('stdout', PIPE)
self._stderr = kwargs.get('stderr', PIPE)
self._envdict = kwargs.get('envdict', os.environ.copy())
self._envdict['LANG'] = kwargs.get('lang', 'C')
self._timeout = kwargs.get('timeout', None)
self._cwd = kwargs.get('cwd', None)
self._command = _get_program_path(command)
if not self._command:
raise FilesError("command not found '{}'".format(command))
self._command = [self._command, *parameters]
self._process = None
self._iterator = iter([])
# Flags.
self._opened = False
self._is_read = False
self._readable = False
self._writable = False
self._readable_errors = False
# I/O handlers.
self.stdin_handler = None
self.stdout_handler = None
self.stderr_handler = None
# Caches.
self._output_cache = ''
self._error_cache = ''
def _get_stdout(self):
self._open_process()
return self.stdout_handler
def _get_stdin(self):
return self.stdin_handler
def _open_process(self):
try:
piped_stdin = self._stdin._get_stdout()
self._process = Popen(self._command,
stdout=self._stdout,
stdin=piped_stdin,
stderr=self._stderr,
cwd=self._cwd,
close_fds=True,
env=self._envdict)
if piped_stdin == PIPE:
self.stdin_handler = TextIOWrapper(self._process.stdin,
encoding='utf8')
self._writable = True
elif piped_stdin is not None:
self.stdin_handler = self._stdin._get_stdin()
self._writable = True
if self._stdout == PIPE:
self.stdout_handler = TextIOWrapper(self._process.stdout,
encoding='utf8')
self._readable = True
if self._stderr == PIPE:
self.stderr_handler = TextIOWrapper(self._process.stderr,
encoding='utf8')
self._readable_errors = True
self._opened = True
except Exception as error:
print('error:', error)
raise FilesError('Can not open process.')
def close(self):
if self._opened:
if self._process.stdin:
self.stdin_handler.close()
self._stdin.close()
self._opened = False
def write(self, data):
if not self._opened:
self._open_process()
self._is_read = False
self._output_cache = ''
try:
if self._writable:
self.stdin_handler.write(data)
self.stdin_handler.flush()
else:
raise FilesError('Process stdin is not writable.')
except IOError as error:
raise FilesError(str(error))
def read(self):
if not self._opened and not self._writable:
self._open_process()
if not self._readable:
raise FilesError('Process is not readable.')
try:
if not self._is_read:
if self._writable:
self.close()
if self._readable:
self._output_cache = self.stdout_handler.read()
if self._readable_errors:
self._error_cache = self.stderr_handler.read()
self._process.poll()
self._is_read = True
return self._output_cache
except KeyboardInterrupt:
self.kill()
raise
def read_error(self):
self.read()
if not self._error_cache:
try:
self._error_cache = self.stderr_handler.read()
except IOError:
self._error_cache = ''
return self._error_cache
def kill(self):
if self._opened:
self._process.kill()
def read_lines(self):
return self.read().split('\n')
def __iter__(self):
if not self._iterator:
self._iterator = iter(self.read_lines())
return self._iterator
def next(self):
return next(self.__iter__(), None)
@property
def writable(self):
return self._writable
@property
def readable(self):
return self._readable
@property
def readable_errors(self):
return self._readable_errors
def return_code(self):
self.read()
return self._process.returncode
@property
def shell_command(self):
command = ' '.join(self._command)
previous_commands = self._stdin.shell_command
if previous_commands == '':
return command
else:
return ' | '.join([previous_commands, command])
def success(self):
return self.return_code() == 0
def failed(self):
return self.return_code() != 0
class ProgramPathCache():
def __init__(self):
self._cache = {}
def __call__(self, program_name, prefix='/'):
program_base_name = path.basename(program_name)
PATH = os.environ['PATH']
PATH = PATH.split(':')
cache_key = (program_base_name, prefix)
if cache_key in self._cache:
self._cache[cache_key]
if program_name.startswith('/'):
if path.exists(join_paths(prefix, program_name)):
self._cache[cache_key] = program_name
return program_name
for program_name in (join_paths(bin_path, program_base_name)
for bin_path in PATH):
if path.exists(join_paths(prefix, program_name)):
self._cache[cache_key] = program_name
return program_name
return False
_get_program_path = ProgramPathCache()
def join_paths(*paths):
if len(paths) == 1:
return next(iter(paths))
paths_to_join = filter(lambda path: path.strip() and path != "/",
map(lambda path:
path[1:] if path.startswith('/') else path,
paths[1:]))
output_path = path.join(paths[0], *paths_to_join)
return output_path

Binary file not shown.

@ -0,0 +1,51 @@
import site
import os
class Variable:
def __init__(self):
pass
def get(self):
"""
Функция заполнения переменной
"""
pass
def set(self, value):
"""
Функция модификации переменной
"""
pass
def choice(self):
"""
Функция возвращет список доступных значений для переменной
"""
pass
def check(self, value):
"""
Функция проверки значения устанавливаемого значения
"""
class NamespaceError(Exception):
pass
class Namespace:
DefaultPath = "[default_path]"
def __init__(self, varPath=DefaultPath):
if varPath is Namespace.DefaultPath:
self.varPath = self._getMainPackage()
else:
self.varPath = varPath
self.childs = []
def _getMainPackage(self):
site_dirs = [os.path.normpath(x) for x in site.getsitepackages()]
for site_dir in site_dirs:
calculate_dir = os.path.join(site_dir, "calculate/vars")
if os.path.exists(calculate_dir):
return calculate_dir
def findVariablePackages(self, dirPath):
pass

@ -0,0 +1,4 @@
from calculate.vars.datavars import Variable
class Profile(Variable):
pass

@ -0,0 +1,164 @@
import pytest
from collections import OrderedDict
@pytest.fixture(scope='function')
def StringDictionaries():
ParamLine1 = OrderedDict({'parameter name1': 'value1'})
ParamLine2 = OrderedDict({'parameter name2': 'value2'})
ParamLine3 = OrderedDict({'parameter name3': 'value3'})
Section1 = OrderedDict({'section name1': OrderedDict(**ParamLine1,
**ParamLine2)})
Section2 = OrderedDict({'section name2': OrderedDict(**ParamLine1,
**ParamLine2)})
Section3 = OrderedDict({'section name3': OrderedDict(**ParamLine3)})
OriginalDictionary = OrderedDict(**Section1, **Section2)
TemplateDictionary = OrderedDict(**Section3)
ResultDictionary = OrderedDict(**Section1, **Section2, **Section3)
return (OriginalDictionary, TemplateDictionary, ResultDictionary)
@pytest.fixture(scope='function')
def TupleDictionaries():
ParamLine1 = OrderedDict({('', 'parameter name1'): 'value1'})
ParamLine2 = OrderedDict({('', 'parameter name2'): 'value2'})
ParamLine3 = OrderedDict({('', 'parameter name3'): 'value3'})
Section1 = OrderedDict({('', 'section name1'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section2 = OrderedDict({('', 'section name2'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section3 = OrderedDict({('', 'section name3'): OrderedDict(**ParamLine3)})
OriginalDictionary = OrderedDict(**Section1, **Section2)
TemplateDictionary = OrderedDict(**Section3)
ResultDictionary = OrderedDict(**Section1, **Section2, **Section3)
return (OriginalDictionary, TemplateDictionary, ResultDictionary)
@pytest.fixture(scope='function')
def MergeSectionDictionaries():
ParamLine1 = OrderedDict({('', 'parameter name1'): 'value1'})
ParamLine2 = OrderedDict({('', 'parameter name2'): 'value2'})
ParamLine3 = OrderedDict({('', 'parameter name3'): 'value3'})
Section1 = OrderedDict({('', 'section name1'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section2 = OrderedDict({('', 'section name2'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section2Add = OrderedDict({('', 'section name2'):
OrderedDict(**ParamLine3)})
Section2Added = OrderedDict({('', 'section name2'):
OrderedDict(**ParamLine1,
**ParamLine2,
**ParamLine3)})
OriginalDictionary = OrderedDict(**Section1, **Section2)
TemplateDictionary = OrderedDict(**Section2Add)
ResultDictionary = OrderedDict(**Section1, **Section2Added)
return (OriginalDictionary, TemplateDictionary, ResultDictionary)
@pytest.fixture(scope='function')
def ChangeParameterDictionaries():
ParamLine1 = OrderedDict({('', 'parameter name1'): 'value1'})
ParamLine2 = OrderedDict({('', 'parameter name2'): 'value2'})
ParamLine3 = OrderedDict({('', 'parameter name3'): 'value3'})
ParamLine2New = OrderedDict({('', 'parameter name2'): 'NewValue'})
ParamLine3New = OrderedDict({('', 'parameter name3'): 'OtherValue'})
Section = OrderedDict({('', 'section name1'): OrderedDict(**ParamLine1,
**ParamLine2,
**ParamLine3)})
SectionNew = OrderedDict({('', 'section name1'):
OrderedDict(**ParamLine1,
**ParamLine2New,
**ParamLine3New)})
OriginalDictionary = OrderedDict(**Section)
TemplateDictionary = OrderedDict(**SectionNew)
ResultDictionary = TemplateDictionary
return (OriginalDictionary, TemplateDictionary, ResultDictionary)
@pytest.fixture(scope='function')
def DeleteSectionDictionaries():
ParamLine1 = OrderedDict({('', 'parameter name1'): 'value1'})
ParamLine2 = OrderedDict({('', 'parameter name2'): 'value2'})
Section1 = OrderedDict({('', 'section name1'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section2 = OrderedDict({('', 'section name2'): OrderedDict(**ParamLine1,
**ParamLine2)})
SectionDel = OrderedDict({('!', 'section name2'): OrderedDict()})
OriginalDictionary = OrderedDict(**Section1, **Section2)
TemplateDictionary = OrderedDict(**SectionDel)
ResultDictionary = OrderedDict(**Section1)
return (OriginalDictionary, TemplateDictionary, ResultDictionary)
@pytest.fixture(scope='function')
def ReplaceSectionDictionaries():
ParamLine1 = OrderedDict({('', 'parameter name1'): 'value1'})
ParamLine2 = OrderedDict({('', 'parameter name2'): 'value2'})
ParamLine3 = OrderedDict({('', 'parameter name3'): 'value3'})
ParamLine4 = OrderedDict({('', 'parameter name4'): 'value4'})
Section1 = OrderedDict({('', 'section name1'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section2 = OrderedDict({('', 'section name2'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section2Replace = OrderedDict({('-', 'section name2'):
OrderedDict(**ParamLine3, **ParamLine4)})
Section2Replaced = OrderedDict({('', 'section name2'):
OrderedDict(**ParamLine3, **ParamLine4)})
OriginalDictionary = OrderedDict(**Section1, **Section2)
TemplateDictionary = OrderedDict(**Section2Replace)
ResultDictionary = OrderedDict(**Section1, **Section2Replaced)
return (OriginalDictionary, TemplateDictionary, ResultDictionary)
@pytest.fixture(scope='function')
def DeleteParameterDictionaries():
ParamLine1 = OrderedDict({('', 'parameter name1'): 'value1'})
ParamLine2 = OrderedDict({('', 'parameter name2'): 'value2'})
ParamLineDel = OrderedDict({('!', 'parameter name2'): 'value2'})
Section1 = OrderedDict({('', 'section name1'): OrderedDict(**ParamLine1,
**ParamLine2)})
Section2 = OrderedDict({('', 'section name2'): OrderedDict(**ParamLine1,
**ParamLine2)})
SectionDel = OrderedDict({('', 'section name2'):
OrderedDict(**ParamLineDel)})
SectionAfterDel = OrderedDict({('', 'section name2'):
OrderedDict(**ParamLine1)})
OriginalDictionary = OrderedDict(**Section1, **Section2)
TemplateDictionary = OrderedDict(**SectionDel)
ResultDictionary = OrderedDict(**Section1, **SectionAfterDel)
return (OriginalDictionary, TemplateDictionary, ResultDictionary)
@pytest.fixture(scope='function')
def DictionariesWithoutSections():
ParamLine1 = OrderedDict({('', 'parameter name1'): 'value1'})
ParamLine2 = OrderedDict({('', 'parameter name2'): 'value2'})
ParamLine3 = OrderedDict({('', 'parameter name3'): 'value3'})
ParamLineDel = OrderedDict({('!', 'parameter name2'): ''})
OriginalDictionary = OrderedDict(**ParamLine1, **ParamLine2)
TemplateDictionary = OrderedDict(**ParamLine3, **ParamLineDel)
ResultDictionary = OrderedDict(**ParamLine1, **ParamLine3)
return (OriginalDictionary, TemplateDictionary, ResultDictionary)

@ -0,0 +1,23 @@
# vim: fileencoding=utf-8
# pytest.ini
[pytest]
markers =
vars: marker for running tests for datavars
base: marker for running tests for base format class.
bind: marker for running tests for bind format.
compiz: marker for running tests for compiz format.
diff: marker for running test for diff format.
dovecot: marker for running tests for devecot format.
json: marker for running tests for json format.
kde: marker for running test for kde format.
kernel: marker for running test for kernel format.
ldap: marker for running test for ldap format.
openrc: marker for running test for openrc format.
patch: marker for running test fot patch format.
postfix: marker for running test for postfix format.
procmail: marker for running test for procmail format.
proftpd: marker for running tests for proftpd format.
samba: marker for running tests for samba format.
xml_xfce: marker for running tests for xml xfce format.
xml_gconf: marker for running tests for xml gconf format.
files: marker for running tests for calculate.utils.files module.

@ -0,0 +1,8 @@
from setuptools import setup, find_packages
from os.path import join, dirname
setup(
name='calculate-lib',
version='1.0',
packages=find_packages(),
)

@ -0,0 +1,83 @@
import pytest
from calculate.templates.format.base_format import BaseFormat
@pytest.mark.base
class TestJoinMethod:
def test_if_inputs_are_dictionaries_with_string_keys_without_any_action_marks__the_dictionaties_just_merged(self, StringDictionaries):
BaseObject = BaseFormat([])
Original, Template, Result = StringDictionaries
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
def test_if_inputs_are_dictionaries_with_tuple_keys_without_any_action_marks_as_their_keys__the_dictionaries_just_merged(self, TupleDictionaries):
BaseObject = BaseFormat([])
Original, Template, Result = TupleDictionaries
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
def test_if_inputs_are_dictionaries_with_same_sections_which_contain_different_parameters__a_section_from_the_template_added_to_the_same_section_of_original_dictionary(self, MergeSectionDictionaries):
BaseObject = BaseFormat([])
Original, Template, Result = MergeSectionDictionaries
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
def test_if_inputs_are_dictionaries_with_parameters_with_same_name_in_same_section__parameters_values_in_original_dictionary_changed_to_values_from_template(self, ChangeParameterDictionaries):
BaseObject = BaseFormat([])
Original, Template, Result = ChangeParameterDictionaries
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
def test_if_input_template_dictionary_has_delete_mark_for_section__section_will_be_deleted(self, DeleteSectionDictionaries):
BaseObject = BaseFormat([])
Original, Template, Result = DeleteSectionDictionaries
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
def test_if_input_template_dictionary_has_replace_mark_for_section__section_will_be_deleted(self, ReplaceSectionDictionaries):
BaseObject = BaseFormat([])
Original, Template, Result = ReplaceSectionDictionaries
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
def test_if_input_template_dictionary_has_delete_mark_for_parameter__parameter_will_be_deleted(self, DeleteParameterDictionaries):
BaseObject = BaseFormat([])
Original, Template, Result = DeleteParameterDictionaries
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
def test_if_input_dictionaries_have_no_sections_and_have_only_parameter_lines__it_will_be_processed_correctly(self, DictionariesWithoutSections):
BaseObject = BaseFormat([])
Original, Template, Result = DictionariesWithoutSections
BaseObject._join(Original, Template, join_before=False)
assert Original == Result
@pytest.mark.base
class TestLogicLinesMethod:
def test_if_input_is_text_document_the_method_returns_list_of_its_lines(self):
with open('./tests/format/testfiles/logic_lines_test.txt', 'r') as InputFile:
InputText = InputFile.read()
processingMethods = []
OutputLines = ['First string of test file.',
'Second string of test file.',
'Third string of test file.',
'Fourth string of test file.']
BaseObject = BaseFormat(processingMethods)
InputLines = BaseObject._get_list_of_logic_lines(InputText)
assert InputLines == OutputLines
def test_if_lines_in_document_divided_using_backslash_as_continuation_symbol__method_returns_list_of_full_lines(self):
with open('./tests/format/testfiles/logic_lines_test_input.txt', 'r') as InputFile:
InputText = InputFile.read()
with open('./tests/format/testfiles/logic_lines_test_output.txt', 'r') as OutputFile:
OutputText = OutputFile.read()
BaseObject = BaseFormat([])
InputLines = BaseObject._get_list_of_logic_lines(InputText)
OutputLines = BaseObject._get_list_of_logic_lines(OutputText)
assert InputLines == OutputLines

@ -0,0 +1,298 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.bind_format import BINDFormat
@pytest.mark.bind
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''directory "/var/bind";
pid-file "/run/named/named.pid";
disable-empty-zone "10.in-addr.arpa";
'''
result = OrderedDict({
('', 'directory'):
['"/var/bind"'],
('', 'pid-file'):
['"/run/named/named.pid"'],
('', 'disable-empty-zone'):
['"10.in-addr.arpa"']
})
bind_object = BINDFormat(document_text)
assert bind_object._document_dictionary == result
def test_if_input_document_contains_some_block_of_parameters__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
acl "dns_servers" {
127.0.0.1;
10.0.1.3;
10.1.0.3;
};
options {
response-policy {
zone "rpz.zone";
};
recursion yes;
};
zone "localhost" IN {
type master;
file "pri/localhost.zone";
notify no;
}
'''
acl_section = OrderedDict({('', '127.0.0.1'): [''],
('', '10.0.1.3'): [''],
('', '10.1.0.3'): ['']})
response_section = OrderedDict({('', 'zone'): ['"rpz.zone"']})
options_section = OrderedDict({('', 'response-policy'): response_section,
('', 'recursion'): ['yes']})
zone_section = OrderedDict({('', 'type'): ['master'],
('', 'file'): ['"pri/localhost.zone"'],
('', 'notify'): ['no']})
result = OrderedDict({('', 'acl', '"dns_servers"'): acl_section,
('', 'options'): options_section,
('', 'zone', '"localhost"', 'IN'): zone_section})
bind_object = BINDFormat(document_text)
assert bind_object._document_dictionary == result
def test_if_input_document_contains_some_blocks_with_similar_names__the_blocks_join_recursively(self):
document_text = '''
acl "dns_servers" {
127.0.0.1;
10.0.1.3;
10.1.0.3;
};
options {
response-policy {
mood "almost.blue";
};
todo "drink.beer"
};
acl "dns_servers" {
10.3.0.3;
10.4.0.3;
};
options {
response-policy {
zone "rpz.zone";
};
}
'''
acl_section = OrderedDict({('', '127.0.0.1'): [''],
('', '10.0.1.3'): [''],
('', '10.1.0.3'): [''],
('', '10.3.0.3'): [''],
('', '10.4.0.3'): ['']})
response_section = OrderedDict({('', 'mood'): ['"almost.blue"'],
('', 'zone'): ['"rpz.zone"']})
options_section = OrderedDict({('', 'response-policy'):
response_section,
('', 'todo'): ['"drink.beer"']})
result = OrderedDict({('', 'acl', '"dns_servers"'): acl_section,
('', 'options'): options_section})
bind_object = BINDFormat(document_text)
assert bind_object._document_dictionary == result
def test_if_input_document_contains_blocks_and_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''
!pid-file "/run/named/named.pid";
-disable-empty-zone "10.in-addr.arpa";
acl "dns_servers" {
!127.0.0.1;
10.0.1.3;
10.1.0.3;
};
-options {
!response-policy {
zone "rpz.zone";
};
!recursion yes;
}
'''
acl_section = OrderedDict({('!', '127.0.0.1'): [''],
('', '10.0.1.3'): [''],
('', '10.1.0.3'): ['']})
response_section = OrderedDict({('', 'zone'): ['"rpz.zone"']})
options_section = OrderedDict({('!', 'response-policy'):
response_section,
('!', 'recursion'): ['yes']})
result = OrderedDict({('!', 'pid-file'):
['"/run/named/named.pid"'],
('-', 'disable-empty-zone'):
['"10.in-addr.arpa"'],
('', 'acl', '"dns_servers"'): acl_section,
('-', 'options'): options_section})
bind_object = BINDFormat(document_text)
assert bind_object._document_dictionary == result
def test_if_parameters_and_blocks_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value_or_with_special_key_in_block_dictionary(self):
document_text = '''
// Comment 1
!pid-file "/run/named/named.pid";
/*
* A very big comment.
* Still here...
* The pure giant of the comment kind.
*/
-disable-empty-zone "10.in-addr.arpa";
# Comment 2
// Comment 3
acl "dns_servers" {
!127.0.0.1;
// Comment 4
10.0.1.3;
10.1.0.3;
};
-options {
!response-policy {
/*
* This comment is very important.
* And I have no idea, why this
* comment is so important.
*/
zone "rpz.zone";
};
!recursion yes;
}
'''
acl_section = OrderedDict({'#': ['# Comment 2', '// Comment 3'],
('!', '127.0.0.1'): [''],
('', '10.0.1.3'): ['// Comment 4', ''],
('', '10.1.0.3'): ['']})
response_section = OrderedDict({('', 'zone'):
['/*',
'* This comment is very important.',
'* And I have no idea, why this',
'* comment is so important.',
'*/',
'"rpz.zone"']})
options_section = OrderedDict({('!', 'response-policy'):
response_section,
('!', 'recursion'): ['yes']})
result = OrderedDict({('!', 'pid-file'):
['// Comment 1',
'"/run/named/named.pid"'],
('-', 'disable-empty-zone'):
['/*',
'* A very big comment.',
'* Still here...',
'* The pure giant of the comment kind.',
'*/',
'"10.in-addr.arpa"'],
('', 'acl', '"dns_servers"'): acl_section,
('-', 'options'): options_section})
bind_object = BINDFormat(document_text)
assert bind_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''
// Comment 1
!pid-file "/run/named/named.pid";
/*
* A very big comment.
* Still here...
* The pure giant of comment kind.
*/
-disable-empty-zone "10.in-addr.arpa";
# Comment 2
// Comment 3
acl "dns_servers" {
!127.0.0.1;
// Comment 4
10.0.1.3;
10.1.0.3;
};
-options {
!response-policy {
/*
* This comment is very important.
* And I have no idea, why this
* comment is so important.
*/
zone "rpz.zone";
};
!recursion yes;
}
'''
acl_section = OrderedDict({('!', '127.0.0.1'): [''],
('', '10.0.1.3'): [''],
('', '10.1.0.3'): ['']})
response_section = OrderedDict({('', 'zone'): ['"rpz.zone"']})
options_section = OrderedDict({('!', 'response-policy'):
response_section,
('!', 'recursion'): ['yes']})
result = OrderedDict({('!', 'pid-file'):
['"/run/named/named.pid"'],
('-', 'disable-empty-zone'):
['"10.in-addr.arpa"'],
('', 'acl', '"dns_servers"'): acl_section,
('-', 'options'): options_section})
bind_object = BINDFormat(document_text, ignore_comments=True)
assert bind_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_values_or_with_empty_block__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
!pid-file;
!acl "dns_servers" {};
options {
!response-policy {};
!recursion;
}
'''
options_section = OrderedDict({('!', 'response-policy'):
OrderedDict(),
('!', 'recursion'): ['']})
result = OrderedDict({('!', 'pid-file'):
[''],
('!', 'acl', '"dns_servers"'): OrderedDict(),
('', 'options'): options_section})
bind_object = BINDFormat(document_text)
assert bind_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/bind_original.conf', 'r') as original_file:
original_text = original_file.read()
print(original_text)
bind_original_object = BINDFormat(original_text)
with open('./tests/format/testfiles/bind_template.conf', 'r') as template_file:
template_text = template_file.read()
bind_template_object = BINDFormat(template_text,
ignore_comments=True)
bind_original_object.join_template(bind_template_object)
with open('./tests/format/testfiles/bind_result.conf', 'r') as result_file:
result_text = result_file.read()
assert bind_original_object.get_document_text() == result_text

@ -0,0 +1,218 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.compiz_format import CompizFormat
from pprint import pprint
@pytest.mark.compiz
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
[Added Associations]
application/illustrator=zzz-gimp.desktop
application/pdf=evince.desktop;
application/rtf=libreoffice-writer.desktop;
application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
'''
section = OrderedDict({('', 'application/illustrator'):
['zzz-gimp.desktop'],
('', 'application/pdf'):
['evince.desktop;'],
('', 'application/rtf'):
['libreoffice-writer.desktop;'],
('', 'application/vnd.oasis.opendocument.spreadsheet'):
['calculate-calc.desktop;']})
result = OrderedDict({('', 'Added Associations'): section})
compiz_object = CompizFormat(document_text)
assert compiz_object._document_dictionary == result
def test_if_input_document_contains_few_parameter_lines_and_some_empty_lines__the_initialized_object_contains_correct_dictionary(self):
document_text = '''
[Added Associations]
application/illustrator=zzz-gimp.desktop
application/pdf=evince.desktop;
application/rtf=libreoffice-writer.desktop;
application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
'''
section = OrderedDict({('', 'application/illustrator'):
['zzz-gimp.desktop'],
('', 'application/pdf'):
['evince.desktop;'],
('', 'application/rtf'):
['libreoffice-writer.desktop;'],
('', 'application/vnd.oasis.opendocument.spreadsheet'):
["calculate-calc.desktop;"]})
result = OrderedDict({('', 'Added Associations'): section})
compiz_object = CompizFormat(document_text)
assert compiz_object._document_dictionary == result
def test_if_input_document_contains_sections_with_different_names_but_different_parameters__the_parameters_merged_in_one_section(self):
document_text = '''
[Added Associations]
application/illustrator=zzz-gimp.desktop
application/pdf=evince.desktop;
[Added Associations]
application/rtf=libreoffice-writer.desktop;
application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
'''
section = OrderedDict({('', 'application/illustrator'):
['zzz-gimp.desktop'],
('', 'application/pdf'):
['evince.desktop;'],
('', 'application/rtf'):
['libreoffice-writer.desktop;'],
('', 'application/vnd.oasis.opendocument.spreadsheet'):
['calculate-calc.desktop;']})
result = OrderedDict({('', 'Added Associations'): section})
compiz_object = CompizFormat(document_text)
assert compiz_object._document_dictionary == result
def test_if_input_document_contains_sections_with_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''
[Added Associations]
!application/illustrator=zzz-gimp.desktop
-application/pdf=evince.desktop;
!application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
'''
section = OrderedDict({('!', 'application/illustrator'):
['zzz-gimp.desktop'],
('-', 'application/pdf'):
['evince.desktop;'],
('!', 'application/vnd.oasis.opendocument.spreadsheet'):
["calculate-calc.desktop;"]})
result = OrderedDict({('', 'Added Associations'): section})
compiz_object = CompizFormat(document_text)
assert compiz_object._document_dictionary == result
def test_if_parameter_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value(self):
document_text = '''
# Comment
[Added Associations]
# Comment1
application/illustrator=zzz-gimp.desktop
application/pdf=evince.desktop;
# Comment2
# Comment3
application/rtf=libreoffice-writer.desktop;
[Other Section]
#Comment
!application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
'''
section_1 = OrderedDict({'#': ['# Comment'],
('', 'application/illustrator'):
['# Comment1',
'zzz-gimp.desktop'],
('', 'application/pdf'):
['evince.desktop;'],
('', 'application/rtf'):
['# Comment2',
'# Comment3',
'libreoffice-writer.desktop;']})
section_2 = OrderedDict({('!', 'application/vnd.oasis.opendocument.spreadsheet'):
['#Comment',
"calculate-calc.desktop;"]})
result = OrderedDict({('', 'Added Associations'): section_1,
('', 'Other Section'): section_2})
compiz_object = CompizFormat(document_text)
assert compiz_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''
# Comment
[Added Associations]
# Comment1
application/illustrator=zzz-gimp.desktop
application/pdf=evince.desktop;
# Comment2
# Comment3
application/rtf=libreoffice-writer.desktop;
[Other Section]
#Comment
!application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
'''
section_1 = OrderedDict({('', 'application/illustrator'):
['zzz-gimp.desktop'],
('', 'application/pdf'):
['evince.desktop;'],
('', 'application/rtf'):
['libreoffice-writer.desktop;']})
section_2 = OrderedDict({('!', 'application/vnd.oasis.opendocument.spreadsheet'):
["calculate-calc.desktop;"]})
result = OrderedDict({('', 'Added Associations'): section_1,
('', 'Other Section'): section_2})
compiz_object = CompizFormat(document_text, ignore_comments=True)
assert compiz_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_assign_symbol_and_any_values_and_sections_to_delete__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
[-Added Associations]
# Comment
!application/illustrator=zzz-gimp.desktop
!application/pdf=
!application/rtf
[!Other Section]
application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
'''
section_1 = OrderedDict({('!', 'application/illustrator'):
['# Comment',
'zzz-gimp.desktop'],
('!', 'application/pdf'): [],
('!', 'application/rtf'): []})
section_2 = OrderedDict({('', 'application/vnd.oasis.opendocument.spreadsheet'):
["calculate-calc.desktop;"]})
result = OrderedDict({('-', 'Added Associations'): section_1,
('!', 'Other Section'): section_2})
compiz_object = CompizFormat(document_text)
assert compiz_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/compiz_original', 'r') as original_file:
original_text = original_file.read()
compiz_original_object = CompizFormat(original_text)
with open('./tests/format/testfiles/compiz_template', 'r') as template_file:
template_text = template_file.read()
compiz_template_object = CompizFormat(template_text,
ignore_comments=True)
compiz_original_object.join_template(compiz_template_object)
with open('./tests/format/testfiles/compiz_result', 'r') as result_file:
result_text = result_file.read()
assert compiz_original_object.get_document_text() == result_text

@ -0,0 +1,97 @@
import pytest
from calculate.templates.format.diff_format import DiffFormat
from calculate.utils.files import Process
from os import path
import os
@pytest.mark.diff
class TestExecuteMethods:
def test_if_diff_patch_used_for_patching_of_several_files__it_changes_patched_file_correctly(self):
test_result = True
root_path = path.join(os.getcwd(), 'tests/format/testfiles/')
with open(path.join(root_path, 'diff_1.patch')) as patch_file:
patch_text = patch_file.read()
diff_patch = DiffFormat(patch_text)
print('Path:', root_path)
output = diff_patch.execute_format(root_path=root_path)
if output:
print('Changed files:')
for changed_file in diff_patch._changed_files_list:
print(changed_file, ':', sep='')
with open(path.join(diff_patch._root_path, changed_file)) as patched_file:
patched_file_text = patched_file.read()
print(patched_file_text)
other_file_name = 'b' + changed_file[1:]
with open(path.join(diff_patch._root_path,
other_file_name)) as other_file:
other_file_text = other_file.read()
test_result = test_result and (other_file_text == patched_file_text)
return_patch_run = Process('patch', '-R',
'-p{}'.format(diff_patch._last_level),
cwd=root_path)
return_patch_run.write(patch_text)
output = return_patch_run.read()
if return_patch_run.success():
print('[*] Changes was returned...')
else:
print('[!] Changes was not returned...')
else:
test_result = False
assert test_result
def test_if_diff_patch_used_for_patching_of_directories__it_changes_files_in_directories_and_adds_ones(self):
test_result = True
root_path = path.join(os.getcwd(),
'tests/format/testfiles/a1')
patch_path = path.join(os.getcwd(),
'tests/format/testfiles/diff_2.patch')
with open(path.join(patch_path)) as patch_file:
patch_text = patch_file.read()
diff_patch = DiffFormat(patch_text)
print('Path:', root_path)
output = diff_patch.execute_format(root_path=root_path)
print('Output:')
print(output)
if output:
print('Changed files:')
for changed_file in diff_patch._changed_files_list:
print(changed_file, ':', sep='')
file_path = path.join(diff_patch._root_path, changed_file)
with open(file_path) as patched_file:
patched_file_text = patched_file.read()
print(patched_file_text)
other_file_path = os.path.join(path.dirname(root_path),
'b1', changed_file)
with open(other_file_path) as other_file:
other_file_text = other_file.read()
test_result = test_result and (other_file_text == patched_file_text)
if not test_result:
print('Differences:')
try:
diff_process = Process('diff', '-u',
file_path,
other_file_path)
diff_result = diff_process.read()
print(diff_result)
except Exception as error:
print('diff was not executed.')
print('Reason:', str(error))
reverse_patch_run = Process('patch', '-R',
'-p{}'.format(diff_patch._last_level),
cwd=root_path)
reverse_patch_run.write(patch_text)
output = reverse_patch_run.read()
if reverse_patch_run.success():
print('[*] Changes was returned...')
else:
print('[!] Changes was not returned...')
else:
test_result = False
assert test_result

@ -0,0 +1,255 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.dovecot_format import DovecotFormat
@pytest.mark.dovecot
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''auth_default_realm = domain.com
auth_mechanisms = plain login
!include conf.d/imap.conf
!include_try passwords.conf
auth_realms = domain.com domain2.com
'''
result = OrderedDict({('', 'auth_default_realm'):
['domain.com'],
('', 'auth_mechanisms'):
['plain login'],
('', '!include', 'conf.d/imap.conf'):
[''],
('', '!include_try', 'passwords.conf'):
[''],
('', 'auth_realms'):
['domain.com domain2.com']
})
dovecot_object = DovecotFormat(document_text)
assert dovecot_object._document_dictionary == result
def test_if_input_document_contains_some_block_of_parameters__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
section optional_name {
section_setting_key = section_setting_value
subsection optional_subname {
subkey = subvalue
}
}
local 127.0.0.2 {
key = 127.0.0.2
}
'''
subsection = OrderedDict({('', 'subkey'): ['subvalue']})
section = OrderedDict({('', 'section_setting_key'):
['section_setting_value'],
('', 'subsection', 'optional_subname'):
subsection})
local = OrderedDict({('', 'key'): ['127.0.0.2']})
result = OrderedDict({('', 'section', 'optional_name'):
section,
('', 'local', '127.0.0.2'):
local})
dovecot_object = DovecotFormat(document_text)
assert dovecot_object._document_dictionary == result
def test_if_input_document_contains_some_blocks_with_similar_names__the_blocks_join_recursively(self):
document_text = '''
section optional_name {
section_setting_key = section_setting_value
subsection optional_subname {
subkey = subvalue
}
}
local 127.0.0.2 {
key = 127.0.0.2
}
section optional_name {
subsection optional_subname {
otherkey = value
}
}
local 127.0.0.2 {
key = 127.0.0.2
subsect name {
param = no
}
}
'''
subsection = OrderedDict({('', 'subkey'): ['subvalue'],
('', 'otherkey'): ['value']})
section = OrderedDict({('', 'section_setting_key'):
['section_setting_value'],
('', 'subsection', 'optional_subname'):
subsection})
sub_sect = OrderedDict({('', 'param'): ['no']})
local = OrderedDict({('', 'key'): ['127.0.0.2'],
('', 'subsect', 'name'): sub_sect})
result = OrderedDict({('', 'section', 'optional_name'):
section,
('', 'local', '127.0.0.2'):
local})
dovecot_object = DovecotFormat(document_text)
assert dovecot_object._document_dictionary == result
def test_if_input_document_contains_blocks_and_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''
!auth_mechanisms = plain login
!!include conf.d/imap.conf
section optional_name {
!section_setting_key = section_setting_value
-subsection optional_subname {
subkey = subvalue
}
}
!local 127.0.0.2 {
key = 127.0.0.2
}
'''
subsection = OrderedDict({('', 'subkey'): ['subvalue']})
section = OrderedDict({('!', 'section_setting_key'):
['section_setting_value'],
('-', 'subsection', 'optional_subname'):
subsection})
local = OrderedDict({('', 'key'): ['127.0.0.2']})
result = OrderedDict({('!', 'auth_mechanisms'):
['plain login'],
('!', '!include', 'conf.d/imap.conf'):
[''],
('', 'section', 'optional_name'):
section,
('!', 'local', '127.0.0.2'):
local})
dovecot_object = DovecotFormat(document_text)
assert dovecot_object._document_dictionary == result
def test_if_parameters_and_blocks_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value_or_with_special_key_in_block_dictionary(self):
document_text = '''
# Comment 1
auth_mechanisms = plain login
# Comment 2
!include conf.d/imap.conf
# Comment 3
section optional_name {
section_setting_key = section_setting_value
# Comment in the block.
subsection optional_subname {
# Comment
subkey = subvalue
}
}
'''
subsection = OrderedDict({'#': ['# Comment in the block.'],
('', 'subkey'): ['# Comment', 'subvalue']})
section = OrderedDict({'#': ['# Comment 3'],
('', 'section_setting_key'):
['section_setting_value'],
('', 'subsection', 'optional_subname'):
subsection})
result = OrderedDict({('', 'auth_mechanisms'):
['# Comment 1', 'plain login'],
('', '!include', 'conf.d/imap.conf'):
['# Comment 2', ''],
('', 'section', 'optional_name'):
section})
dovecot_object = DovecotFormat(document_text)
assert dovecot_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''
# Comment 1
auth_mechanisms = plain login
# Comment 2
!include conf.d/imap.conf
# Comment 3
section optional_name {
section_setting_key = section_setting_value
# Comment in the block.
subsection optional_subname {
# Comment
subkey = subvalue
}
}
'''
subsection = OrderedDict({('', 'subkey'): ['subvalue']})
section = OrderedDict({('', 'section_setting_key'):
['section_setting_value'],
('', 'subsection', 'optional_subname'):
subsection})
result = OrderedDict({('', 'auth_mechanisms'):
['plain login'],
('', '!include', 'conf.d/imap.conf'):
[''],
('', 'section', 'optional_name'):
section})
dovecot_object = DovecotFormat(document_text, ignore_comments=True)
assert dovecot_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_values_or_with_empty_block__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
!auth_mechanisms
!auth_realms =
section optional_name {
!section_setting_key
!subsection optional_subname {
}
}
!local 127.0.0.2 {
}
'''
section = OrderedDict({('!', 'section_setting_key'): [''],
('!', 'subsection', 'optional_subname'):
OrderedDict()})
result = OrderedDict({('!', 'auth_mechanisms'):
[''],
('!', 'auth_realms'):
[''],
('', 'section', 'optional_name'):
section,
('!', 'local', '127.0.0.2'):
OrderedDict()})
dovecot_object = DovecotFormat(document_text)
assert dovecot_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/dovecot_original.conf', 'r') as original_file:
original_text = original_file.read()
dovecot_original_object = DovecotFormat(original_text)
with open('./tests/format/testfiles/dovecot_template.conf', 'r') as template_file:
template_text = template_file.read()
dovecot_template_object = DovecotFormat(template_text,
ignore_comments=True)
dovecot_original_object.join_template(dovecot_template_object)
with open('./tests/format/testfiles/dovecot_result.conf', 'r') as result_file:
result_text = result_file.read()
assert dovecot_original_object.get_document_text() == result_text

@ -0,0 +1,44 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.json_format import JSONFormat
@pytest.mark.json
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameters_and_parameter_blocks__the_initialised_object_contains_correct_dictionary(self):
documentText = '''
{
"Param1":"ParamValue1",
"Param2": 1,
"BlockParam1":{
"BlockParam1":1,
"BlockParam2":0
},
"Param3": true
}
'''
blockContent = OrderedDict({"BlockParam1": 1, "BlockParam2": 0})
result = OrderedDict({'Param1': 'ParamValue1',
'Param2': 1,
'BlockParam1': blockContent,
'Param3': True})
jsonObject = JSONFormat(documentText)
assert jsonObject._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/json_original.json', 'r') as originalFile:
originalText = originalFile.read()
jsonOriginalObject = JSONFormat(originalText)
with open('./tests/format/testfiles/json_template.json', 'r') as templateFile:
templateText = templateFile.read()
jsonTemplateObject = JSONFormat(templateText)
jsonOriginalObject.join_template(jsonTemplateObject)
with open('./tests/format/testfiles/json_result.json', 'r') as resultFile:
resultText = resultFile.read()
assert jsonOriginalObject.get_document_text() == resultText

@ -0,0 +1,222 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.kde_format import KDEFormat
@pytest.mark.kde
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''[section name][first][second]
parameter name = /home/divanov/Home
other parameter = yes'''
param_line_1 = OrderedDict({('', 'parameter name'): ['/home/divanov/Home']})
param_line_2 = OrderedDict({('', 'other parameter'): ['yes']})
result = OrderedDict({('', 'section name', 'first', 'second'):
OrderedDict(**param_line_1,
**param_line_2)})
kde_object = KDEFormat(document_text)
assert kde_object._document_dictionary == result
def test_if_input_document_contains_parameters_with_values_with_unicode_symbols__the_initialized_object_contains_correct_dictionary(self):
document_text = '''
[Desktop Entry][val]
GenericName=IRC Client
GenericName[ar]=عميل IRC
GenericName[be]=Кліент IRC
GenericName[bg]=IRC клиент
GenericName[bs]=IRC klijent
GenericName[ca]=Client d'IRC
GenericName[ca@valencia]=Client d'IRC'''
section = OrderedDict({('', 'GenericName'): ['IRC Client'],
('', 'GenericName[ar]'): ['عميل IRC'],
('', 'GenericName[be]'): ['Кліент IRC'],
('', 'GenericName[bg]'): ['IRC клиент'],
('', 'GenericName[bs]'): ['IRC klijent'],
('', 'GenericName[ca]'): ["Client d'IRC"],
('', 'GenericName[ca@valencia]'): ["Client d'IRC"]})
result = OrderedDict({('', 'Desktop Entry', 'val'): section})
kde_object = KDEFormat(document_text)
assert kde_object._document_dictionary == result
def test_if_input_document_contains_few_parameter_lines_and_some_empty_lines__the_initialized_object_contains_correct_dictionary(self):
document_text = '''
[PlasmaViews][Panel 69][Horizontal2048]
alignment=132
length=674
thickness = 56
[Desktop Entry]
Exec=konversation -qwindowtitle %c %u
'''
section1Content = OrderedDict({('', 'alignment'): ['132'],
('', 'length'): ['674'],
('', 'thickness'): ['56']})
section_2_content = OrderedDict({('', 'Exec'): ['konversation -qwindowtitle %c %u']})
result = OrderedDict({('', 'PlasmaViews', 'Panel 69', 'Horizontal2048'): section1Content,
('', 'Desktop Entry'): section_2_content})
kde_object = KDEFormat(document_text)
assert kde_object._document_dictionary == result
def test_if_input_document_contains_sections_with_different_names_but_different_parameters__the_parameters_merged_in_one_section(self):
document_text = '''
[PlasmaViews][Panel 69][Horizontal2048]
alignment=132
length=674
[PlasmaViews][Panel 69][Horizontal2048]
thickness = 56
'''
section1Content = OrderedDict({('', 'alignment'): ['132'],
('', 'length'): ['674'],
('', 'thickness'): ['56']})
result = OrderedDict({('', 'PlasmaViews', 'Panel 69', 'Horizontal2048'): section1Content})
kde_object = KDEFormat(document_text)
assert kde_object._document_dictionary == result
def test_if_input_document_contains_sections_with_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''
[PlasmaViews][Panel 69][Horizontal2048]
!alignment=132
length=674
-thickness = 56
'''
section1Content = OrderedDict({('!', 'alignment'): ['132'],
('', 'length'): ['674'],
('-', 'thickness'): ['56']})
result = OrderedDict({('', 'PlasmaViews', 'Panel 69', 'Horizontal2048'): section1Content})
kde_object = KDEFormat(document_text)
assert kde_object._document_dictionary == result
def test_if_parameter_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value(self):
document_text = '''
# Comment to section
[PlasmaViews][Panel 69][Horizontal2048]
# Comment 1
alignment=132
length=674
# Comment 2
#Comment 3
thickness = 56
[Desktop Entry]
# Comment
Exec=konversation -qwindowtitle %c %u
'''
section_1_content = OrderedDict({'#': ['# Comment to section'],
('', 'alignment'): ['# Comment 1',
'132'],
('', 'length'): ['674'],
('', 'thickness'): ['# Comment 2',
'#Comment 3',
'56']})
section_2_content = OrderedDict({('', 'Exec'): ['# Comment',
'konversation -qwindowtitle %c %u']})
result = OrderedDict({('', 'PlasmaViews', 'Panel 69', 'Horizontal2048'): section_1_content,
('', 'Desktop Entry'): section_2_content})
kde_object = KDEFormat(document_text)
assert kde_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''
# Comment to section
[PlasmaViews][Panel 69][Horizontal2048]
# Comment 1
alignment=132
length=674
# Comment 2
#Comment 3
thickness = 56
[Desktop Entry]
# Comment
Exec=konversation -qwindowtitle %c %u
'''
section_1_content = OrderedDict({('', 'alignment'): ['132'],
('', 'length'): ['674'],
('', 'thickness'): ['56']})
section_2_content = OrderedDict({('', 'Exec'): ['konversation -qwindowtitle %c %u']})
result = OrderedDict({('', 'PlasmaViews', 'Panel 69', 'Horizontal2048'): section_1_content,
('', 'Desktop Entry'): section_2_content})
kde_object = KDEFormat(document_text, ignore_comments=True)
assert kde_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_assign_symbol_and_any_values_and_sections_to_delete__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
[PlasmaViews][Panel 69][Horizontal2048]
alignment=132
!length =
!thickness
[!PlasmaViews][Panel 69]
alignment=132
panelVisibility=1
[-Desktop Entry]
Exec=konversation -qwindowtitle %c %u
'''
section_1_content = OrderedDict({('', 'alignment'): ['132'],
('!', 'length'): [],
('!', 'thickness'): []})
section_2_content = OrderedDict({('', 'alignment'): ['132'],
('', 'panelVisibility'): ['1']})
section3Content = OrderedDict({('', 'Exec'): ['konversation -qwindowtitle %c %u']})
result = OrderedDict({('', 'PlasmaViews', 'Panel 69', 'Horizontal2048'): section_1_content,
('!', 'PlasmaViews', 'Panel 69'): section_2_content,
('-', 'Desktop Entry'): section3Content})
kde_object = KDEFormat(document_text)
assert kde_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/kde_original', 'r') as original_file:
original_text = original_file.read()
kde_original_object = KDEFormat(original_text)
with open('./tests/format/testfiles/kde_template', 'r') as template_file:
template_text = template_file.read()
kde_template_object = KDEFormat(template_text,
ignore_comments=True)
kde_original_object.join_template(kde_template_object)
with open('./tests/format/testfiles/kde_result', 'r') as result_file:
result_text = result_file.read()
assert kde_original_object.get_document_text() == result_text

@ -0,0 +1,112 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.kernel_format import KernelFormat
@pytest.mark.kernel
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
CONFIG_CC_IS_GCC=y
CONFIG_GCC_VERSION=90200
'''
result = OrderedDict({('', 'CONFIG_CC_IS_GCC'): ['y'],
('', 'CONFIG_GCC_VERSION'): ['90200']})
kernel_object = KernelFormat(document_text)
assert kernel_object._document_dictionary == result
def test_if_input_document_contains_few_parameter_lines_and_some_empty_lines__the_initialized_object_contains_correct_dictionary(self):
document_text = '''
CONFIG_CLANG_VERSION=0
CONFIG_CC_HAS_ASM_GOTO=y
CONFIG_IRQ_WORK=y
'''
result = OrderedDict({('', 'CONFIG_CLANG_VERSION'): ['0'],
('', 'CONFIG_CC_HAS_ASM_GOTO'): ['y'],
('', 'CONFIG_IRQ_WORK'): ['y']})
kernel_object = KernelFormat(document_text)
assert kernel_object._document_dictionary == result
def test_if_input_document_contains_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''
-CONFIG_REISERFS_FS=y
CONFIG_CC_IS_GCC=y
!CONFIG_IRQ_WORK=y
'''
result = OrderedDict({('-', 'CONFIG_REISERFS_FS'): ['y'],
('', 'CONFIG_CC_IS_GCC'): ['y'],
('!', 'CONFIG_IRQ_WORK'): ['y']})
kernel_object = KernelFormat(document_text)
assert kernel_object._document_dictionary == result
def test_if_parameter_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value(self):
document_text = '''# Comment1
CONFIG_DEFAULT_HOSTNAME="calculate"
CONFIG_SWAP=y
# Comment2
# Comment3
CONFIG_SYSVIPC=y
CONFIG_SYSVIPC_SYSCTL=y
# Очень важный комментарий, который нужно удалить.
!CONFIG_CROSS_MEMORY_ATTACH=y
'''
result = OrderedDict({('', 'CONFIG_DEFAULT_HOSTNAME'):
['# Comment1', '"calculate"'],
('', 'CONFIG_SWAP'):
['y'],
('', 'CONFIG_SYSVIPC'):
['# Comment2', '# Comment3', 'y'],
('', 'CONFIG_SYSVIPC_SYSCTL'): ['y'],
('!', 'CONFIG_CROSS_MEMORY_ATTACH'):
['# Очень важный комментарий, который нужно удалить.','y']})
kernel_object = KernelFormat(document_text)
assert kernel_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_assign_symbol_and_any_values__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
!CONFIG_REISERFS_FS=y
!CONFIG_EXT3_FS_POSIX_ACL=
!CONFIG_EXT3_FS_SECURITY
'''
result = OrderedDict({('!', 'CONFIG_REISERFS_FS'): ['y'],
('!', 'CONFIG_EXT3_FS_POSIX_ACL'): [],
('!', 'CONFIG_EXT3_FS_SECURITY'): []})
kernel_object = KernelFormat(document_text)
assert kernel_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/kernel_original', 'r') as original_file:
original_text = original_file.read()
kernel_original_object = KernelFormat(original_text)
with open('./tests/format/testfiles/kernel_template', 'r') as template_file:
template_text = template_file.read()
kernel_template_object = KernelFormat(template_text,
ignore_comments=True)
kernel_original_object.join_template(kernel_template_object)
with open('./tests/format/testfiles/kernel_result', 'r') as result_file:
result_text = result_file.read()
assert kernel_original_object.get_document_text() == result_text

@ -0,0 +1,364 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.ldap_format import LDAPFormat
@pytest.mark.ldap
class TestParsingMethods:
def test_if_logiclines_method_takes_text_with_lines_that_starts_whit_space_symbols__it_returns_joined_lines(self):
with open('./tests/format/testfiles/ldap_logic_lines_test.txt', 'r') as input_file:
input_text = input_file.read()
output_lines = ['First string of test file.',
'Second string of test file.',
'Third string of test file.',
'Fourth string of test file.']
ldap_object = LDAPFormat('')
input_lines = ldap_object._get_list_of_logic_lines(input_text)
assert input_lines == output_lines
def test_if_input_doc_contains_some_type_sections_with_plain_directives__object_dictionary_contains_correct_dictionary_with_directives_values_and_comments(self):
document_text = '''
include /etc/openldap/schema/samba.schema
include /etc/openldap/schema/mail.schema
loglevel 0
allow bind_v2
modulepath /usr/lib/openldap/openldap
database bdb
checkpoint 1024 5
suffix "dc=calculate"
cachesize 10000
sizelimit unlimited
directory /var/lib/openldap-data
rootdn "cn=ldaproot,dc=calculate"'''
global_section = OrderedDict({'#': [],
('', 'include', '/etc/openldap/schema/samba.schema'):
[''],
('', 'include', '/etc/openldap/schema/mail.schema'):
[''],
('', 'loglevel'): ['0'],
('', 'allow'): ['bind_v2'],
('', 'modulepath'):
['/usr/lib/openldap/openldap']})
database_section = OrderedDict({('', 'checkpoint'): ['1024 5'],
('', 'suffix'): ['"dc=calculate"'],
('', 'cachesize'): ['10000'],
('', 'sizelimit'): ['unlimited'],
('', 'directory'):
['/var/lib/openldap-data'],
('', 'rootdn'):
['"cn=ldaproot,dc=calculate"']})
result = OrderedDict({('', 'global'): global_section,
('', 'database', 'bdb'): database_section})
ldap_object = LDAPFormat(document_text)
assert ldap_object._document_dictionary == result
def test_if_input_document_contains_access_to_directive__the_object_s_dictionary_contains_correct_dictionary_with_list_of_access_to_parameters_and_comments(self):
document_text = '''
database bdb
# Comment1
# Comment2
access to attrs=userPassword
by dn="cn=ldapadmin,dc=calculate" write
by dn="ou=Samba,ou=Services,dc=calculate" write
by self read
by * auth
# Comment3
access to * by * read
'''
access_1 = OrderedDict({'#': ['# Comment1', '# Comment2'],
('', '*'):
['auth'],
('', 'self'):
['read'],
('', 'dn="ou=Samba,ou=Services,dc=calculate"'):
['write'],
('', 'dn="cn=ldapadmin,dc=calculate"'):
['write']})
access_2 = OrderedDict({'#': ['# Comment3'],
('', '*'): ['read']})
database_section = OrderedDict({('', 'access to', 'attrs=userPassword'):
access_1,
('', 'access to', '*'):
access_2})
result = OrderedDict({('', 'global'): OrderedDict(),
('', 'database', 'bdb'): database_section})
ldap_object = LDAPFormat(document_text)
assert ldap_object._document_dictionary == result
def test_if_input_document_contains_syncrepl_directive__the_object_s_dictionary_contains_correct_dictionary_with_list_of_syncrepl_parameters_and_comments(self):
document_text = '''
# Comment1
# Comment2
syncrepl rid=123
provider=ldap://provider.example.com:389
type=refreshOnly
interval=01:00:00:00
searchbase="dc=example,dc=com"
'''
syncrepl_dictionary = OrderedDict({('', 'provider'):
['ldap://provider.example.com:389'],
('', 'type'):
['refreshOnly'],
('', 'interval'):
['01:00:00:00'],
('', 'searchbase'):
['"dc=example,dc=com"']})
global_section = OrderedDict({'#': ['# Comment1', '# Comment2'],
('', 'syncrepl', 'rid=123'):
syncrepl_dictionary})
result = OrderedDict({('', 'global'): global_section})
ldap_object = LDAPFormat(document_text)
assert ldap_object._document_dictionary == result
def test_if_input_document_contains_index_directives__the_object_s_dictionary_contains_correct_dictionary_with_index_elements_and_comments(self):
document_text = '''
# Comment for global
index objectClass eq
# Comment for index
index cn pres,sub,eq
index sn pres,sub,eq
index uid pres,sub,eq
database bdb
# Comment1
# Comment2
index uidNumber eq
index gidNumber eq
index default sub'''
global_section = OrderedDict({'#': ['# Comment for global'],
('', 'index', 'objectClass'): ['eq'],
('', 'index', 'cn'):
['# Comment for index', 'pres,sub,eq'],
('', 'index', 'sn'): ['pres,sub,eq'],
('', 'index', 'uid'): ['pres,sub,eq']})
database_section = OrderedDict({('', 'index', 'uidNumber'):
['# Comment1', '# Comment2', 'eq'],
('', 'index', 'gidNumber'): ['eq'],
('', 'index', 'default'): ['sub']})
result = OrderedDict({('', 'global'): global_section,
('', 'database', 'bdb'): database_section})
ldap_object = LDAPFormat(document_text)
assert ldap_object._document_dictionary == result
def test_if_input_document_contains_comments_to_type_sections__the_object_s_dictionary_collect_them(self):
document_text = '''
# Comment1
loglevel 0
allow bind_v2
modulepath /usr/lib/openldap/openldap
# Comment2
database bdb
# Comment3
checkpoint 1024 5
suffix "dc=calculate"
cachesize 10000'''
global_section = OrderedDict({'#': ['# Comment1'],
('', 'loglevel'): ['0'],
('', 'allow'): ['bind_v2'],
('', 'modulepath'):
['/usr/lib/openldap/openldap']})
database_section = OrderedDict({'#': ['# Comment2'],
('', 'checkpoint'):
['# Comment3',
'1024 5'],
('', 'suffix'): ['"dc=calculate"'],
('', 'cachesize'): ['10000']})
result = OrderedDict({('', 'global'): global_section,
('', 'database', 'bdb'): database_section})
ldap_object = LDAPFormat(document_text)
assert ldap_object._document_dictionary == result
def test_if_input_doc_contains_some_type_sections_with_plain_directives_and_action_marks__object_dictionary_contains_correct_dictionary_with_directives_values_and_comments(self):
document_text = '''
!include /etc/openldap/schema/samba.schema
-include /etc/openldap/schema/mail.schema
-backend hdb
modulepath /usr/lib/openldap/openldap
!database bdb
checkpoint 1024 5
!directory /var/lib/openldap-data
!rootdn
-allow
# Comment1
!index uidNumber eq
-index gidNumber eq
# Comment for index
!index cn
!index sn
'''
global_section = OrderedDict({'#': [],
('!', 'include', '/etc/openldap/schema/samba.schema'):
[''],
('-', 'include', '/etc/openldap/schema/mail.schema'):
['']})
backend_section = OrderedDict({('', 'modulepath'):
['/usr/lib/openldap/openldap']})
database_section = OrderedDict({('', 'checkpoint'): ['1024 5'],
('!', 'directory'):
['/var/lib/openldap-data'],
('!', 'rootdn'): [],
('!', 'index', 'uidNumber'):
['# Comment1', 'eq'],
('-', 'index', 'gidNumber'): ['eq'],
('!', 'index', 'cn'):
['# Comment for index'],
('!', 'index', 'sn'):
[]})
result = OrderedDict({('', 'global'): global_section,
('-', 'backend', 'hdb'): backend_section,
('!', 'database', 'bdb'): database_section})
ldap_object = LDAPFormat(document_text)
assert ldap_object._document_dictionary == result
def test_if_template_text_contains_some_access_to_constuctions_with_same_what_value_and_without_action_marks_for_whole_constructions__they_join_in_one_access_to_construction(self):
document_text = '''
# Unix
access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Unix,ou=Services,dc=calculate" write
# Newval
access to attrs=sambaLMPassword,sambaNTPassword
by dn="cn=newval, dc=calculate" read
# Mail
access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Mail,ou=Services,dc=calculate" read
# Jabber
access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Jabber,ou=Services,dc=calculate" read
'''
access = OrderedDict({('', 'dn="ou=Unix,ou=Services,dc=calculate"'):
['write'],
('', 'dn="cn=newval, dc=calculate"'):
['read'],
('', 'dn="ou=Mail,ou=Services,dc=calculate"'):
['read'],
('', 'dn="ou=Jabber,ou=Services,dc=calculate"'):
['read']})
global_section = OrderedDict({('', 'access to',
'attrs=sambaLMPassword,sambaNTPassword'):
access})
result = OrderedDict({('', 'global'): global_section})
ldap_object = LDAPFormat(document_text, ignore_comments=True)
assert ldap_object._document_dictionary == result
def test_if_input_document_contains_syncrepl_and_access_to_constructions_with_action_marks__object_dictionary_contains_correct_dictionary_with_action_marks(self):
document_text = '''
# Comment
!syncrepl rid=123
provider=ldap://provider.example.com:389
type=refreshOnly
interval=01:00:00:00
searchbase="dc=example,dc=com"
# Comment1
!syncrepl rid=001
database bdb
# Comment2
!access to attrs=userPassword
by dn="cn=ldapadmin,dc=calculate" write
by !dn="ou=Samba,ou=Services,dc=calculate" write
by self read
by * auth
# Comment3
!access to dn.base="cn=proxyuser,dc=calculate"
'''
access_1 = OrderedDict({'#': ['# Comment2'],
('', '*'):
['auth'],
('', 'self'):
['read'],
('!', 'dn="ou=Samba,ou=Services,dc=calculate"'):
['write'],
('', 'dn="cn=ldapadmin,dc=calculate"'):
['write']})
syncrepl_dictionary = OrderedDict({('', 'provider'):
['ldap://provider.example.com:389'],
('', 'type'):
['refreshOnly'],
('', 'interval'):
['01:00:00:00'],
('', 'searchbase'):
['"dc=example,dc=com"']})
global_section = OrderedDict({'#': ['# Comment'],
('!', 'syncrepl', 'rid=123'):
syncrepl_dictionary,
('!', 'syncrepl', 'rid=001'):
OrderedDict({'#': ['# Comment1']})})
database_section = OrderedDict({('!', 'access to', 'attrs=userPassword'):
access_1,
('!', 'access to', 'dn.base="cn=proxyuser,dc=calculate"'):
OrderedDict({'#': ['# Comment3']})})
result = OrderedDict({('', 'global'): global_section,
('', 'database', 'bdb'): database_section})
ldap_object = LDAPFormat(document_text)
assert ldap_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/ldap_original.conf', 'r') as original_file:
original_text = original_file.read()
ldap_original_object = LDAPFormat(original_text)
with open('./tests/format/testfiles/ldap_template.conf', 'r') as template_file:
template_text = template_file.read()
ldap_template_object = LDAPFormat(template_text,
ignore_comments=True)
ldap_original_object.join_template(ldap_template_object)
with open('./tests/format/testfiles/ldap_result.conf', 'r') as result_file:
result_text = result_file.read()
assert ldap_original_object.get_document_text() == result_text

@ -0,0 +1,146 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.openrc_format import OpenRCFormat
@pytest.mark.openrc
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
rc_interactive="NO"
INSTANCE="openldap${SVCNAME#slapd}"
OPTS_CONF="-f /etc/${INSTANCE}/slapd.conf"
OPTS="${OPTS_CONF} -h 'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock'"
'''
result = OrderedDict({('', 'rc_interactive'): ['"NO"'],
('', 'instance'): ['"openldap${SVCNAME#slapd}"'],
('', 'opts_conf'): ['"-f /etc/${INSTANCE}/slapd.conf"'],
('', 'opts'): ['"${OPTS_CONF} -h \'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock\'"']})
openrc_object = OpenRCFormat(document_text)
assert openrc_object._document_dictionary == result
def test_if_input_document_contains_few_parameter_lines_and_some_empty_lines__the_initialized_object_contains_correct_dictionary(self):
document_text = '''
rc_interactive="NO"
INSTANCE="openldap${SVCNAME#slapd}"
OPTS_CONF="-f /etc/${INSTANCE}/slapd.conf"
OPTS="${OPTS_CONF} -h 'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock'"
'''
result = OrderedDict({('', 'rc_interactive'): ['"NO"'],
('', 'instance'): ['"openldap${SVCNAME#slapd}"'],
('', 'opts_conf'): ['"-f /etc/${INSTANCE}/slapd.conf"'],
('', 'opts'): ['"${OPTS_CONF} -h \'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock\'"']})
openrc_object = OpenRCFormat(document_text)
assert openrc_object._document_dictionary == result
def test_if_input_document_contains_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''
!rc_interactive="NO"
-INSTANCE="openldap${SVCNAME#slapd}"
OPTS_CONF="-f /etc/${INSTANCE}/slapd.conf"
!OPTS="${OPTS_CONF} -h 'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock'"
'''
result = OrderedDict({('!', 'rc_interactive'): ['"NO"'],
('-', 'instance'): ['"openldap${SVCNAME#slapd}"'],
('', 'opts_conf'): ['"-f /etc/${INSTANCE}/slapd.conf"'],
('!', 'opts'): ['"${OPTS_CONF} -h \'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock\'"']})
openrc_object = OpenRCFormat(document_text)
assert openrc_object._document_dictionary == result
def test_if_parameter_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value(self):
document_text = '''
# If you have multiple slapd instances per #376699, this will provide a default config
rc_interactive="NO"
INSTANCE="openldap${SVCNAME#slapd}"
# Comment1
# Comment2
OPTS_CONF="-f /etc/${INSTANCE}/slapd.conf"
OPTS="${OPTS_CONF} -h 'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock'"
'''
result = OrderedDict({('', 'rc_interactive'):
['# If you have multiple slapd instances per #376699, this will provide a default config', '"NO"'],
('', 'instance'):
['"openldap${SVCNAME#slapd}"'],
('', 'opts_conf'):
['# Comment1',
'# Comment2',
'"-f /etc/${INSTANCE}/slapd.conf"'],
('', 'opts'):
['"${OPTS_CONF} -h \'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock\'"']})
openrc_object = OpenRCFormat(document_text)
assert openrc_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''
# If you have multiple slapd instances per #376699, this will provide a default config
rc_interactive="NO"
INSTANCE="openldap${SVCNAME#slapd}"
# Comment1
# Comment2
OPTS_CONF="-f /etc/${INSTANCE}/slapd.conf"
OPTS="${OPTS_CONF} -h 'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock'"
'''
result = OrderedDict({('', 'rc_interactive'):
['"NO"'],
('', 'instance'):
['"openldap${SVCNAME#slapd}"'],
('', 'opts_conf'):
['"-f /etc/${INSTANCE}/slapd.conf"'],
('', 'opts'):
['"${OPTS_CONF} -h \'ldaps:// ldap:// ldapi://%2fvar%2frun%2fopenldap%2fslapd.sock\'"']})
openrc_object = OpenRCFormat(document_text, ignore_comments=True)
assert openrc_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_assign_symbol_and_any_values__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
!rc_interactive="NO"
!INSTANCE=
!OPTS_CONF
'''
result = OrderedDict({('!', 'rc_interactive'): ['"NO"'],
('!', 'instance'): [],
('!', 'opts_conf'): []})
openrc_object = OpenRCFormat(document_text)
assert openrc_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/openrc_original', 'r') as original_file:
original_text = original_file.read()
openrc_original_object = OpenRCFormat(original_text)
with open('./tests/format/testfiles/openrc_template', 'r') as template_file:
template_text = template_file.read()
openrc_template_object = OpenRCFormat(template_text,
ignore_comments=True)
openrc_original_object.join_template(openrc_template_object)
with open('./tests/format/testfiles/openrc_result', 'r') as result_file:
result_text = result_file.read()
assert openrc_original_object.get_document_text() == result_text

@ -0,0 +1,80 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.patch_format import PatchFormat
@pytest.mark.patch
class TestParsingMethods:
def test_if_input_patch_document_contains_only_regular_expressions_without_any_regex_flags__it_correctly_patches_input_document(self):
input_text = '''
First line
Another meaningless line.
TEXT&DATA
ParameterName = Value
Another line of endless sadness.
'''
output_text = '''
First line
Another meaningless line.
TEXT_CONFIG
ParameterName = NewValue
Another line of endless sadness.
'''
patch_text = '''<reg>TEXT&amp;DATA</reg>
<text>TEXT_CONFIG</text>
<reg>ParameterName\\s*=\\s*[a-zA-Z_][a-zA-Z_0-9]*</reg>
<text>ParameterName = NewValue</text>
'''
patch = PatchFormat(patch_text)
patch_result = patch.execute_format(input_text)
assert patch_result == output_text
def test_if_input_patch_document_contains_regular_expressions_with_global_regex_flags_and_flags_as_attributes__it_correctly_patches_input_document_using_regex_flags(self):
input_text = '''
#============================== Share Definitions =============================
[homes]
comment = Home Directories
browseable = no
writable = yes
# Un-comment the following and create the netlogon directory for Domain Logons
[netlogon]
comment = Network Logon Service
path = /var/lib/samba/netlogon
guest ok = yes
writable = no
share modes = no
'''
output_text = '''
#============================== Share Definitions =============================
[homes]
comment = Home Directories
browseable = who knows
writable = yes
# Un-comment the following and create the netlogon directory for Domain Logons
[netlogon]
comment = Network Logon Service
path = /var/lib/samba/netlogon
writable = yes
share modes = no
'''
patch_text = '''
<reg dotall="1" multiline="0">(\\[netlogon\\].*)writable\\s*=\\s*[a-zA-Z_][a-zA-Z_0-9]*</reg>
<text>\\1writable = yes</text>
<reg multiline="false" dotall="True">(\\[homes\\].*)browseable\\s*=\\s*[a-zA-Z_][a-zA-Z_0-9]*</reg>
<text>\\1browseable = who knows</text>
<reg>(\\[netlogon\\].*)^\\s*guest ok\\s*=\\s*[a-zA-Z_][a-zA-Z_0-9]*\\n</reg>
<text>\\1</text>
'''
patch = PatchFormat(patch_text, multiline=True, dotall=True)
patch_result = patch.execute_format(input_text)
assert patch_result == output_text

@ -0,0 +1,124 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.postfix_format import PostfixFormat
@pytest.mark.postfix
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''parameter_name = /home/divanov/Home
other_parameter = yes'''
result = OrderedDict({('', 'parameter_name'): ['/home/divanov/Home'],
('', 'other_parameter'): ['yes']})
postfix_object = PostfixFormat(document_text)
assert postfix_object._document_dictionary == result
def test_if_input_document_contains_few_parameter_lines_and_some_empty_lines__the_initialized_object_contains_correct_dictionary(self):
document_text = '''parameter_name = /home/divanov/Home
other_parameter = yes
another_parameter = none
'''
result = OrderedDict({('', 'parameter_name'): ['/home/divanov/Home'],
('', 'other_parameter'): ['yes'],
('', 'another_parameter'): ['none']})
postfix_object = PostfixFormat(document_text)
assert postfix_object._document_dictionary == result
def test_if_input_document_contains_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''-parameter_name = /home/divanov/Home
other_parameter = yes
!another_parameter = 1'''
result = OrderedDict({('-', 'parameter_name'): ['/home/divanov/Home'],
('', 'other_parameter'): ['yes'],
('!', 'another_parameter'): ['1']})
postfix_object = PostfixFormat(document_text)
assert postfix_object._document_dictionary == result
def test_if_parameter_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value(self):
document_text = '''# Comment1
parameter_name = /home/divanov/Home
# Comment2
# Comment3
other_parameter = yes
smtp_tls_note_starttls_offer = yes
tls_random_source = dev:/dev/urandom
# Очень важный комментарий, который нужно удалить.
!another_parameter = 1'''
result = OrderedDict({('', 'parameter_name'):
['# Comment1', '/home/divanov/Home'],
('', 'other_parameter'):
['# Comment2', '# Comment3', 'yes'],
('', 'smtp_tls_note_starttls_offer'): ['yes'],
('', 'tls_random_source'): ['dev:/dev/urandom'],
('!', 'another_parameter'):
['# Очень важный комментарий, который нужно удалить.','1']})
postfix_object = PostfixFormat(document_text)
assert postfix_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''# Comment1
parameter_name = /home/divanov/Home
# Comment2
# Comment3
other_parameter = yes
smtp_tls_note_starttls_offer = yes
tls_random_source = dev:/dev/urandom
# Очень важный комментарий, который нужно удалить.
!another_parameter = 1'''
result = OrderedDict({('', 'parameter_name'):
['/home/divanov/Home'],
('', 'other_parameter'):
['yes'],
('', 'smtp_tls_note_starttls_offer'): ['yes'],
('', 'tls_random_source'): ['dev:/dev/urandom'],
('!', 'another_parameter'):
['1']})
postfix_object = PostfixFormat(document_text, ignore_comments=True)
assert postfix_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_assign_symbol_and_any_values__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''!parameter_name = /home/divanov/Home
!other_parameter =
-ignored_line
!another_parameter'''
result = OrderedDict({('!', 'parameter_name'): ['/home/divanov/Home'],
('!', 'other_parameter'): [],
('!', 'another_parameter'): []})
postfix_object = PostfixFormat(document_text)
assert postfix_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/postfix_original', 'r') as original_file:
original_text = original_file.read()
postfix_original_object = PostfixFormat(original_text)
with open('./tests/format/testfiles/postfix_template', 'r') as template_file:
template_text = template_file.read()
postfix_template_object = PostfixFormat(template_text,
ignore_comments=True)
postfix_original_object.join_template(postfix_template_object)
with open('./tests/format/testfiles/postfix_result', 'r') as result_file:
result_text = result_file.read()
assert postfix_original_object.get_document_text() == result_text

@ -0,0 +1,130 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.procmail_format import ProcmailFormat
@pytest.mark.procmail
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
net.ipv4.ip_forward = 0
parameter_name = /home/divanov/Home
other_parameter = yes'''
result = OrderedDict({('', 'net.ipv4.ip_forward'): ['0'],
('', 'parameter_name'): ['/home/divanov/Home'],
('', 'other_parameter'): ['yes']})
procmail_object = ProcmailFormat(document_text)
assert procmail_object._document_dictionary == result
def test_if_input_document_contains_few_parameter_lines_and_some_empty_lines__the_initialized_object_contains_correct_dictionary(self):
document_text = '''
net.ipv4.ip_forward = 0
parameter_name = /home/divanov/Home
other_parameter = yes'''
result = OrderedDict({('', 'net.ipv4.ip_forward'): ['0'],
('', 'parameter_name'): ['/home/divanov/Home'],
('', 'other_parameter'): ['yes']})
procmail_object = ProcmailFormat(document_text)
assert procmail_object._document_dictionary == result
def test_if_input_document_contains_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''
!net.ipv4.ip_forward = 0
local_recipient_maps = ldap:/etc/postfix/ldap-recipient.cf, ldap:/etc/postfix/ldap-recipient-gr.cf, ldap:/etc/postfix/ldap-recipient-repl.cf
parameter_name = /home/divanov/Home
-other_parameter = yes'''
result = OrderedDict({('!', 'net.ipv4.ip_forward'): ['0'],
('', 'local_recipient_maps'):
['ldap:/etc/postfix/ldap-recipient.cf, ldap:/etc/postfix/ldap-recipient-gr.cf, ldap:/etc/postfix/ldap-recipient-repl.cf'],
('', 'parameter_name'): ['/home/divanov/Home'],
('-', 'other_parameter'): ['yes']})
procmail_object = ProcmailFormat(document_text)
assert procmail_object._document_dictionary == result
def test_if_parameter_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value(self):
document_text = '''
# Comment1
net.ipv4.ip_forward = 0
# Comment2
# Comment3
parameter_name = /home/divanov/Home
# Comment
!other_parameter = yes'''
result = OrderedDict({('', 'net.ipv4.ip_forward'): ['# Comment1', '0'],
('', 'parameter_name'): ['# Comment2',
'# Comment3',
'/home/divanov/Home'],
('!', 'other_parameter'): ['# Comment',
'yes']})
procmail_object = ProcmailFormat(document_text)
assert procmail_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''
# Comment1
net.ipv4.ip_forward = 0
# Comment2
# Comment3
parameter_name = /home/divanov/Home
# Comment
!other_parameter = yes'''
result = OrderedDict({('', 'net.ipv4.ip_forward'): ['0'],
('', 'parameter_name'): ['/home/divanov/Home'],
('!', 'other_parameter'): ['yes']})
procmail_object = ProcmailFormat(document_text, ignore_comments=True)
assert procmail_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_assign_symbol_and_any_values__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
!net.ipv4.ip_forward = 0
!parameter_name =
!other_parameter'''
result = OrderedDict({('!', 'net.ipv4.ip_forward'): ['0'],
('!', 'parameter_name'): [],
('!', 'other_parameter'): []})
procmail_object = ProcmailFormat(document_text)
assert procmail_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/procmail_original', 'r') as original_file:
original_text = original_file.read()
procmail_original_object = ProcmailFormat(original_text)
with open('./tests/format/testfiles/procmail_template', 'r') as template_file:
template_text = template_file.read()
procmail_template_object = ProcmailFormat(template_text,
ignore_comments=True)
procmail_original_object.join_template(procmail_template_object)
with open('./tests/format/testfiles/procmail_result', 'r') as result_file:
result_text = result_file.read()
assert procmail_original_object.get_document_text() == result_text

@ -0,0 +1,237 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.proftpd_format import ProFTPDFormat
@pytest.mark.proftpd
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
ServerName "ProFTPD Anonymous Server"
ServerType standalone
DefaultServer on
MaxInstances 30
'''
result = OrderedDict({('', '', 'ServerName'):
['"ProFTPD Anonymous Server"'],
('', '', 'ServerType'):
['standalone'],
('', '', 'DefaultServer'):
['on'],
('', '', 'MaxInstances'):
['30']})
proftpd_object = ProFTPDFormat(document_text)
assert proftpd_object._document_dictionary == result
def test_if_input_document_contains_some_block_of_parameters__the_initialised_object_contains_correct_dictionary(self):
document_text = '''
ServerName "ProFTPD Anonymous Server"
ServerType standalone
<Anonymous ~ftp>
<Limit LOGIN>
DisplayLogin welcome.msg
DisplayFirstChdir .message
</Limit>
User bob
Group bobs
UserAlias anonymous ftp
<Limit WRITE>
Order allow,deny
Allow from 10.0.0
Deny from all
</Limit>
</Anonymous>
'''
result = OrderedDict({('', '', 'ServerName'):
['"ProFTPD Anonymous Server"'],
('', '', 'ServerType'):
['standalone'],
('', (('Anonymous', '~ftp'), ('Limit', 'LOGIN')),
'DisplayLogin'): ['welcome.msg'],
('', (('Anonymous', '~ftp'), ('Limit', 'LOGIN')),
'DisplayFirstChdir'): ['.message'],
('', (('Anonymous', '~ftp'), ),
'User'): ['bob'],
('', (('Anonymous', '~ftp'), ),
'Group'): ['bobs'],
('', (('Anonymous', '~ftp'), ),
'UserAlias', 'anonymous', 'ftp'): [''],
('', (('Anonymous', '~ftp'), ('Limit', 'WRITE')),
'Order'): ['allow,deny'],
('', (('Anonymous', '~ftp'), ('Limit', 'WRITE')),
'Allow from', '10.0.0'): [''],
('', (('Anonymous', '~ftp'), ('Limit', 'WRITE')),
'Deny from', 'all'): ['']})
proftpd_object = ProFTPDFormat(document_text)
assert proftpd_object._document_dictionary == result
def test_if_input_document_contains_blocks_and_parameters_with_action_marks__the_key_tuples_of_parameters_s_have_it_as_its_first_element_inherited(self):
document_text = '''
!ServerName "ProFTPD Anonymous Server"
<!Anonymous ~ftp>
<-Limit LOGIN>
DisplayLogin welcome.msg
DisplayFirstChdir .message
</Limit>
</Anonymous>
<!Limit WRITE>
Order allow,deny
Allow from 10.0.0
-Deny from all
</Limit>
'''
result = OrderedDict({('!', '', 'ServerName'):
['"ProFTPD Anonymous Server"'],
('!', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayLogin'): ['welcome.msg'],
('!', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayFirstChdir'): ['.message'],
('!', (('Limit', 'WRITE'), ),
'Order'): ['allow,deny'],
('!', (('Limit', 'WRITE'), ),
'Allow from', '10.0.0'): [''],
('!', (('Limit', 'WRITE'), ),
'Deny from', 'all'): ['']})
proftpd_object = ProFTPDFormat(document_text)
assert proftpd_object._document_dictionary == result
def test_if_parameters_and_blocks_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value_or_with_special_key_in_block_dictionary(self):
document_text = '''
# Comment 1
!ServerName "ProFTPD Anonymous Server"
# Comment 2
# Comment 3
<!Anonymous ~ftp>
<-Limit LOGIN>
DisplayLogin welcome.msg
DisplayFirstChdir .message
</Limit>
</Anonymous>
<!Limit WRITE>
Order allow,deny
Allow from 10.0.0
# Comment 4
-Deny from all
</Limit>
'''
result = OrderedDict({('!', '', 'ServerName'):
['# Comment 1', '"ProFTPD Anonymous Server"'],
('!', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayLogin'): ['# Comment 2',
'# Comment 3',
'welcome.msg'],
('!', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayFirstChdir'): ['.message'],
('!', (('Limit', 'WRITE'), ),
'Order'): ['allow,deny'],
('!', (('Limit', 'WRITE'), ),
'Allow from', '10.0.0'): [''],
('!', (('Limit', 'WRITE'), ),
'Deny from', 'all'): ['# Comment 4', '']})
proftpd_object = ProFTPDFormat(document_text)
assert proftpd_object._document_dictionary == result
def test_if_the_ignoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''
# Comment 1
ServerName "ProFTPD Anonymous Server"
# Comment 2
# Comment 3
<!Anonymous ~ftp>
<-Limit LOGIN>
DisplayLogin welcome.msg
DisplayFirstChdir .message
</Limit>
</Anonymous>
<Limit WRITE>
Order allow,deny
Allow from 10.0.0
# Comment 4
!Deny from all
</Limit>
'''
result = OrderedDict({('', '', 'ServerName'):
['"ProFTPD Anonymous Server"'],
('!', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayLogin'): ['welcome.msg'],
('!', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayFirstChdir'): ['.message'],
('', (('Limit', 'WRITE'), ),
'Order'): ['allow,deny'],
('', (('Limit', 'WRITE'), ),
'Allow from', '10.0.0'): [''],
('!', (('Limit', 'WRITE'), ),
'Deny from', 'all'): ['']})
proftpd_object = ProFTPDFormat(document_text, ignore_comments=True)
assert proftpd_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_any_values_the_document_object_contains_dictionary_with_this_items_to_delete(self):
document_text = '''
!SQLLog PASS
<Anonymous ~ftp>
<Limit LOGIN>
!DisplayLogin
DisplayFirstChdir .message
</Limit>
</Anonymous>
<Limit WRITE>
!Allow from 10.0.0
</Limit>
'''
result = OrderedDict({('!', '', 'SQLLog', 'PASS'): [''],
('!', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayLogin'): [''],
('', (('Anonymous', '~ftp'),
('Limit', 'LOGIN')),
'DisplayFirstChdir'): ['.message'],
('!', (('Limit', 'WRITE'), ),
'Allow from', '10.0.0'): ['']})
proftpd_object = ProFTPDFormat(document_text, ignore_comments=True)
assert proftpd_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/proftpd_original.conf', 'r') as original_file:
original_text = original_file.read()
proftpd_original_object = ProFTPDFormat(original_text)
with open('./tests/format/testfiles/proftpd_template.conf', 'r') as template_file:
template_text = template_file.read()
proftpd_template_object = ProFTPDFormat(template_text,
ignore_comments=True)
proftpd_original_object.join_template(proftpd_template_object)
with open('./tests/format/testfiles/proftpd_result.conf', 'r') as result_file:
result_text = result_file.read()
assert proftpd_original_object.get_document_text() == result_text

@ -0,0 +1,229 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.samba_format import SambaFormat
@pytest.mark.samba
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''[section name]
parameter name = /home/divanov/Home
other parameter = yes'''
param_line_1 = OrderedDict({('', 'parameter name'): ['/home/divanov/Home']})
param_line_2 = OrderedDict({('', 'other parameter'): ['yes']})
result = OrderedDict({('', 'section name'): OrderedDict(**param_line_1,
**param_line_2)})
samba_object = SambaFormat(document_text)
assert samba_object._document_dictionary == result
def test_if_input_document_contains_few_parameter_lines_and_some_empty_lines__the_initialized_object_contains_correct_dictionary(self):
document_text = '''
[section name1]
parameter name = /home/divanov/Home
other parameter = yes
second parameter = 1
[section name2]
other parameter = yes
'''
section_1_content = OrderedDict({('', 'parameter name'): ['/home/divanov/Home'],
('', 'other parameter'): ['yes'],
('', 'second parameter'): ['1']})
section_2_content = OrderedDict({('', 'other parameter'): ['yes']})
result = OrderedDict({('', 'section name1'): section_1_content,
('', 'section name2'): section_2_content})
samba_object = SambaFormat(document_text)
assert samba_object._document_dictionary == result
def test_if_input_document_contains_sections_with_similar_names_but_different_parameters__the_parameters_merged_in_one_section(self):
document_text = '''[section name]
parameter name = /home/divanov/Home
other parameter = yes
[section name]
another parameter = 1'''
section_content = OrderedDict({('', 'parameter name'): ['/home/divanov/Home'],
('', 'other parameter'): ['yes'],
('', 'another parameter'): ['1']})
result = OrderedDict({('', 'section name'): section_content})
samba_object = SambaFormat(document_text)
assert samba_object._document_dictionary == result
def test_if_input_document_contains_sections_with_parameters_with_action_marks__the_key_tuples_of_object_s_dictionary_have_it_as_its_first_element(self):
document_text = '''[section name]
-parameter name = /home/divanov/Home
other parameter = yes
!another parameter = 1'''
section_content = OrderedDict({('-', 'parameter name'): ['/home/divanov/Home'],
('', 'other parameter'): ['yes'],
('!', 'another parameter'): ['1']})
result = OrderedDict({('', 'section name'): section_content})
samba_object = SambaFormat(document_text)
assert samba_object._document_dictionary == result
def test_if_parameter_in_input_document_has_some_comments__the_comments_will_be_collected_in_the_list_of_parameter_value(self):
document_text = '''# Comment1
[section name1]
parameter name = /home/divanov/Home
# Comment2
# Comment3
other parameter = yes
[section name2]
#Comment
!another parameter = 1'''
section = OrderedDict({'#': ['# Comment1'],
('', 'parameter name'): ['/home/divanov/Home'],
('', 'other parameter'): ['# Comment2',
'# Comment3',
'yes']})
result = OrderedDict({('', 'section name1'): section,
('', 'section name2'): OrderedDict({
('!', 'another parameter'):
['#Comment', '1']})})
samba_object = SambaFormat(document_text)
assert samba_object._document_dictionary == result
def test_if_the_IgnoreComments_flag_is_set__the_parser_ignores_all_comments(self):
document_text = '''# Comment1
[section name1]
parameter name = /home/divanov/Home
# Comment2
# Comment3
other parameter = yes
[section name2]
#Comment
!another parameter = 1'''
section_1 = OrderedDict({('', 'parameter name'): ['/home/divanov/Home'],
('', 'other parameter'): ['yes']})
section_2 = OrderedDict({('!', 'another parameter'): ['1']})
result = OrderedDict({('', 'section name1'): section_1,
('', 'section name2'): section_2})
samba_object = SambaFormat(document_text, ignore_comments=True)
assert samba_object._document_dictionary == result
def test_if_input_document_contains_parameters_to_delete_without_assign_symbol_and_any_values_and_sections_to_delete__the_document_object_contains_dictionary_with_item_to_delete(self):
document_text = '''
[section name1]
!parameter name = /home/divanov/Home
!other parameter =
!another parameter
[!section name2]
parameter = no
[-section name3]
parameter = no'''
section_1 = OrderedDict({('!', 'parameter name'): ['/home/divanov/Home'],
('!', 'other parameter'): [],
('!', 'another parameter'): []})
section_2 = OrderedDict({('', 'parameter'): ['no']})
result = OrderedDict({('', 'section name1'): section_1,
('!', 'section name2'): section_2,
('-', 'section name3'): section_2})
samba_object = SambaFormat(document_text)
assert samba_object._document_dictionary == result
def test_if_joinBefore_flag_is_set__the_document_object_contains_dictionary_with_sections_added_in_the_top_of_it(self):
original_text = '''# Comment1
[section name2]
parameter name = /home/divanov/Home
# Comment2
# Comment3
other parameter = yes
[section name3]
#Comment
another parameter = 1'''
template_text = '''
[section name1]
parameter name = /homeless/poorness
one more parameter = oh no
[section name3]
# Comment
unspoken parameter = 1'''
result = OrderedDict({('', 'section name1'):
OrderedDict({('', 'parameter name'):
['/homeless/poorness'],
('', 'one more parameter'):
['oh no']}),
('', 'section name2'):
OrderedDict({'#': ['# Comment1'],
('', 'parameter name'):
['/home/divanov/Home'],
('', 'other parameter'):
['# Comment2', '# Comment3', 'yes']}),
('', 'section name3'):
OrderedDict({('', 'another parameter'):
['#Comment', '1'],
('', 'unspoken parameter'):
['1']})})
samba_original_object = SambaFormat(original_text, join_before=True)
samba_template_object = SambaFormat(template_text, ignore_comments=True)
samba_original_object.join_template(samba_template_object)
assert samba_original_object._document_dictionary == result
def test_if_input_document_parameters_contains_upper_case_symbols__it_becomes_lower_case(self):
document_text = '''[SECTION]
parameter NAME = /home/divanov/Home
Other Parameter = yes'''
param_line_1 = OrderedDict({('', 'parameter name'): ['/home/divanov/Home']})
param_line_2 = OrderedDict({('', 'other parameter'): ['yes']})
result = OrderedDict({('', 'section'): OrderedDict(**param_line_1,
**param_line_2)})
samba_object = SambaFormat(document_text)
assert samba_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/samba_original', 'r') as original_file:
original_text = original_file.read()
samba_original_object = SambaFormat(original_text)
with open('./tests/format/testfiles/samba_template', 'r') as template_file:
template_text = template_file.read()
samba_template_object = SambaFormat(template_text,
ignore_comments=True)
samba_original_object.join_template(samba_template_object)
with open('./tests/format/testfiles/samba_result', 'r') as result_file:
result_text = result_file.read()
assert samba_original_object.get_document_text() == result_text

@ -0,0 +1,89 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.xml_gconf_format import XMLGConfFormat
@pytest.mark.xml_gconf
class TestParsingMethods:
def test_if_input_document_is_simple_gconf_tree__the_format_object_contains_correct_dictionary(self):
document_text = '''<?xml version="1.0" encoding="UTF-8"?>
<gconf>
<dir name="gnome">
<dir name="ymsgr">
<entry name="needs_terminal">
<default type="string">
<stringvalue>Something I can never have.</stringvalue>
</default>
<local_schema short_desc="Run the command in a terminal">
<longdesc>True if the command used to handle this type of URL should be run in a terminal.</longdesc>
</local_schema>
</entry>
<entry name="logo_icon_name" mtime="1342486180" type="string">
<stringvalue>distributor</stringvalue>
</entry>
</dir>
</dir>
</gconf>
'''
result = OrderedDict({('', 'gconf'):
OrderedDict({('', 'dir', ('name', 'gnome')):
OrderedDict({('', 'dir', ('name', 'ymsgr')):
OrderedDict({('', 'entry', ('name', 'needs_terminal')):
OrderedDict({('', 'default', ('type', 'string')):
OrderedDict({('', 'stringvalue'): 'Something I can never have.'}),
('', 'local_schema', ('short_desc', 'Run the command in a terminal')):
OrderedDict({('', 'longdesc'): 'True if the command used to handle this type of URL should be run in a terminal.'})}),
('', 'entry', ('name', 'logo_icon_name'), ('mtime', '1342486180'), ('type', 'string')):
OrderedDict({('', 'stringvalue'): 'distributor'})})})})})
xml_gconf_object = XMLGConfFormat(document_text)
assert xml_gconf_object._document_dictionary == result
def test_if_input_document_is_simple_gconf__the_format_object_contains_correct_dictionary(self):
document_text = '''<?xml version="1.0" encoding="UTF-8"?>
<gconf>
<entry name="options" mtime="1298136657" type="list" ltype="string">
<li type="string">
<stringvalue>grp grp:lwin_toggle</stringvalue>
</li>
</entry>
<entry name="layouts" mtime="1298136657" type="list" ltype="string">
<li type="string">
<stringvalue>us</stringvalue>
</li>
<li type="string">
<stringvalue>ru</stringvalue>
</li>
</entry>
<entry name="hinting" mtime="1298136657" type="list">
<stringvalue>full</stringvalue>
</entry>
</gconf>
'''
result = OrderedDict({('', 'gconf'):
OrderedDict({('', 'entry', ('name', 'options'), ('mtime', '1298136657'), ('type', 'list'), ('ltype', 'string')): ['grp grp:lwin_toggle'],
('', 'entry', ('name', 'layouts'), ('mtime', '1298136657'), ('type', 'list'), ('ltype', 'string')):
['us', 'ru'],
('', 'entry', ('name', 'hinting'), ('mtime', '1298136657'), ('type', 'list')):
OrderedDict({('', 'stringvalue'): 'full'})})})
xml_gconf_object = XMLGConfFormat(document_text)
assert xml_gconf_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/xml_gconf_original.xml', 'r') as original_file:
original_text = original_file.read()
xml_gconf_original_object = XMLGConfFormat(original_text)
with open('./tests/format/testfiles/xml_gconf_template.xml', 'r') as template_file:
template_text = template_file.read()
xml_gconf_template_object = XMLGConfFormat(template_text)
xml_gconf_original_object.join_template(xml_gconf_template_object)
with open('./tests/format/testfiles/xml_gconf_result.xml', 'r') as result_file:
result_text = result_file.read()
assert xml_gconf_original_object.get_document_text() == result_text

@ -0,0 +1,52 @@
import pytest
from collections import OrderedDict
from calculate.templates.format.xml_xfce_format import XMLXfceFormat
@pytest.mark.xml_xfce
class TestParsingMethods:
def test_if_input_document_contains_just_few_parameter_lines__the_initialised_object_contains_correct_dictionary(self):
document_text = '''<?xml version="1.0" encoding="UTF-8"?>
<channel name="xsettings" version="1.0">
<property name="Net" type="empty">
<property name="ThemeName" type="string" value="Calculate"/>
<property name="IconThemeName" type="string" value="Calculate"/>
<property name="DoubleClickTime" type="int" value="400"/>
</property>
<property name="Xft" type="empty">
<property name="Antialias" type="int" value="1"/>
<property name="HintStyle" type="string" value="hintmedium"/>
</property>
</channel>
'''
net_dict = OrderedDict({('', 'property', 'ThemeName', 'string'): "Calculate",
('', 'property', 'IconThemeName', 'string'): "Calculate",
('', 'property', 'DoubleClickTime', 'int'): '400'})
xft_dict = OrderedDict({('', 'property', 'Antialias', 'int'): "1",
('', 'property', 'HintStyle', 'string'): 'hintmedium'})
channel_content = OrderedDict({('', 'property', 'Net', 'empty'): net_dict,
('', 'property', 'Xft', 'empty'): xft_dict})
result = OrderedDict({('', 'channel', 'xsettings', '1.0'): channel_content})
xml_xfce_object = XMLXfceFormat(document_text)
assert xml_xfce_object._document_dictionary == result
def test_joining_documents_1(self):
with open('./tests/format/testfiles/xml_xfce_original.xml', 'r') as original_file:
original_text = original_file.read()
xml_xfce_original_object = XMLXfceFormat(original_text)
with open('./tests/format/testfiles/xml_xfce_template.xml', 'r') as template_file:
template_text = template_file.read()
xml_xfce_template_object = XMLXfceFormat(template_text)
xml_xfce_original_object.join_template(xml_xfce_template_object)
with open('./tests/format/testfiles/xml_xfce_result.xml', 'r') as result_file:
result_text = result_file.read()
assert xml_xfce_original_object.get_document_text() == result_text

@ -0,0 +1,10 @@
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
#
# General setup
#
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y

@ -0,0 +1,10 @@
Nine Inch Nails -- Hurt
I hurt myself today
To see if I still feel
I focused on the pain
The only thing that real
A needle tears a hole
The old familiar sting
Try to kill it all away
But I remember everything.

@ -0,0 +1,10 @@
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
#
# General setup
#
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y

@ -0,0 +1,17 @@
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
CONFIG_THREAD_INFO_IN_TASK=y
#
# General setup
#
CONFIG_INIT_ENV_ARG_LIMIT=16
# CONFIG_COMPILE_TEST is not set
CONFIG_LOCALVERSION=""
# CONFIG_LOCALVERSION_AUTO is not set
CONFIG_BUILD_SALT=""
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
CONFIG_HAVE_KERNEL_LZMA=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y

@ -0,0 +1,16 @@
Nine Inch Nails -- Hurt
I hurt myself today
To see if I still feel
I focused on the pain
The only thing that real
A needle tears a hole
The old familiar sting
Try to kill it all away
But I remember everything.
What have I become
My sweetest friend
Everyone I know
Goes away
In the end

@ -0,0 +1,11 @@
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
#
# General setup
#
CONFIG_BUILD_SALT=""
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y

@ -0,0 +1,16 @@
Nine Inch Nails -- Hurt
I hurt myself today
To see if I still feel
I focused on the pain
The only thing that real
A needle tears a hole
The old familiar sting
Try to kill it all away
But I remember everything.
What have I become
My sweetest friend
Everyone I know
Goes away
In the end

@ -0,0 +1,108 @@
/*
* Refer to the named.conf(5) and named(8) man pages, and the documentation
* in /usr/share/doc/bind-* for more details.
* Online versions of the documentation can be found here:
* https://kb.isc.org/article/AA-01031
*
* If you are going to set up an authoritative server, make sure you
* understand the hairy details of how DNS works. Even with simple mistakes,
* you can break connectivity for affected parties, or cause huge amounts of
* useless Internet traffic.
*/
/*
* You might put in here some ips which are allowed to use the cache or
* recursive queries
*/
acl "trusted" {
127.0.0.0/8;
10.0.0.0/8;
192.168.1.0/24;
::1/128;
};
acl "dns_servers" {
127.0.0.1;
10.0.1.3;
10.1.0.3;
10.2.0.3;
10.4.0.3;
};
options {
directory "/var/bind";
pid-file "/run/named/named.pid";
disable-empty-zone "10.in-addr.arpa";
/* https://www.isc.org/solutions/dlv >=bind-9.7.x only */
//bindkeys-file "/etc/bind/bind.keys";
listen-on-v6 { ::1; };
listen-on { 10.0.0.0/8; 127.0.0.1; };
allow-query {
/*
* Accept queries from our "trusted" ACL. We will
* allow anyone to query our master zones below.
* This prevents us from becoming a free DNS server
* to the masses.
*/
trusted;
};
allow-query-cache {
/* Use the cache for the "trusted" ACL. */
trusted;
};
allow-recursion {
/* Only trusted addresses are allowed to use recursion. */
trusted;
};
recursion yes;
response-policy {
zone "rpz.zone";
};
};
controls {
// local host -- default key.
inet 127.0.0.1 port 953 -allow { 127.0.0.1; "rndc-users"; }
keys { "rndc-remote"; "rndc-key"; };
inet 127.0.0.1 allow { localhost; };
};
include "/etc/bind/rndc.key";
zone "." in {
type hint;
file "/var/bind/named.cache";
};
zone "localhost" IN {
type master;
file "pri/localhost.zone";
notify no;
};
zone "rpz.zone" {
type master;
file "/var/bind/pri/rpz.zone";
allow-query {trusted;};
allow-update {none;};
};
# DMZ
zone "dmz.calculate.ru" IN {
type slave;
file "/var/bind/sec/dmz.calculate.ru.zone";
masters { 10.1.0.3; };
};
zone "1.10.in-addr.arpa" IN {
type slave;
file "/var/bind/sec/dmz.calculate.ru.rev.zone";
masters { 10.1.0.3; };
};

@ -0,0 +1,131 @@
/*
* Refer to the named.conf(5) and named(8) man pages, and the documentation
* in /usr/share/doc/bind-* for more details.
* Online versions of the documentation can be found here:
* https://kb.isc.org/article/AA-01031
*
* If you are going to set up an authoritative server, make sure you
* understand the hairy details of how DNS works. Even with simple mistakes,
* you can break connectivity for affected parties, or cause huge amounts of
* useless Internet traffic.
*/
/*
* You might put in here some ips which are allowed to use the cache or
* recursive queries
*/
acl "trusted" {
127.0.0.0/8;
10.0.0.0/8;
192.168.1.0/24;
::1/128;
};
acl "dns_servers" {
127.0.0.1;
10.0.1.3;
10.1.0.3;
10.2.0.3;
10.3.0.3;
};
options {
directory "/var/bind";
pid-file "/run/named/named.pid";
disable-empty-zone "10.in-addr.arpa";
/* https://www.isc.org/solutions/dlv >=bind-9.7.x only */
//bindkeys-file "/etc/bind/bind.keys";
listen-on-v6 {
::1;
};
listen-on {
10.0.0.0/8;
127.0.0.1;
};
allow-query {
/*
* Accept queries from our "trusted" ACL. We will
* allow anyone to query our master zones below.
* This prevents us from becoming a free DNS server
* to the masses.
*/
trusted;
};
recursion yes;
response-policy {
zone "bad.zone";
mood "almost.blue";
};
};
controls {
// local host -- default key.
inet 127.0.0.1 port 953 allow { 127.0.0.1; "rndc-users"; } keys { "rndc-remote"; "rndc-key"; };
inet 127.0.0.1 allow { localhost; };
};
include "/etc/bind/rndc.key";
zone "." in {
type hint;
file "/var/bind/named.cache";
};
zone "localhost" IN {
type master;
file "pri/localhost.zone";
notify no;
};
zone "rpz.zone" {
type master;
file "/var/bind/pri/rpz.zone";
allow-query {
untrusted;
};
allow-update {
none;
};
};
# DMZ
zone "dmz.calculate.ru" IN {
type slave;
file "/var/bind/sec/spb.calculate.ru.zone";
masters {
10.1.0.3;
};
};
zone "1.10.in-addr.arpa" IN {
type slave;
file "/var/bind/sec/dmz.calculate.ru.rev.zone";
masters {
10.1.0.3;
};
};
zone "msk.calculate.ru" IN {
type slave;
file "/var/bind/sec/msk.calculate.ru.zone";
masters {
10.1.0.3;
};
};
zone "17.2.10.in-addr.arpa" IN {
type slave;
file "/var/bind/sec/phone.spb.calculate.ru.rev.zone";
masters {
10.1.0.3;
};
};

@ -0,0 +1,58 @@
/*
* Шаблок для проведения теста.
* Этот комментарий не перенесется в оригинальный файл
* после наложения шаблона.
*/
// First appearing of this block with replace action mark.
options {
-response-policy {
zone "bad.zone";
};
};
zone "msk.calculate.ru" IN {
type slave;
file "/var/bind/sec/msk.calculate.ru.zone";
masters { 10.1.0.3; };
};
zone "17.2.10.in-addr.arpa" IN {
type slave;
file "/var/bind/sec/phone.spb.calculate.ru.rev.zone";
masters { 10.1.0.3; };
};
# Second appearing of this block in purpose to add one meaningless line in.
options {
response-policy {
mood "almost.blue";
};
};
/* Replace section */
zone "dmz.calculate.ru" IN {
type slave;
file "/var/bind/sec/spb.calculate.ru.zone";
masters { 10.1.0.3; };
};
options {
-allow-recursion {};
};
zone "rpz.zone" {
-allow-query {
untrusted;
};
};
acl "dns_servers" {
10.3.0.3;
!10.4.0.3;
};
options {
!allow-query-cache {};
};

@ -0,0 +1,32 @@
# Compiz test config.
[Added Associations]
application/illustrator=zzz-gimp.desktop
application/pdf=evince.desktop;
application/rtf=libreoffice-writer.desktop;
application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
application/vnd.oasis.opendocument.text=libreoffice-calc.desktop;
# The Comment have to be saved.
image/bmp=gwenview.desktop;
image/gif=gwenview.desktop;
image/jpeg=gwenview.desktop;
image/jpg=gwenview.desktop;
image/png=gwenview.desktop;
# The Comment to go away.
audio/x-ms-wma=clementine.desktop;
audio/x-wav=clementine.desktop;
[Non Realistic Section]
audio/mp4=clementine.desktop;
audio/mpeg=clementine.desktop;
audio/x-flac=clementine.desktop;
audio/x-ms-wma=clementine.desktop;
audio/x-wav=clementine.desktop;
# It is very strange section -- may be It needs to be more strange.
[Strange Section]
video/mp4=smplayer.desktop;
video/mpeg=smplayer.desktop;
video/quicktime=smplayer.desktop;
video/vnd.mpegurl=smplayer.desktop;
video/x-m4v=smplayer.desktop;
video/x-sgi-movie=smplayer.desktop;

@ -0,0 +1,34 @@
# Compiz test config.
[Added Associations]
application/illustrator=zzz-gimp.desktop
application/pdf=evince.desktop;
application/rtf=libreoffice-writer.desktop;
application/vnd.oasis.opendocument.spreadsheet=calculate-calc.desktop;
application/vnd.oasis.opendocument.text=libreoffice-calc.desktop;
# The Comment have to be saved.
image/bmp=other.desktop;
image/gif=another.desktop;
image/jpeg=gwenview.desktop;
image/jpg=gwenview.desktop;
image/png=gwenview.desktop;
image/x-portable-anymap=gwenview.desktop;
image/x-portable-bitmap=gwenview.desktop;
image/x-portable-graymap=gwenview.desktop;
x-scheme-handler/http=firefox.desktop;
x-scheme-handler/https=firefox.desktop;
# It is very strange section -- may be It needs to be more strange.
[Strange Section]
video/x-sgi-movie=smplayer.desktop;
text/plain=kwrite.desktop;
x-scheme-handler/mailto=org.kde.kmail2.desktop;
video/ogg=smplayer.desktop;
audio/mp4=clementine.desktop;
[Audio]
audio/mp4=clementine.desktop;
audio/mpeg=clementine.desktop;
audio/x-flac=clementine.desktop;
audio/x-ms-wma=clementine.desktop;
audio/x-wav=clementine.desktop;

@ -0,0 +1,39 @@
[Added Associations]
image/x-portable-anymap=gwenview.desktop;
image/x-portable-bitmap=gwenview.desktop;
image/x-portable-graymap=gwenview.desktop;
[Added Associations]
image/bmp=other.desktop;
image/gif=another.desktop;
# Let's remove non realistic section.
[!Non Realistic Section]
[Added Associations]
x-scheme-handler/http=firefox.desktop;
x-scheme-handler/https=firefox.desktop;
# New section for audio
[Audio]
audio/mp4=clementine.desktop;
audio/mpeg=clementine.desktop;
audio/x-flac=clementine.desktop;
audio/x-ms-wma=clementine.desktop;
audio/x-wav=clementine.desktop;
[Added Associations]
!audio/mp4
!audio/mpeg
!audio/x-flac=
!audio/x-ms-wma=
!audio/x-wav
# To make strange section more strange.
[-Strange Section]
video/x-sgi-movie=smplayer.desktop;
text/plain=kwrite.desktop;
x-scheme-handler/mailto=org.kde.kmail2.desktop;
video/ogg=smplayer.desktop;
audio/mp4=clementine.desktop;

@ -0,0 +1,34 @@
diff -urN a/dir/file1.txt b/dir/file1.txt
--- a/dir/file1.txt 2020-01-29 14:38:21.216540100 +0300
+++ b/dir/file1.txt 2020-01-29 14:40:19.200542500 +0300
@@ -1,10 +1,17 @@
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
+CONFIG_THREAD_INFO_IN_TASK=y
#
# General setup
#
+CONFIG_INIT_ENV_ARG_LIMIT=16
+# CONFIG_COMPILE_TEST is not set
+CONFIG_LOCALVERSION=""
+# CONFIG_LOCALVERSION_AUTO is not set
+CONFIG_BUILD_SALT=""
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
+CONFIG_HAVE_KERNEL_LZMA=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y
diff -urN a/dir/file2.txt b/dir/file2.txt
--- a/dir/file2.txt 2020-01-29 14:35:45.112536800 +0300
+++ b/dir/file2.txt 2020-01-29 13:47:05.475437800 +0300
@@ -8,3 +8,9 @@
The old familiar sting
Try to kill it all away
But I remember everything.
+
+What have I become
+My sweetest friend
+Everyone I know
+Goes away
+In the end

@ -0,0 +1,41 @@
diff -Naru a1/dir/file1.txt b1/dir/file1.txt
--- a1/dir/file1.txt 2020-01-29 16:12:32.179927200 +0300
+++ b1/dir/file1.txt 2020-01-29 15:54:03.080863300 +0300
@@ -1,10 +1,17 @@
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
+CONFIG_THREAD_INFO_IN_TASK=y
#
# General setup
#
+CONFIG_INIT_ENV_ARG_LIMIT=16
+# CONFIG_COMPILE_TEST is not set
+CONFIG_LOCALVERSION=""
+# CONFIG_LOCALVERSION_AUTO is not set
+CONFIG_BUILD_SALT=""
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
+CONFIG_HAVE_KERNEL_LZMA=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y
diff -Naru a1/dir/file2.txt b1/dir/file2.txt
--- a1/dir/file2.txt 1970-01-01 03:00:00.000000000 +0300
+++ b1/dir/file2.txt 2020-01-29 13:47:05.475437800 +0300
@@ -0,0 +1,16 @@
+Nine Inch Nails -- Hurt
+
+I hurt myself today
+To see if I still feel
+I focused on the pain
+The only thing that real
+A needle tears a hole
+The old familiar sting
+Try to kill it all away
+But I remember everything.
+
+What have I become
+My sweetest friend
+Everyone I know
+Goes away
+In the end

@ -0,0 +1,38 @@
# 2.2.32 (dfbe293d4): /usr/local/etc/dovecot/dovecot.conf
# Pigeonhole version 0.4.20 (7cd71ba)
# OS: FreeBSD 10.3-RELEASE-p20 amd64
auth_default_realm = domain.com
auth_mechanisms = plain login
auth_realms = domain.com domain2.com
# Log unsuccessful authentication attempts and the reasons why they failed.
auth_verbose = no
# In case of password mismatches, log the attempted password. Valid values are
# no, plain and sha1. sha1 can be useful for detecting brute force password
# attempts vs. user simply trying the same password over and over again.
auth_verbose_passwords = no
dict {
acl = mysql:/usr/local/etc/dovecot/shared-folders.conf
sqlquota = mysql:/usr/local/etc/dovecot/quota.conf
}
hostname = mail.domain.com
namespace inbox {
# These mailboxes are widely used and could perhaps be created automatically:
mailbox Drafts {
special_use = \Drafts
}
mailbox Junk {
special_use = \Junk
}
mailbox Trash {
special_use = \Trash
}
}
!include auth-passwdfile.conf.ext
!include auth-checkpassword.conf.ext

@ -0,0 +1,47 @@
# 2.2.32 (dfbe293d4): /usr/local/etc/dovecot/dovecot.conf
# Pigeonhole version 0.4.20 (7cd71ba)
# OS: FreeBSD 10.3-RELEASE-p20 amd64
auth_default_realm = domain.com
auth_realms = domain.com domain2.com
# Log unsuccessful authentication attempts and the reasons why they failed.
auth_verbose = yes
# In case of password mismatches, log the attempted password. Valid values are
# no, plain and sha1. sha1 can be useful for detecting brute force password
# attempts vs. user simply trying the same password over and over again.
auth_verbose_passwords = no
dict {
acl = mysql:/usr/local/etc/dovecot/shared-folders.conf
sqlquota = mysql:/etc/dovecot/quota.conf
something_strange = val:12, /something/meaningless.conf
}
hostname = mail.domain.com
namespace inbox {
# These mailboxes are widely used and could perhaps be created automatically:
mailbox Drafts {
special_use = \Something else
}
mailbox Trash {
special_use = \Disgusting Trash
useless_parameter = 13
}
mailbox Archives {
auto = subscribe
special_use = \Archive
}
}
!include auth-passwdfile.conf.ext
!include auth-importantextension.conf.ext

@ -0,0 +1,39 @@
namespace inbox {
mailbox Drafts {
special_use = \Something else
}
}
!auth_mechanisms
namespace inbox {
mailbox Archives {
auto = subscribe
special_use = \Archive
}
}
!!include auth-checkpassword.conf.ext
!include auth-importantextension.conf.ext
namespace inbox {
!mailbox Junk {
}
-mailbox Trash {
special_use = \Disgusting Trash
useless_parameter = 13
}
}
# The comment that have to be ignored.
auth_verbose = yes
dict {
sqlquota = mysql:/etc/dovecot/quota.conf
something_strange = val:12, /something/meaningless.conf
}

@ -0,0 +1,21 @@
{
"Param1":"ParamValue1",
"Param2":"ParamValue2",
"ParamList":["Param1", "Param2", "Param3"],
"Param3": 1,
"Param4": 0,
"BlockParam1":{
"BlockParam1":1,
"BlockParam2":0
},
"BlockParam2":{
"BlockParam1":1,
"BlockParam2":"Special value"
},
"BlockParam3":{
"BlockParam1": false,
"BlockParam2": 0,
"BlockParam3": "Special value"
},
"Param5": true
}

@ -0,0 +1,25 @@
{
"Param1": "NewParamValue1",
"Param2": "ParamValue2",
"ParamList": [
"Param1",
"Param2",
"Param3"
],
"Param3": 1,
"Param4": 0,
"BlockParam1": {
"BlockParam3": true,
"BlockParam4": [
"Param4",
"Param5",
"Param6"
]
},
"BlockParam2": {
"BlockParam1": 0,
"BlockParam2": "Special value",
"BlockParam3": true
},
"Param6": 37
}

@ -0,0 +1,14 @@
{
"Param1":"NewParamValue1",
"-BlockParam1":{
"BlockParam3":true,
"BlockParam4":["Param4", "Param5", "Param6"]
},
"BlockParam2":{
"BlockParam1" : 0,
"BlockParam3" : true
},
"!BlockParam3":{},
"!Param5" : false,
"Param6" : 37
}

@ -0,0 +1,63 @@
# KDE or Plasma config file.
# Part from Plasma
[PlasmaViews][Panel 69][Horizontal1024]
alignment=132
length=674
maxLength=674
minLength=674
panelVisibility=1
thickness=56
[PlasmaViews][Panel 69][Horizontal1152]
# Comment have to be saved.
alignment=132
length=674
maxLength=674
minLength=674
panelVisibility=1
thickness=56
[FileDialogSize]
Height 1080=466
Width 1920=747
[KFileDialog Settings]
Recent Files[$e]=start-here-blue.svg,/usr/share/pixmaps/calculate/start-here-blue.svg
Recent URLs[$e]=/usr/share/pixmaps/calculate/
# Very important comment -- need to be saved.
[KPropertiesDialog]
Height 1080=453
Width 1920=512
[PlasmaRunnerManager]
LaunchCounts=None
pluginWhiteList=services,shell,bookmarks,baloosearch,locations
[PlasmaViews][Panel 69]
alignment=132
panelVisibility=1
# Part from KDE
[Desktop Entry]
Type=Application
Exec=konversation -qwindowtitle %c %u
Icon=/usr/share/icons/hicolor/64x64/apps/konversation.png
X-DocPath=konversation/index.html
GenericName=IRC Client
GenericName[ar]=عميل IRC
GenericName[ast]=Veceru IRC
GenericName[be]=Кліент IRC
GenericName[bg]=IRC клиент
GenericName[bs]=IRC klijent
GenericName[ca]=Client d'IRC
GenericName[ca@valencia]=Client d'IRC
GenericName[cs]=IRC klient
GenericName[da]=IRC-klient
GenericName[de]=IRC-Programm
Categories=Qt;KDE;Network;IRCClient;
X-KDE-ServiceTypes=DBUS/InstantMessenger
X-DBUS-StartupType=Unique
X-DBUS-ServiceName=org.kde.konversation
StartupNotify=true
NoDisplay=true

@ -0,0 +1,75 @@
# KDE or Plasma config file.
# Part from Plasma
[PlasmaViews][Panel 69][Horizontal1024]
alignment=132
length=674
maxLength=674
minLength=674
panelVisibility=1
thickness=56
[PlasmaViews][Panel 69][Horizontal1152]
# Comment have to be saved.
alignment=666
maxLength=674
minLength=674
panelVisibility=0
thickness=56
[FileDialogSize]
Height 1080=466
Width 1920=747
[KFileDialog Settings]
Recent Files[$e]=start-here-blue.svg,/usr/share/pixmaps/calculate/start-here-blue.svg
Recent URLs[$e]=/usr/share/pixmaps/calculate/
# Very important comment -- need to be saved.
[KPropertiesDialog]
Width 1920=486
Height 1080=123
[PlasmaRunnerManager]
LaunchCounts=None
pluginWhiteList=services,shell,bookmarks,baloosearch,locations
# Part from KDE
[Desktop Entry]
Type=Application
Exec=konversation -qwindowtitle %c %u
Icon=/usr/share/icons/hicolor/64x64/apps/konversation.png
X-DocPath=konversation/index.html
GenericName=IRC Client
GenericName[ast]=Veceru IRC
GenericName[be]=Кліент IRC
GenericName[bg]=IRC клиент
GenericName[bs]=IRC klijent
GenericName[ca]=Client d'IRC
GenericName[ca@valencia]=Client d'IRC
GenericName[cs]=IRC klient
GenericName[da]=IRC-klient
GenericName[de]=IRC-Programm
Categories=Qt;KDE;Network;IRCClient;
X-KDE-ServiceTypes=DBUS/InstantMessenger
X-DBUS-StartupType=Unique
X-DBUS-ServiceName=org.kde.konversation
StartupNotify=true
NoDisplay=true
GenericName[el]=Πελάτης IRC
GenericName[en_GB]=IRC Client
GenericName[es]=Cliente de IRC
GenericName[et]=IRC klient
GenericName[eu]=IRC bezeroa
GenericName[fi]=IRC-keskustelu
GenericName[fr]=Client IRC
GenericName[ga]=Cliant IRC
GenericName[gl]=Cliente de IRC
GenericName[he]=לקוח IRC
[PlasmaViews][Panel 69][Horizontal1200]
alignment=132
length=674
maxLength=674
minLength=674
thickness=56

@ -0,0 +1,40 @@
# New comment for test.
[PlasmaViews][Panel 69][Horizontal1152]
alignment=666
!length=674
panelVisibility=0
# thickness=
[Desktop Entry]
GenericName[de]=IRC-Programm
GenericName[el]=Πελάτης IRC
GenericName[en_GB]=IRC Client
GenericName[es]=Cliente de IRC
GenericName[et]=IRC klient
# New section
[PlasmaViews][Panel 69][Horizontal1200]
alignment=132
length=674
maxLength=674
minLength=674
!panelVisibility=1
thickness=56
[!PlasmaViews][Panel 69]
[-KPropertiesDialog]
Width 1920=486
Height 1080=123
# Thickness
[Desktop Entry]
GenericName[eu]=IRC bezeroa
GenericName[fi]=IRC-keskustelu
GenericName[fr]=Client IRC
GenericName[ga]=Cliant IRC
GenericName[gl]=Cliente de IRC
GenericName[he]=לקוח IRC
!GenericName[ar]

@ -0,0 +1,39 @@
#
# Automatically generated file; DO NOT EDIT.
# Linux/x86 4.19.85-calculate Kernel Configuration
#
#
# Compiler: gcc (Gentoo 9.2.0-r2 p3) 9.2.0
#
CONFIG_CC_IS_GCC=y
CONFIG_GCC_VERSION=90200
CONFIG_CLANG_VERSION=0
CONFIG_CC_HAS_ASM_GOTO=y
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
CONFIG_THREAD_INFO_IN_TASK=y
#Comment, that can not exist.
CONFIG_EXT3_FS_POSIX_ACL=y
CONFIG_EXT3_FS_SECURITY=n
CONFIG_EXT3_FS_XATTR=m
#
# General setup
#
CONFIG_INIT_ENV_ARG_LIMIT=32
# CONFIG_COMPILE_TEST is not set
CONFIG_LOCALVERSION=""
# CONFIG_LOCALVERSION_AUTO is not set
CONFIG_BUILD_SALT=""
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
CONFIG_HAVE_KERNEL_LZMA=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y
# CONFIG_KERNEL_GZIP is not set
# CONFIG_KERNEL_BZIP2 is not set
# CONFIG_KERNEL_LZMA is not set
CONFIG_KERNEL_XZ=y

@ -0,0 +1,34 @@
#
# Automatically generated file; DO NOT EDIT.
# Linux/x86 4.19.85-calculate Kernel Configuration
#
#
# Compiler: gcc (Gentoo 9.2.0-r2 p3) 9.2.0
#
CONFIG_CC_IS_GCC=y
CONFIG_GCC_VERSION=90200
CONFIG_CLANG_VERSION=0
CONFIG_CC_HAS_ASM_GOTO=y
CONFIG_IRQ_WORK=y
CONFIG_BUILDTIME_EXTABLE_SORT=y
CONFIG_THREAD_INFO_IN_TASK=y
#
# General setup
#
CONFIG_INIT_ENV_ARG_LIMIT=16
# CONFIG_COMPILE_TEST is not set
CONFIG_LOCALVERSION=""
# CONFIG_LOCALVERSION_AUTO is not set
CONFIG_BUILD_SALT=""
CONFIG_HAVE_KERNEL_GZIP=y
CONFIG_HAVE_KERNEL_BZIP2=y
CONFIG_HAVE_KERNEL_LZMA=y
CONFIG_HAVE_KERNEL_XZ=y
CONFIG_HAVE_KERNEL_LZO=y
CONFIG_HAVE_KERNEL_LZ4=y
# CONFIG_KERNEL_GZIP is not set
# CONFIG_KERNEL_BZIP2 is not set
# CONFIG_KERNEL_LZMA is not set
CONFIG_KERNEL_XZ=y
CONFIG_XFS_FS=m
CONFIG_REISERFS_FS=y

@ -0,0 +1,10 @@
# Calculate format=kernel -- this comment will be not saved.
CONFIG_XFS_FS=m
CONFIG_REISERFS_FS=y
# CONFIG_EXT3_FS is not set
!CONFIG_EXT3_FS_POSIX_ACL=
!CONFIG_EXT3_FS_SECURITY=
!CONFIG_EXT3_FS_XATTR
CONFIG_INIT_ENV_ARG_LIMIT=16

@ -0,0 +1,9 @@
First string
of test file.
Second
string of
test file.
Third string of test file.
Fourth string
of test file.

@ -0,0 +1,71 @@
#------------------------------------------------------------------------------
# Modified Calculate-server 2.1.16
# File of a profile "profile/samba"
#------------------------------------------------------------------------------
include /etc/openldap/schema/core.schema
include /etc/openldap/schema/cosine.schema
include /etc/openldap/schema/nis.schema
include /etc/openldap/schema/inetorgperson.schema
pidfile /var/run/openldap/slapd.pid
argsfile /var/run/openldap/slapd.arg
loglevel 0
allow bind_v2
modulepath /usr/lib/openldap/openldap
access to attrs=userPassword
by dn="cn=ldapadmin,dc=calculate" write
by dn="ou=Samba,ou=Services,dc=calculate" write
by dn="ou=Unix,ou=Services,dc=calculate" write
by dn="ou=Mail,ou=Services,dc=calculate" read
by dn="ou=Jabber,ou=Services,dc=calculate" read
by dn="ou=Ftp,ou=Services,dc=calculate" read
by dn="ou=Replication,ou=LDAP,ou=Services,dc=calculate" write
by self read
by * auth
access to attrs=sambaLMPassword,sambaNTPassword
by dn="cn=ldapadmin,dc=calculate" write
by dn="ou=Samba,ou=Services,dc=calculate" write
by dn="ou=Replication,ou=LDAP,ou=Services,dc=calculate" write
by * none
access to dn.base="cn=proxyuser,dc=calculate"
by dn="cn=ldapadmin,dc=calculate" write
by dn="cn=proxyuser,dc=calculate" read
by * none
access to *
by dn="cn=ldapadmin,dc=calculate" write
by self write
by * read
# Backend section for test.
backend bdb
suffix "dc=calculate"
database bdb
suffix "dc=example, dc=calculate"
checkpoint 1024 5
cachesize 10000
sizelimit unlimited
directory /var/lib/openldap-data
rootdn "cn=ldaproot,dc=calculate"
#include /etc/openldap/replication.conf
index objectClass eq
index cn pres,sub,eq
index sn pres,sub,eq
index uid pres,sub,eq
index uidNumber eq
index gidNumber eq
index default sub
syncrepl rid=123
provider=ldap://provider.example.com:389
type=refreshOnly
interval=01:00:00:00
searchbase="dc=example, dc=com"
filter="(objectClass=organizationalPerson)"
scope=sub
attrs="cn, sn, ou, telephoneNumber, title, l"
schemachecking=off
bindmethod=simple
binddn="cn=syncuser, dc=example, dc=com"
credentials=secret
updateref ldap://ldapmaster.example.com

@ -0,0 +1,67 @@
#------------------------------------------------------------------------------
# Modified Calculate-server 2.1.16
# File of a profile "profile/samba"
#------------------------------------------------------------------------------
include /etc/openldap/schema/cosine.schema
include /etc/openldap/schema/nis.schema
include /etc/openldap/schema/inetorgperson.schema
include /etc/openldap/schema/otherschema.schema
pidfile /var/run/openldap/slapd.pid
argsfile /var/run/openldap/slapd.arg
loglevel 0
allow bind_v2
modulepath /usr/lib/openldap/openldap
access to attrs=userPassword
by dn="cn=newother, dc=calculate" read
by dn="cn=newval, dc=calculate" read
by dn="cn=ldapadmin,dc=calculate" write
by dn="ou=Samba,ou=Services,dc=calculate" write
by dn="ou=Unix,ou=Services,dc=calculate" write
by dn="ou=Mail,ou=Services,dc=calculate" read
by dn="ou=Jabber,ou=Services,dc=calculate" read
by dn="ou=Replication,ou=LDAP,ou=Services,dc=calculate" read
by self read
by * none
access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Jabber,ou=Services,dc=calculate" read
by dn="ou=Mail,ou=Services,dc=calculate" read
by dn="cn=newval, dc=calculate" read
by dn="ou=Unix,ou=Services,dc=calculate" write
by dn="ou=Replication,ou=LDAP,ou=Services,dc=calculate" write
by dn="ou=Samba,ou=Services,dc=calculate" write
by dn="cn=ldapadmin,dc=calculate" read
by self read
by * auth
access to * by * read
# Backend section for test.
backend bdb
suffix "dc=example"
rootdn "cn=ldaproot,dc=calculate"
modulepath /usr/lib/openldap
database bdb
include /etc/openldap/replication.conf
suffix "dc=example, dc=calculate"
checkpoint 1024 5
cachesize 10000
sizelimit unlimited
directory /var/lib/openldap-data
rootdn "cn=ldaproot,dc=calculate"
#include /etc/openldap/replication.conf
index objectClass eq
index cn pres,sub,eq
index uid pres,sub,eq
index uidNumber eq
index gidNumber eq
index default sub
syncrepl rid=001
provider=ldap://provider.newexample.com:389
type=refreshOnly
interval=01:00:00:00
searchbase="dc=example,dc=com"
updateref ldap://ldapmaster.newexample.com
modulepath /usr/lib/openldap
moduleload accesslog.la
moduleload syncprov.la

@ -0,0 +1,71 @@
# After deleting of this directive, comment from top of original file will be
saved.
!include /etc/openldap/schema/core.schema
include /etc/openldap/schema/otherschema.schema
access to attrs=userPassword
by dn="cn=newval, dc=calculate" read
by dn="cn=ldapadmin,dc=calculate" write
by dn="ou=Samba,ou=Services,dc=calculate" write
by !dn="ou=Ftp,ou=Services,dc=calculate" read
by dn="ou=Replication,ou=LDAP,ou=Services,dc=calculate" read
by * none
-access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Replication,ou=LDAP,ou=Services,dc=calculate" write
by dn="ou=Samba,ou=Services,dc=calculate" write
by dn="cn=ldapadmin,dc=calculate" read
by self read
by * auth
!access to dn.base="cn=proxyuser,dc=calculate"
access to *
by !self
by !dn="cn=ldapadmin,dc=calculate" write
access to attrs=userPassword
by dn="cn=newother, dc=calculate" read
# Unix
access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Unix,ou=Services,dc=calculate" write
# Newval
access to attrs=sambaLMPassword,sambaNTPassword
by dn="cn=newval, dc=calculate" read
# Mail
access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Mail,ou=Services,dc=calculate" read
# Jabber
access to attrs=sambaLMPassword,sambaNTPassword
by dn="ou=Jabber,ou=Services,dc=calculate" read
# Comment to backend section from template.
backend bdb
rootdn "cn=ldaproot,dc=calculate"
suffix "dc=example"
database bdb
!syncrepl rid=123
include /etc/openldap/replication.conf
!index sn
!updateref ldap://ldapmaster.example.com
syncrepl rid=001
provider=ldap://provider.newexample.com:389
type=refreshOnly
interval=01:00:00:00
searchbase="dc=example,dc=com"
updateref ldap://ldapmaster.newexample.com
modulepath /usr/lib/openldap
moduleload accesslog.la
moduleload syncprov.la
backend bdb
modulepath /usr/lib/openldap

@ -0,0 +1,5 @@
First string of test file.
Second string of test file.
Third string of test file.
Fourth string of test file.

@ -0,0 +1,41 @@
#Определяет учетную запись, которая является владельцем почтовой очереди.
myhostname = mail.spb.calculate.ru
#Определяет домен данного компьютера. По умолчанию преобразуется из myhostname
#mydomain = local.calculate.ru
#Это имя добавляется локально посланным сообщениям.
#Например: если вы посылаете сообщение от пользователя root,
#то он его получит таким: from root@mta1.domain.com.
#myorigin = $mydomain
#Эта директива указывает postfix что он должен принять почту для
#пользователя этого домена. Пожалуйста, учтите, что данная директива НЕ
#может быть использована для витруального домена или для запасного MX
#хоста. В нашем случае, мы сделаем так, чтобы принималась почта для
#пользователей следующих доменов:
mydestination = $myhostname, localhost.$mydomain, $mydomain
#Разрешенные адреса получателей указаны в параметре virtual_alias_maps. SMTP
#сервер Postfix отклоняет недопустимые адреса получателей с сообщением "User
#unknown in virtual alias table (Пользователь неизвестен в таблице #виртуальных алиасов)".
virtual_alias_maps = ldap:/etc/postfix/ldap-aliases.cf, \
ldap:/etc/postfix/ldap-aliases-gr.cf, ldap:/etc/postfix/ldap-aliases-repl.cf
# The unknown_local_recipient_reject_code specifies the SMTP server
# response code when a recipient domain matches $mydestination or
# ${proxy,inet}_interfaces, while $local_recipient_maps is non-empty
# and the recipient address or address local-part is not found.
unknown_local_recipient_reject_code = 550
#Эта директива указывает postfix какие сети он должен считать
#локальными. Другими словами, компьютеры, соединяющиеся из этих сетей
#будут иметь возможность релея почтовых сообщений. В нашем случае мы
#прописываем следующие сети 127.0.0.0 (для localhost, собственно сам
#сервер), 192.168.10.0 (для всех других компьютеров в нашей внешней сети),
#и 192.168.0.0 (для всех компьютеров во внутренней сети).
# 93.100.239.44 - Алексей Пестриков
# 109.167.151.108 - lautre.ru
mynetworks = 10.0.0.0/8, 80.246.243.18, 95.213.228.194, 94.159.1.246, \
109.167.151.108, 80.246.245.82, 80.246.248.234, 93.100.239.44

@ -0,0 +1,39 @@
#Определяет учетную запись, которая является владельцем почтовой очереди.
myhostname = mail.spb.calculate.ru
#Определяет домен данного компьютера. По умолчанию преобразуется из myhostname
#mydomain = local.calculate.ru
#Это имя добавляется локально посланным сообщениям.
#Например: если вы посылаете сообщение от пользователя root,
#то он его получит таким: from root@mta1.domain.com.
#myorigin = $mydomain
#Эта директива указывает postfix что он должен принять почту для
#пользователя этого домена. Пожалуйста, учтите, что данная директива НЕ
#может быть использована для витруального домена или для запасного MX
#хоста. В нашем случае, мы сделаем так, чтобы принималась почта для
#пользователей следующих доменов:
mydestination = $myhostname, localhost.$mydomain, $mydomain
#Разрешенные адреса получателей указаны в параметре virtual_alias_maps. SMTP
#сервер Postfix отклоняет недопустимые адреса получателей с сообщением "User
#unknown in virtual alias table (Пользователь неизвестен в таблице #виртуальных алиасов)".
virtual_alias_maps = ldap:/etc/postfix/ldap-aliases.cf, ldap:/etc/postfix/ldap-aliases-gr.cf, ldap:/etc/postfix/ldap-aliases-repl.cf
# The unknown_local_recipient_reject_code specifies the SMTP server
# response code when a recipient domain matches $mydestination or
# ${proxy,inet}_interfaces, while $local_recipient_maps is non-empty
# and the recipient address or address local-part is not found.
unknown_local_recipient_reject_code = 550
#Эта директива указывает postfix какие сети он должен считать
#локальными. Другими словами, компьютеры, соединяющиеся из этих сетей
#будут иметь возможность релея почтовых сообщений. В нашем случае мы
#прописываем следующие сети 127.0.0.0 (для localhost, собственно сам
#сервер), 192.168.10.0 (для всех других компьютеров в нашей внешней сети),
#и 192.168.0.0 (для всех компьютеров во внутренней сети).
# 93.100.239.44 - Алексей Пестриков
# 109.167.151.108 - lautre.ru
mynetworks = 10.0.0.0/8, 80.246.243.18, 95.213.228.194, 94.159.1.246, 109.167.151.108, 80.246.245.82, 80.246.248.234, 93.100.239.44

@ -0,0 +1,37 @@
# It is used in the consolefont, keymaps, numlock and termencoding
# service scripts.
rc_tty_number=12
# The following setting turns on the memory.use_hierarchy setting in the
# root memory cgroup for cgroups v1.
# It must be set to yes in this file if you want this functionality.
rc_cgroup_memory_use_hierarchy="NO"
# This sets the mode used to mount cgroups.
# "hybrid" mounts cgroups version 2 on /sys/fs/cgroup/unified and
# cgroups version 1 on /sys/fs/cgroup.
# "legacy" mounts cgroups version 1 on /sys/fs/cgroup
# "unified" mounts cgroups version 2 on /sys/fs/cgroup
rc_cgroup_mode="hybrid"
# Multiple settings and values can be specified.
# For example, you would use this to set the maximum memory and maximum
# number of pids for a service.
rc_cgroup_settings="10485760"
# If you have multiple slapd instances per #376699, this will provide a default config
INSTANCE="openldap${SVCNAME#slapd}"
# If you use the classical configuration file:
OPTS_CONF="-f /etc/${INSTANCE}/slapd.conf"
# Specify the kerberos keytab file
#KRB5_KTNAME=/etc/openldap/krb5-ldap.keytab
c_need="!net net.lo"
# setting rc_send_sigkill to no.
rc_cgroup_cleanup="NO"
# If this is yes, we will send sighup to the processes in the cgroup
# immediately after stopsig and sigcont.
rc_send_sighup="YES"

@ -0,0 +1,37 @@
# It is used in the consolefont, keymaps, numlock and termencoding
# service scripts.
rc_tty_number=12
# The following setting turns on the memory.use_hierarchy setting in the
# root memory cgroup for cgroups v1.
# It must be set to yes in this file if you want this functionality.
rc_cgroup_memory_use_hierarchy="YES"
# Multiple settings and values can be specified.
# For example, you would use this to set the maximum memory and maximum
# number of pids for a service.
rc_cgroup_settings="10485760"
# If you have multiple slapd instances per #376699, this will provide a default config
instance="openldap${SVCNAME#slapd}"
# If you use the classical configuration file:
opts_conf="-f /etc/${INSTANCE}/slapd.conf"
# Specify the kerberos keytab file
#KRB5_KTNAME=/etc/openldap/krb5-ldap.keytab
c_need="!net net.lo"
# setting rc_send_sigkill to no.
rc_cgroup_cleanup="NO"
# If this is yes, we will send sighup to the processes in the cgroup
# immediately after stopsig and sigcont.
rc_send_sighup="YES"
clock="Any Clock Type"
clock_systohc="YES"
rc_timeout_stopsec="90"

@ -0,0 +1,15 @@
# It must be set to yes in this file if you want this functionality.
rc_cgroup_memory_use_hierarchy="YES"
clock="Any Clock Type"
clock_systohc="YES"
!rc_cgroup_mode
# This is the amount of time in seconds that we delay after sending sigcont
# and optionally sighup, before we optionally send sigkill to all
# processes in the # cgroup.
# The default is 90 seconds.
rc_timeout_stopsec="90"

@ -0,0 +1,34 @@
#Рабочая директория Postfix. То место, где временно сохраняется
#вся приходящая почта до процесса доставки.
queue_directory = /var/spool/postfix
#Путь для всех выполняемых программ почтового сервера.
command_directory = /usr/sbin
#Эта директива указывает postfix какие сети он должен считать
#локальными. Другими словами, компьютеры, соединяющиеся из этих сетей
#будут иметь возможность релея почтовых сообщений. В нашем случае мы
#прописываем следующие сети 127.0.0.0 (для localhost, собственно сам
#сервер), 192.168.10.0 (для всех других компьютеров в нашей внешней сети),
#и 192.168.0.0 (для всех компьютеров во внутренней сети).
# 93.100.239.44 - Алексей Пестриков
# 109.167.151.108 - lautre.ru
mynetworks = 10.0.0.0/8, 80.246.243.18, 95.213.228.194, 94.159.1.246, 109.167.151.108, 80.246.245.82, 80.246.248.234, 93.100.239.44
#По умолчанию, Postfix пытается посылать почту в Internet напрямую. В зависимости
#от окружения, в котором функционирует Ваш почтовый сервер, это может быть
#невозможно или нежелательно. Например, Ваша машина может быть отключена от
#Internet-а в нерабочее время, она может быть закрыта файрволлом, Ваш провайдер
#может запрещать пересылку почты в Internet напрямую. В таких случаях Вам
#необходимо настроить Postfix на пересылку писем через другой почтовый сервер
#(relay host).
#Вариант, заключенный в квадратные скобки [], заставляет Postfix
#не предпринимать поиск записей DNS MX.
#по умолчанию: посылать в Internet напрямую
#relayhost = [mail.$mydomain]
relay_domains = lists.calculate-linux.org
#Для создания базы используется postmap
transport_maps = hash:/etc/postfix/transport_maps
relay_recipient_maps = hash:/etc/postfix/valid_recipients

Some files were not shown because too many files have changed in this diff Show More

Loading…
Cancel
Save