~azzar1/unity/add-show-desktop-key

« back to all changes in this revision

Viewing changes to www/apps/tutorialservice/test/parse_tute.py

  • Committer: mattgiuca
  • Date: 2008-01-24 23:57:26 UTC
  • Revision ID: svn-v3-trunk0:2b9c9e99-6f39-0410-b283-7f802c844ae2:trunk:294
Added application: tutorialservice. Will be used as the Ajax backend for
    tutorial (currently empty).
Moved tutorial/test to tutorialservice/test.
Reason: The testing framework will not be used by the tutorial HTML-side app.
    Only by the ajax backend.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
# IVLE - Informatics Virtual Learning Environment
 
2
# Copyright (C) 2007-2008 The University of Melbourne
 
3
#
 
4
# This program is free software; you can redistribute it and/or modify
 
5
# it under the terms of the GNU General Public License as published by
 
6
# the Free Software Foundation; either version 2 of the License, or
 
7
# (at your option) any later version.
 
8
#
 
9
# This program is distributed in the hope that it will be useful,
 
10
# but WITHOUT ANY WARRANTY; without even the implied warranty of
 
11
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
12
# GNU General Public License for more details.
 
13
#
 
14
# You should have received a copy of the GNU General Public License
 
15
# along with this program; if not, write to the Free Software
 
16
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 
17
 
 
18
# Module: parse_tute
 
19
# Author: Dilshan Angampitiya
 
20
# Date:   24/1/2008
 
21
 
 
22
"""
 
23
This file provides the function parse_tutorial_file which takes an
 
24
xml specification of a tutorial problem file and returns a test suite object
 
25
for that problem. It throws a ParseException if there was a problem parsing
 
26
the file.
 
27
"""
 
28
 
 
29
from xml.dom.minidom import *
 
30
from TestFramework import *
 
31
 
 
32
DEFAULT_TEST_TYPE = 'norm'
 
33
DEFAULT_CASE_TYPE = 'match'
 
34
 
 
35
class ParseException(Exception):
 
36
    " Error when parsing the xml problem file "
 
37
    def __init___(self, reason):
 
38
        self._reason = reason
 
39
 
 
40
    def __str__(self):
 
41
        return self._reason
 
42
 
 
43
def getTextData(element):
 
44
    """ Get the text and cdata inside an element
 
45
    Leading and trailing whitespace are stripped
 
46
    """
 
47
    data = ''
 
48
    for child in element.childNodes:
 
49
        if child.nodeType == child.CDATA_SECTION_NODE:
 
50
            data += child.data
 
51
        if child.nodeType == child.TEXT_NODE:
 
52
            data += child.data
 
53
 
 
54
    return data.strip()
 
55
 
 
56
def getCasePartData(partNode):
 
57
    """ Create an TestCasePaart instance from test part xml data
 
58
    """
 
59
    
 
60
    func_desc = partNode.getAttribute('desc')
 
61
    default = partNode.getAttribute('default')
 
62
    if default == '': default = DEFAULT_CASE_TYPE
 
63
    
 
64
    part = TestCasePart(func_desc, default)
 
65
 
 
66
    for child in partNode.childNodes:
 
67
        if child.nodeType != child.ELEMENT_NODE:
 
68
            continue
 
69
 
 
70
        if child.tagName == 'stdout':
 
71
            test_type = child.getAttribute('type')
 
72
            if test_type == '': test_type = DEFAULT_TEST_TYPE
 
73
            part.add_stdout_test(getTextData(child), test_type)
 
74
        elif child.tagName == 'stderr':
 
75
            test_type = child.getAttribute('type')
 
76
            if test_type == '': test_type = DEFAULT_TEST_TYPE
 
77
            part.add_stderr_test(getTextData(child), test_type)
 
78
        elif child.tagName == 'file':
 
79
            test_type = child.getAttribute('type')
 
80
            if test_type == '': test_type = DEFAULT_TEST_TYPE
 
81
            filename = child.getAttribute('name')
 
82
            if filename == '':
 
83
                raise ParseException("File without name in case %s" %case_name)
 
84
            part.add_file_test(filename, getTextData(child), test_type)
 
85
 
 
86
    return part
 
87
 
 
88
def getCaseData(caseNode):
 
89
    """ Creare a TestCase instance from test case xml data
 
90
    """
 
91
    
 
92
    case_name = caseNode.getAttribute('name')
 
93
    function = caseNode.getAttribute('function')
 
94
    if function == '': function = None
 
95
    case = TestCase(case_name, function)
 
96
    
 
97
    for child in caseNode.childNodes:
 
98
        if child.nodeType != child.ELEMENT_NODE:
 
99
            continue
 
100
 
 
101
        if child.tagName == 'stdin':
 
102
            # standard input
 
103
            case.set_stdin(getTextData(child))
 
104
        elif child.tagName == 'file':
 
105
            # file
 
106
            filename = child.getAttribute('name')
 
107
            if filename == '':
 
108
                raise ParseException("File without name in case %s" %case_name)
 
109
            case.add_file(filename, getTextData(child))
 
110
        elif child.tagName == 'var':
 
111
            # global variable
 
112
            var_name = child.getAttribute('name')
 
113
            var_val = child.getAttribute('value')
 
114
            if not var_name or not var_val:
 
115
                raise ParseException("Incomplete variable in case %s" %case_name)
 
116
            case.add_variable(var_name, var_val)
 
117
        elif child.tagName == 'arg':
 
118
            # function argument
 
119
            arg_val = child.getAttribute('value')
 
120
            arg_name = child.getAttribute('name')
 
121
            if arg_name == '': arg_name = None
 
122
            
 
123
            if not arg_val:
 
124
                raise ParseException("Incomplete argument in case %s" %case_name)
 
125
            case.add_arg(arg_val, arg_name)
 
126
        elif child.tagName == 'function':
 
127
            # specify a test case part
 
128
            case.add_part(getCasePartData(child))
 
129
 
 
130
    return case
 
131
                
 
132
def parse_tutorial_file(filename, prob_num=1):
 
133
    """ Parse an xml problem file and return a testsuite for that problem """
 
134
    dom = parse(filename)
 
135
 
 
136
    # get problem
 
137
    count = 0
 
138
    problem = None
 
139
    for child in dom.childNodes:
 
140
        if child.nodeType == child.ELEMENT_NODE and child.tagName == 'problem':
 
141
            count += 1
 
142
            if count == prob_num:
 
143
                problem = child
 
144
                break
 
145
 
 
146
    if problem == None:
 
147
        raise ParseException("Not enough problems")
 
148
 
 
149
    # get name
 
150
    problem_name = problem.getAttribute('name')
 
151
 
 
152
    if not problem_name:
 
153
        raise ParseException('Problem name not supplied')
 
154
 
 
155
    problem_suite = TestSuite(problem_name)
 
156
 
 
157
    # get solution and include info
 
158
    for child in problem.childNodes:
 
159
        if child.nodeType != child.ELEMENT_NODE:
 
160
            continue
 
161
        if child.tagName == 'solution':
 
162
            problem_suite.add_solution(getTextData(child))
 
163
        elif child.tagName == 'include':
 
164
            problem_suite.add_include_code(getTextData(child))
 
165
        elif child.tagName == 'case':
 
166
            problem_suite.add_case(getCaseData(child))
 
167
 
 
168
    return problem_suite
 
169