zaut-2019/task2eduwiki.py
2018-12-07 21:09:51 +01:00

117 lines
3.5 KiB
Python
Executable File

#!/usr/bin/python2
# -*- coding: utf-8 -*-
import sys
import re
def process_file(filename):
parsed_file = parse_file(filename)
wikify(parsed_file)
def parse_file(filename):
task_file = open(filename,'r')
state = 'DOCSTRING_EXPECTED'
parsed_file = {}
parsed_file['filename'] = filename
for line in task_file:
line = line.rstrip()
if line == '' \
and state != 'INSIDE_DESCRIPTION' and state != 'INSIDE_TEST':
continue
if state == 'DOCSTRING_EXPECTED':
if line == '"""':
state = 'HEADER_EXPECTED'
continue
if state == 'HEADER_EXPECTED':
if re.match(r"Zadanie [A-Z0-9]+", line):
parsed_file['header'] = line
state = 'DESCRIPTION_EXPECTED'
else:
raise_error(state, line)
continue
if state == 'DESCRIPTION_EXPECTED':
parsed_file['description'] = line
state = 'INSIDE_DESCRIPTION'
continue
if state == 'INSIDE_DESCRIPTION':
if line == '':
state = 'ATTRS_EXPECTED'
else:
parsed_file['description'] += ' ' + line
continue
if state == 'ATTRS_EXPECTED':
if line == '"""':
state = 'TEST_EXPECTED'
else:
matched = re.match(r"([A-Z]+):\s*(.*)$", line)
if matched:
parsed_file[matched.group(1).lower()] = matched.group(2)
else:
raise_error(state, line)
continue
if state == 'TEST_EXPECTED':
if re.match(r"\s+def\s+test", line):
state = 'INSIDE_TEST'
parsed_file['test'] = line
continue
if state == 'INSIDE_TEST':
if re.match(r"if\s+__name__", line):
state = 'DONE'
else:
parsed_file['test'] += "\n" + line
if state != 'DONE':
raise BaseException('DONE state expected, was: %s' % state)
check_parsed_file(parsed_file)
return parsed_file
def check_parsed_file(parsed_file):
attrs_to_check = ('name', 'points', 'params', 'return', 'filename')
for attr in attrs_to_check:
if not attr in parsed_file:
raise BaseException('no %s attribute' % attr)
def raise_error(state, line):
raise BaseException("unexpected line in state %s: '%s'" % (state, line))
def wikify(parsed_file):
print "==== %(header)s ====" % parsed_file
print "\n({{{%(filename)s}}})\n" % parsed_file
print get_description_line(parsed_file['description'])
print_attr(parsed_file, "name", "Nazwa funkcji")
print_attr(parsed_file, "params", "Typy parametrów")
print_attr(parsed_file, "return", "Typ zwracany")
print_attr(parsed_file, "points", "Punkty")
print ""
print "Testy:{{{"
print parsed_file['test']
print "}}}"
print ""
print ""
def print_attr(parsed_file, attr, pl_label):
print "|| '''%s''' || `%s` ||" % (pl_label, parsed_file[attr])
def get_description_line(description):
formatting = "||<tablewidth=\"100%%\"> ''' Zadanie''' ||<80%%> %s ||"
return formatting % process_description(description)
def process_description(description):
description = re.sub(r"((?:\d+|n)\^(?:\d+|n))", r"\1^", description)
return description
if __name__ == '__main__':
if len(sys.argv) != 2:
raise BaseException('expected just one argument!')
process_file(sys.argv[1])