no more lxc-enter-namespace - use ssh
[tests.git] / qaapi / qa / QAAPI.py
1 import sys, os
2 import traceback
3 import tests
4 from Config import Config
5 from tests.Test import Test
6 from logger import log  
7
8 class QAAPI:
9    
10     tests_path = os.path.realpath(tests.__path__[0])
11     methods = []
12                 
13         
14     def __init__(self, globals, config = None, logging=None, verbose=None):
15         if config is None: self.config = Config()
16         else: self.config = Config(config)
17
18         test_files = self.test_files(self.tests_path)
19         callables = set()
20         # determine what is callable
21         for file in test_files:
22             tests = self.callables(file)
23             tests = filter(lambda t: t.test_name not in ['Test'], tests)
24             callables.update(tests)
25                 
26         # Add methods to self and global environemt     
27         for method in callables:
28             if logging: method = log(method, method.test_name)
29             elif hasattr(self.config, 'log') and self.config.log:
30                 method = log(method, method.test_name)
31             class Dummy: pass
32             paths = method.test_name.split(".")
33             
34             if len(paths) > 1:
35                 first = paths.pop(0)
36
37                 if not hasattr(self, first):
38                     obj = Dummy()
39                     setattr(self, first, obj)
40                     # Also add to global environment if specified
41                     if globals is not None:
42                         globals[first] = obj
43
44                 obj = getattr(self, first)
45
46                 for path in paths:
47                     if not hasattr(obj, path):
48                         if path == paths[-1]:
49                             setattr(obj, path, method)
50                             globals[method.test_name]=obj  
51                         else:
52                             setattr(obj, path, Dummy())
53                     obj = getattr(obj, path)
54             else:
55                 if globals is not None:
56                     globals[method.test_name] = method          
57
58     def test_files(self, tests_dir):
59         """
60         Build a list of files   
61         """     
62         
63         # Load files from tests direcotry
64         real_files = lambda name: not name.startswith('__init__') \
65                                   and  name.endswith('.py')
66         remove_ext = lambda name: name.split(".py")[0]
67         iterator = os.walk(tests_dir)
68         (root, basenames, files) = iterator.next()
69         test_base = ""
70         test_files = []
71         test_files.extend([test_base+file for file in map(remove_ext, filter(real_files, files))])
72         
73         # recurse through directory             
74         #for (root, dirs, files) in iterator:
75         #    parts = root.split(os.sep)
76         #    for basename in basenames:
77         #        if basename in parts:
78         #            test_base = ".".join(parts[parts.index(basename):])+"."
79         #    files = filter(real_files, files)
80         #    files = map(remove_ext, files)
81         #    test_files.extend([test_base+file for file in  files])
82         return list(set(test_files)) 
83
84     def callables(self, test_file):
85         """
86         Return a new instance of the specified method. 
87         """      
88         
89         # Get new instance of method
90         parts = test_file.split(".")
91         # add every part except for the last to name (filename)
92         tests_dir =  "tests."
93         test_basename = ".".join(parts[:-1])
94         if test_basename: test_basename += '.'
95         test_path = tests_dir + test_file
96         try:
97             test = __import__(test_path, globals(), locals(), test_path)
98             callables = []
99             for attribute in dir(test):
100                 attr = getattr(test, attribute)
101                 if callable(attr) and hasattr(attr, 'status'):
102                     setattr(attr, 'test_name', test_basename+attribute)
103                     try:
104                         test_instance = attr(self.config)
105                         callables.append(test_instance)
106                     except: pass
107             return callables 
108         except ImportError, AttributeError:
109             raise  
110          
111