249 lines
7.5 KiB
Python
249 lines
7.5 KiB
Python
#!/usr/bin/env python
|
|
# -*- coding: utf-8 -*-
|
|
# coding=UTF-8
|
|
# Relational
|
|
# Copyright (C) 2010 Salvo "LtWorf" Tomaselli
|
|
#
|
|
# Relational is free software: you can redistribute it and/or modify
|
|
# it under the terms of the GNU General Public License as published by
|
|
# the Free Software Foundation, either version 3 of the License, or
|
|
# (at your option) any later version.
|
|
#
|
|
# This program is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU General Public License
|
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
#
|
|
# author Salvo "LtWorf" Tomaselli <tiposchi@tiscali.it>
|
|
|
|
import os
|
|
from sys import exit
|
|
|
|
from relational import relation, parser, optimizer
|
|
from xtermcolor import colorize
|
|
|
|
|
|
COLOR_RED = 0xff0000
|
|
COLOR_GREEN = 0x00ff00
|
|
COLOR_MAGENTA = 0xff00ff
|
|
COLOR_CYAN = 0x00ffff
|
|
|
|
print relation
|
|
|
|
rels = {}
|
|
examples_path = 'samples/'
|
|
tests_path = 'test/'
|
|
|
|
|
|
def readfile(fname):
|
|
'''Reads a file as string and returns its content'''
|
|
fd = open(fname)
|
|
expr = fd.read()
|
|
fd.close()
|
|
return expr
|
|
|
|
|
|
def load_relations():
|
|
'''Loads all the relations present in the directory indicated in the
|
|
examples_path variable and stores them in the rels dictionary'''
|
|
print "Loading relations"
|
|
for i in os.listdir(examples_path):
|
|
if i.endswith('.csv'): # It's a relation, loading it
|
|
|
|
# Naming the relation
|
|
relname = i[:-4]
|
|
|
|
print ("Loading relation %s with name %s..." % (i, relname)),
|
|
|
|
rels[relname] = relation.relation('%s%s' % (examples_path, i))
|
|
print 'done'
|
|
|
|
|
|
def execute_tests():
|
|
|
|
py_bad = 0
|
|
py_good = 0
|
|
py_tot = 0
|
|
q_bad = 0
|
|
q_good = 0
|
|
q_tot = 0
|
|
ex_bad = 0
|
|
ex_good = 0
|
|
ex_tot = 0
|
|
|
|
for i in os.listdir(tests_path):
|
|
if i.endswith('.query'):
|
|
q_tot += 1
|
|
if run_test(i[:-6]):
|
|
q_good += 1
|
|
else:
|
|
q_bad += 1
|
|
elif i.endswith('.python'):
|
|
py_tot += 1
|
|
if run_py_test(i[:-7]):
|
|
py_good += 1
|
|
else:
|
|
py_bad += 1
|
|
elif i.endswith('.exec'):
|
|
ex_tot += 1
|
|
if run_exec_test(i[:-5]):
|
|
ex_good += 1
|
|
else:
|
|
ex_bad += 1
|
|
print colorize("Resume of the results", COLOR_CYAN)
|
|
|
|
print colorize("Query tests", COLOR_MAGENTA)
|
|
print "Total test count: %d" % q_tot
|
|
print "Passed tests: %d" % q_good
|
|
if q_bad > 0:
|
|
print colorize("Failed tests count: %d" % q_bad, COLOR_RED)
|
|
|
|
print colorize("Python tests", COLOR_MAGENTA)
|
|
print "Total test count: %d" % py_tot
|
|
print "Passed tests: %d" % py_good
|
|
if py_bad > 0:
|
|
print colorize("Failed tests count: %d" % py_bad, COLOR_RED)
|
|
|
|
print colorize("Execute Python tests", COLOR_MAGENTA)
|
|
print "Total test count: %d" % ex_tot
|
|
print "Passed tests: %d" % ex_good
|
|
if ex_bad > 0:
|
|
print colorize("Failed tests count: %d" % ex_bad, COLOR_RED)
|
|
|
|
print colorize("Total results", COLOR_CYAN)
|
|
if q_bad + py_bad + ex_bad == 0:
|
|
print colorize("No failed tests", COLOR_GREEN)
|
|
return 0
|
|
else:
|
|
print colorize("There are %d failed tests" % (py_bad + q_bad + ex_bad), COLOR_RED)
|
|
return 1
|
|
|
|
|
|
def run_exec_test(testname):
|
|
'''Runs a python test, which executes code directly rather than queries'''
|
|
print "Running python test: " + colorize(testname, COLOR_MAGENTA)
|
|
|
|
glob = rels.copy()
|
|
exp_result = {}
|
|
|
|
try:
|
|
|
|
expr = readfile('%s%s.exec' % (tests_path, testname))
|
|
exec(expr, glob) # Evaluating the expression
|
|
|
|
expr = readfile('%s%s.exec' % (tests_path, testname))
|
|
exec(expr, glob) # Evaluating the expression
|
|
|
|
expr = readfile('%s%s.result' % (tests_path, testname))
|
|
exp_result = eval(expr, rels) # Evaluating the expression
|
|
|
|
if isinstance(exp_result, dict):
|
|
fields_ok = True
|
|
|
|
for i in exp_result:
|
|
fields_ok = fields_ok and glob[i] == exp_result[i]
|
|
|
|
if fields_ok:
|
|
print colorize('Test passed', COLOR_GREEN)
|
|
return True
|
|
except:
|
|
pass
|
|
print colorize('ERROR', COLOR_RED)
|
|
print colorize('=====================================', COLOR_RED)
|
|
print "Expected %s" % exp_result
|
|
# print "Got %s" % result
|
|
print colorize('=====================================', COLOR_RED)
|
|
return False
|
|
|
|
|
|
def run_py_test(testname):
|
|
'''Runs a python test, which evaluates expressions directly rather than queries'''
|
|
print "Running expression python test: " + colorize(testname, COLOR_MAGENTA)
|
|
|
|
try:
|
|
|
|
expr = readfile('%s%s.python' % (tests_path, testname))
|
|
result = eval(expr, rels) # Evaluating the expression
|
|
|
|
expr = readfile('%s%s.result' % (tests_path, testname))
|
|
exp_result = eval(expr, rels) # Evaluating the expression
|
|
|
|
if result == exp_result:
|
|
print colorize('Test passed', COLOR_GREEN)
|
|
return True
|
|
except:
|
|
pass
|
|
|
|
print colorize('ERROR', COLOR_RED)
|
|
print colorize('=====================================', COLOR_RED)
|
|
print "Expected %s" % exp_result
|
|
print "Got %s" % result
|
|
print colorize('=====================================', COLOR_RED)
|
|
return False
|
|
|
|
|
|
def run_test(testname):
|
|
'''Runs a specific test executing the file
|
|
testname.query
|
|
and comparing the result with
|
|
testname.result
|
|
The query will be executed both unoptimized and
|
|
optimized'''
|
|
print "Running test: " + colorize(testname, COLOR_MAGENTA)
|
|
|
|
query = None
|
|
expr = None
|
|
o_query = None
|
|
o_expr = None
|
|
result_rel = None
|
|
result = None
|
|
o_result = None
|
|
|
|
try:
|
|
result_rel = relation.relation('%s%s.result' % (tests_path, testname))
|
|
|
|
query = unicode(
|
|
readfile('%s%s.query' % (tests_path, testname)).strip(), 'utf8')
|
|
o_query = optimizer.optimize_all(query, rels)
|
|
|
|
expr = parser.parse(query) # Converting expression to python string
|
|
result = eval(expr, rels) # Evaluating the expression
|
|
|
|
o_expr = parser.parse(
|
|
o_query) # Converting expression to python string
|
|
o_result = eval(o_expr, rels) # Evaluating the expression
|
|
|
|
c_expr = parser.tree(query).toCode() # Converting to python code
|
|
c_result = eval(c_expr, rels)
|
|
|
|
if (o_result == result_rel) and (result == result_rel) and (c_result == result_rel):
|
|
print colorize('Test passed', COLOR_GREEN)
|
|
return True
|
|
except Exception as inst:
|
|
print inst
|
|
pass
|
|
print colorize('ERROR', COLOR_RED)
|
|
print "Query: %s -> %s" % (query, expr)
|
|
print "Optimized query: %s -> %s" % (o_query, o_expr)
|
|
print colorize('=====================================', COLOR_RED)
|
|
print colorize("Expected result", COLOR_GREEN)
|
|
print result_rel
|
|
print colorize("Result", COLOR_RED)
|
|
print result
|
|
print colorize("Optimized result", COLOR_RED)
|
|
print o_result
|
|
print colorize("optimized result match %s" % str(result_rel == o_result), COLOR_MAGENTA)
|
|
print colorize("result match %s" % str(result == result_rel), COLOR_MAGENTA)
|
|
print colorize('=====================================', COLOR_RED)
|
|
return False
|
|
|
|
|
|
if __name__ == '__main__':
|
|
print "-> Starting testsuite for relational"
|
|
load_relations()
|
|
print "-> Starting tests"
|
|
exit(execute_tests())
|