mirror of https://github.com/QMCPACK/qmcpack.git
nexus: preliminary testing framework
This commit is contained in:
parent
77df73250c
commit
161515a188
File diff suppressed because it is too large
Load Diff
|
@ -31,7 +31,7 @@
|
|||
#====================================================================#
|
||||
|
||||
|
||||
from generic import obj,object_interface,log,error,warn,devlog
|
||||
from generic import obj,object_interface,log,error,warn
|
||||
from debug import ci,interact
|
||||
|
||||
|
||||
|
|
|
@ -60,6 +60,12 @@ class Gamess(Simulation):
|
|||
Gamess.mcppath = mcppath
|
||||
#end def settings
|
||||
|
||||
@staticmethod
|
||||
def restore_default_settings():
|
||||
Gamess.ericfmt = None
|
||||
Gamess.mcppath = None
|
||||
#end def restore_default_settings
|
||||
|
||||
|
||||
def post_init(self):
|
||||
# gamess seems to need lots of environment variables to run properly
|
||||
|
|
|
@ -36,17 +36,30 @@ from copy import deepcopy
|
|||
import cPickle
|
||||
from random import randint
|
||||
|
||||
|
||||
class generic_settings:
|
||||
devlog = sys.stdout
|
||||
raise_error = False
|
||||
#end class generic_settings
|
||||
|
||||
|
||||
class NexusError(Exception):
|
||||
None
|
||||
#end class NexusError
|
||||
|
||||
|
||||
exit_call = sys.exit
|
||||
devlog = sys.stdout
|
||||
|
||||
|
||||
def nocopy(value):
|
||||
return value
|
||||
#end def nocopy
|
||||
|
||||
|
||||
|
||||
def log(*items,**kwargs):
|
||||
indent=None
|
||||
logfile=devlog
|
||||
logfile=generic_settings.devlog
|
||||
if len(kwargs)>0:
|
||||
n=0
|
||||
if 'indent' in kwargs:
|
||||
|
@ -81,24 +94,36 @@ def log(*items,**kwargs):
|
|||
#end def log
|
||||
|
||||
|
||||
def message(msg,header=None,post_header=' message:',indent=' ',logfile=devlog):
|
||||
def message(msg,header=None,post_header=' message:',indent=' ',logfile=None):
|
||||
if logfile is None:
|
||||
logfile = generic_settings.devlog
|
||||
#end if
|
||||
if header is None:
|
||||
header = post_header.lstrip()
|
||||
else:
|
||||
header += post_header
|
||||
#end if
|
||||
log('\n '+header)
|
||||
log('\n '+header,logfile=logfile)
|
||||
log(msg.rstrip(),indent=indent,logfile=logfile)
|
||||
#end def message
|
||||
|
||||
|
||||
def warn(msg,header=None,indent=' ',logfile=devlog):
|
||||
def warn(msg,header=None,indent=' ',logfile=None):
|
||||
if logfile is None:
|
||||
logfile = generic_settings.devlog
|
||||
#end if
|
||||
post_header=' warning:'
|
||||
message(msg,header,post_header,indent,logfile)
|
||||
#end def warn
|
||||
|
||||
|
||||
def error(msg,header=None,exit=True,trace=True,indent=' ',logfile=devlog):
|
||||
def error(msg,header=None,exit=True,trace=True,indent=' ',logfile=None):
|
||||
if generic_settings.raise_error:
|
||||
raise NexusError(msg)
|
||||
#end if
|
||||
if logfile is None:
|
||||
logfile = generic_settings.devlog
|
||||
#end if
|
||||
post_header=' error:'
|
||||
message(msg,header,post_header,indent,logfile)
|
||||
if exit:
|
||||
|
@ -569,9 +594,9 @@ class obj(object_interface):
|
|||
|
||||
def to_dict(self):
|
||||
d = dict()
|
||||
for k,v in self:
|
||||
for k,v in self._iteritems():
|
||||
if isinstance(v,obj):
|
||||
d[k] = v.to_dict()
|
||||
d[k] = v._to_dict()
|
||||
else:
|
||||
d[k] = v
|
||||
#end if
|
||||
|
@ -651,54 +676,6 @@ class obj(object_interface):
|
|||
return self
|
||||
#end def set_optional
|
||||
|
||||
def set_path(self,path,value=None):
|
||||
o = self
|
||||
cls = self.__class__
|
||||
if isinstance(path,str):
|
||||
path = path.split('/')
|
||||
#end if
|
||||
for p in path[0:-1]:
|
||||
if not p in o:
|
||||
o[p] = cls()
|
||||
#end if
|
||||
o = o[p]
|
||||
#end for
|
||||
o[path[-1]] = value
|
||||
#end def set_path
|
||||
|
||||
def get_path(self,path,value=None):
|
||||
o = self
|
||||
if isinstance(path,str):
|
||||
path = path.split('/')
|
||||
#end if
|
||||
for p in path[0:-1]:
|
||||
if not p in o:
|
||||
return value
|
||||
#end if
|
||||
o = o[p]
|
||||
#end for
|
||||
lp = path[-1]
|
||||
if lp not in o:
|
||||
return value
|
||||
else:
|
||||
return o[lp]
|
||||
#end if
|
||||
#end def get_path
|
||||
|
||||
def path_exists(self,path):
|
||||
o = self
|
||||
if isinstance(path,str):
|
||||
path = path.split('/')
|
||||
#end if
|
||||
for p in path:
|
||||
if not p in o:
|
||||
return False
|
||||
#end if
|
||||
o = o[p]
|
||||
#end for
|
||||
return True
|
||||
#end def path_exists
|
||||
|
||||
def get(self,key,value=None): # follow dict interface, no plural
|
||||
if key in self:
|
||||
value = self[key]
|
||||
|
@ -855,7 +832,7 @@ class obj(object_interface):
|
|||
def shallow_copy(self):
|
||||
new = self.__class__()
|
||||
for k,v in self._iteritems():
|
||||
self[k] = v
|
||||
new[k] = v
|
||||
#end for
|
||||
return new
|
||||
#end def shallow_copy
|
||||
|
@ -868,6 +845,54 @@ class obj(object_interface):
|
|||
return new
|
||||
#end def inverse
|
||||
|
||||
def path_exists(self,path):
|
||||
o = self
|
||||
if isinstance(path,str):
|
||||
path = path.split('/')
|
||||
#end if
|
||||
for p in path:
|
||||
if not p in o:
|
||||
return False
|
||||
#end if
|
||||
o = o[p]
|
||||
#end for
|
||||
return True
|
||||
#end def path_exists
|
||||
|
||||
def set_path(self,path,value=None):
|
||||
o = self
|
||||
cls = self.__class__
|
||||
if isinstance(path,str):
|
||||
path = path.split('/')
|
||||
#end if
|
||||
for p in path[0:-1]:
|
||||
if not p in o:
|
||||
o[p] = cls()
|
||||
#end if
|
||||
o = o[p]
|
||||
#end for
|
||||
o[path[-1]] = value
|
||||
#end def set_path
|
||||
|
||||
def get_path(self,path,value=None):
|
||||
o = self
|
||||
if isinstance(path,str):
|
||||
path = path.split('/')
|
||||
#end if
|
||||
for p in path[0:-1]:
|
||||
if not p in o:
|
||||
return value
|
||||
#end if
|
||||
o = o[p]
|
||||
#end for
|
||||
lp = path[-1]
|
||||
if lp not in o:
|
||||
return value
|
||||
else:
|
||||
return o[lp]
|
||||
#end if
|
||||
#end def get_path
|
||||
|
||||
def serial(self,s=None,path=None):
|
||||
first = s is None
|
||||
if first:
|
||||
|
@ -877,7 +902,11 @@ class obj(object_interface):
|
|||
for k,v in self._iteritems():
|
||||
p = path+str(k)
|
||||
if isinstance(v,obj):
|
||||
v._serial(s,p+'/')
|
||||
if len(v)==0:
|
||||
s[p]=v
|
||||
else:
|
||||
v._serial(s,p+'/')
|
||||
#end if
|
||||
else:
|
||||
s[p]=v
|
||||
#end if
|
||||
|
@ -920,8 +949,6 @@ class obj(object_interface):
|
|||
obj.set(self,*args,**kwargs)
|
||||
def _set_optional(self,*args,**kwargs):
|
||||
obj.set_optional(self,*args,**kwargs)
|
||||
def _set_path(self,*args,**kwargs):
|
||||
obj.set_path(self,*args,**kwargs)
|
||||
def _get(self,*args,**kwargs):
|
||||
obj.get(self,*args,**kwargs)
|
||||
def _get_optional(self,*args,**kwargs):
|
||||
|
@ -954,6 +981,12 @@ class obj(object_interface):
|
|||
obj.shallow_copy(self,*args,**kwargs)
|
||||
def _inverse(self,*args,**kwargs):
|
||||
return obj.inverse(self,*args,**kwargs)
|
||||
def _path_exists(self,*args,**kwargs):
|
||||
obj.path_exists(self,*args,**kwargs)
|
||||
def _set_path(self,*args,**kwargs):
|
||||
obj.set_path(self,*args,**kwargs)
|
||||
def _get_path(self,*args,**kwargs):
|
||||
obj.get_path(self,*args,**kwargs)
|
||||
def _serial(self,*args,**kwargs):
|
||||
return obj.serial(self,*args,**kwargs)
|
||||
|
||||
|
@ -971,12 +1004,12 @@ class hobj(obj):
|
|||
@property
|
||||
def _dict(self):
|
||||
return self.__dict__
|
||||
#end def __get_dict
|
||||
#end def _dict
|
||||
|
||||
@property
|
||||
def _alt(self):
|
||||
return self.__dict__
|
||||
#end def __alt
|
||||
#end def _alt
|
||||
|
||||
def __len__(self):
|
||||
return len(self._dict)
|
||||
|
|
|
@ -155,6 +155,12 @@ class Job(NexusCore):
|
|||
cray_compilers = set(['cray'])
|
||||
|
||||
|
||||
@staticmethod
|
||||
def restore_default_settings():
|
||||
Job.machine = None
|
||||
#end def restore_default_settings
|
||||
|
||||
|
||||
@staticmethod
|
||||
def generate_jobid():
|
||||
Job.job_count += 1
|
||||
|
@ -924,6 +930,14 @@ class Machine(NexusCore):
|
|||
Machine.add(self)
|
||||
#end def __init__
|
||||
|
||||
|
||||
def restore_default_settings(self):
|
||||
self.account = None
|
||||
self.local_directory = None
|
||||
self.app_directory = None
|
||||
self.app_directories = None
|
||||
#end def restore_default_settings
|
||||
|
||||
|
||||
def add_job(self,job):
|
||||
if isinstance(job,Job):
|
||||
|
|
|
@ -27,7 +27,7 @@ import os
|
|||
from generic import obj
|
||||
from developer import error
|
||||
|
||||
from nexus_base import NexusCore,nexus_core,nexus_noncore,nexus_core_noncore
|
||||
from nexus_base import NexusCore,nexus_core,nexus_noncore,nexus_core_noncore,restore_nexus_core_defaults
|
||||
from machines import Job,job,Machine,Supercomputer,get_machine
|
||||
from simulation import generate_simulation,input_template,multi_input_template,generate_template_input,generate_multi_template_input
|
||||
from project_manager import ProjectManager
|
||||
|
@ -104,8 +104,8 @@ class Settings(NexusCore):
|
|||
ericfmt mcppath
|
||||
'''.split())
|
||||
|
||||
pwscf_vars = set('''
|
||||
vdw_table
|
||||
pwscf_vars = set('''
|
||||
vdw_table
|
||||
'''.split())
|
||||
|
||||
nexus_core_vars = core_assign_vars | core_process_vars
|
||||
|
@ -133,7 +133,7 @@ class Settings(NexusCore):
|
|||
if Settings.singleton is None:
|
||||
Settings.singleton = self
|
||||
else:
|
||||
self.error('attempted to create a second Settings object\n please just use the original')
|
||||
self.error('attempted to create a second Settings object\nplease just use the original')
|
||||
#end if
|
||||
#end def __init__
|
||||
|
||||
|
@ -156,6 +156,9 @@ class Settings(NexusCore):
|
|||
self.error('unrecognized variables provided\nyou provided: {0}\nallowed variables are: {1}'.format(sorted(not_allowed),sorted(Settings.allowed_vars)))
|
||||
#end if
|
||||
|
||||
# restore default core default settings
|
||||
restore_nexus_core_defaults()
|
||||
|
||||
# assign simple variables
|
||||
for name in Settings.core_assign_vars:
|
||||
if name in kwargs:
|
||||
|
@ -204,9 +207,11 @@ class Settings(NexusCore):
|
|||
|
||||
|
||||
# process gamess settings
|
||||
Gamess.restore_default_settings()
|
||||
Gamess.settings(**gamess_kw)
|
||||
|
||||
# process pwscf settings
|
||||
# process pwscf settings
|
||||
Pwscf.restore_default_settings()
|
||||
Pwscf.settings(**pwscf_kw)
|
||||
|
||||
return
|
||||
|
@ -214,6 +219,9 @@ class Settings(NexusCore):
|
|||
|
||||
|
||||
def process_machine_settings(self,mset):
|
||||
Job.restore_default_settings()
|
||||
ProjectManager.restore_default_settings()
|
||||
mid_set = set()
|
||||
if 'machine_info' in mset:
|
||||
machine_info = mset.machine_info
|
||||
if isinstance(machine_info,dict) or isinstance(machine_info,obj):
|
||||
|
@ -221,7 +229,9 @@ class Settings(NexusCore):
|
|||
mname = machine_name.lower()
|
||||
if Machine.exists(mname):
|
||||
machine = Machine.get(mname)
|
||||
machine.restore_default_settings()
|
||||
machine.incorporate_user_info(minfo)
|
||||
mid_set.add(id(machine))
|
||||
else:
|
||||
self.error('machine {0} is unknown\n cannot set machine_info'.format(machine_name))
|
||||
#end if
|
||||
|
@ -236,7 +246,11 @@ class Settings(NexusCore):
|
|||
self.error('machine {0} is unknown'.format(machine_name))
|
||||
#end if
|
||||
Job.machine = machine_name
|
||||
ProjectManager.machine = Machine.get(machine_name)
|
||||
machine = Machine.get(machine_name)
|
||||
ProjectManager.machine = machine
|
||||
if machine is not None and id(machine) not in mid_set:
|
||||
machine.restore_default_settings()
|
||||
#end if
|
||||
if 'account' in mset:
|
||||
account = mset.account
|
||||
if not isinstance(account,str):
|
||||
|
|
|
@ -38,6 +38,7 @@ from developer import DevBase
|
|||
# nexus_noncore: allows read only access to some nexus_core data to non-core classes
|
||||
nexus_core = obj()
|
||||
nexus_noncore = obj()
|
||||
nexus_core_noncore = obj()
|
||||
|
||||
status_modes = obj(
|
||||
none = 0,
|
||||
|
@ -61,18 +62,18 @@ modes = obj(
|
|||
garbage_collector.enable()
|
||||
|
||||
|
||||
nexus_noncore.set(
|
||||
nexus_noncore_defaults = obj(
|
||||
basis_dir = None,
|
||||
basissets = None,
|
||||
)
|
||||
|
||||
# core namespace elements that can be accessed by noncore classes
|
||||
nexus_core_noncore = obj(
|
||||
nexus_core_noncore_defaults = obj(
|
||||
pseudo_dir = None, # used by: Settings, VaspInput
|
||||
pseudopotentials = None, # used by: Simulation, GamessInput
|
||||
)
|
||||
|
||||
nexus_core.set(
|
||||
nexus_core_defaults = obj(
|
||||
status_only = False, # used by: ProjectManager
|
||||
generate_only = False, # used by: Simulation,Machine
|
||||
sleep = 3, # used by: ProjectManager
|
||||
|
@ -98,9 +99,22 @@ nexus_core.set(
|
|||
status = status_modes.none, # used by: ProjectManager
|
||||
emulate = False, # unused
|
||||
progress_tty = False, # used by: ProjectManager
|
||||
**nexus_core_noncore
|
||||
**nexus_core_noncore_defaults
|
||||
)
|
||||
|
||||
def restore_nexus_core_defaults():
|
||||
nexus_core.clear()
|
||||
nexus_noncore.clear()
|
||||
nexus_core_noncore.clear()
|
||||
|
||||
nexus_core.set(**nexus_core_defaults.copy())
|
||||
nexus_noncore.set(**nexus_noncore_defaults.copy())
|
||||
nexus_core_noncore.transfer_from(nexus_core,keys=nexus_core_noncore_defaults.keys())
|
||||
#end def restore_nexus_core_defaults
|
||||
|
||||
restore_nexus_core_defaults()
|
||||
|
||||
|
||||
nexus_core_no_process = set('''
|
||||
status_only generate_only sleep
|
||||
'''.split())
|
||||
|
|
|
@ -31,6 +31,14 @@ def trivial(sim,*args,**kwargs):
|
|||
|
||||
|
||||
class ProjectManager(NexusCore):
|
||||
|
||||
machine = None
|
||||
|
||||
@staticmethod
|
||||
def restore_default_settings():
|
||||
ProjectManager.machine = None
|
||||
#end def restore_default_settings
|
||||
|
||||
def __init__(self):
|
||||
modes = nexus_core.modes
|
||||
self.persistent_modes = set([modes.submit,modes.all])
|
||||
|
|
|
@ -99,6 +99,12 @@ class Pwscf(Simulation):
|
|||
Pwscf.vdw_table = vdw_table
|
||||
#end def settings
|
||||
|
||||
@staticmethod
|
||||
def restore_default_settings():
|
||||
Pwscf.vdw_table = None
|
||||
#end def restore_default_settings
|
||||
|
||||
|
||||
#def propagate_identifier(self):
|
||||
# self.input.control.prefix = self.identifier
|
||||
##end def propagate_identifier
|
||||
|
|
|
@ -3,7 +3,8 @@ import os
|
|||
import itertools
|
||||
from time import clock
|
||||
from numpy import ndarray,ceil
|
||||
from developer import obj,ci,error as dev_error,devlog,DevBase
|
||||
from generic import generic_settings
|
||||
from developer import obj,ci,error as dev_error,DevBase
|
||||
from physical_system import generate_physical_system
|
||||
from simulation import Simulation,GenericSimulation,graph_sims
|
||||
from bundle import bundle as bundle_function
|
||||
|
@ -60,8 +61,7 @@ from qmcpack import generate_qmcpack
|
|||
# should probably make temp simlist at qmcpack_workflow start
|
||||
|
||||
|
||||
|
||||
def error(msg,loc=None,exit=True,trace=True,indent=' ',logfile=devlog):
|
||||
def error(msg,loc=None,exit=True,trace=True,indent=' ',logfile=generic_settings.devlog):
|
||||
header = 'qmcpack_workflows'
|
||||
if loc!=None:
|
||||
msg+='\nfunction location: {0}'.format(loc)
|
||||
|
|
|
@ -0,0 +1,271 @@
|
|||
|
||||
import os
|
||||
import sys
|
||||
import traceback
|
||||
from numpy import ndarray,array,abs
|
||||
|
||||
|
||||
def value_diff(v1,v2,tol=1e-6):
|
||||
diff = False
|
||||
if not isinstance(v1,type(v2)):
|
||||
diff = True
|
||||
elif isinstance(v1,(bool,int,str)):
|
||||
diff = v1!=v2
|
||||
elif isinstance(v1,float):
|
||||
diff = abs(v1-v2)>tol
|
||||
elif isinstance(v1,(list,tuple)):
|
||||
v1 = array(v1,dtype=object).ravel()
|
||||
v2 = array(v2,dtype=object).ravel()
|
||||
for vv1,vv2 in zip(v1,v2):
|
||||
diff |= value_diff(vv1,vv2)
|
||||
#end for
|
||||
elif isinstance(v1,ndarray):
|
||||
v1 = v1.ravel()
|
||||
v2 = v2.ravel()
|
||||
for vv1,vv2 in zip(v1,v2):
|
||||
diff |= value_diff(vv1,vv2)
|
||||
#end for
|
||||
elif isinstance(v1,dict):
|
||||
diff = v1!=v2
|
||||
elif isinstance(v1,set):
|
||||
diff = v1!=v2
|
||||
elif v1 is None and v2 is None:
|
||||
diff = False
|
||||
else:
|
||||
diff = True # unsupported types
|
||||
#end if
|
||||
return diff
|
||||
#end def value_diff
|
||||
|
||||
|
||||
def object_diff(o1,o2,tol=1e-6,full=False):
|
||||
diff1 = dict()
|
||||
diff2 = dict()
|
||||
o1 = o1._serial()
|
||||
o2 = o2._serial()
|
||||
keys1 = set(o1._keys())
|
||||
keys2 = set(o2._keys())
|
||||
ku1 = keys1 - keys2
|
||||
ku2 = keys2 - keys1
|
||||
km = keys1 & keys2
|
||||
for k in ku1:
|
||||
diff1[k] = o1[k]
|
||||
#end for
|
||||
for k in ku2:
|
||||
diff2[k] = o2[k]
|
||||
#end for
|
||||
for k in km:
|
||||
v1 = o1[k]
|
||||
v2 = o2[k]
|
||||
if value_diff(v1,v2,tol):
|
||||
diff1[k] = v1
|
||||
diff2[k] = v2
|
||||
#end if
|
||||
#end for
|
||||
diff = len(diff1)!=0 or len(diff2)!=0
|
||||
if not full:
|
||||
return diff
|
||||
else:
|
||||
return diff,diff1,diff2
|
||||
#end if
|
||||
#end def object_diff
|
||||
|
||||
|
||||
|
||||
value_neq = value_diff
|
||||
def value_eq(*args,**kwargs):
|
||||
return not value_neq(*args,**kwargs)
|
||||
#end def value_eq
|
||||
|
||||
object_neq = object_diff
|
||||
def object_eq(*args,**kwargs):
|
||||
return not object_neq(*args,**kwargs)
|
||||
#end def object_eq
|
||||
|
||||
|
||||
|
||||
class NexusTestFail(Exception):
|
||||
None
|
||||
#end class NexusTestFail
|
||||
|
||||
class NexusTestMisconstructed(Exception):
|
||||
None
|
||||
#end class NexusTestMisconstructed
|
||||
|
||||
class NexusTestTripped(Exception):
|
||||
None
|
||||
#end class NexusTestTripped
|
||||
|
||||
|
||||
class NexusTestBase(object):
|
||||
nexus_test_dir = '.nexus_test' # ntest directory
|
||||
|
||||
launch_path = None # path from which ntest exe was launched
|
||||
current_test = '' # current NexusTest.name
|
||||
current_label = '' # current nlabel()
|
||||
test_count = 0 # current test count
|
||||
label_count = 0 # current label count in NexusTest.operation()
|
||||
current_assert = 0 # current assert count
|
||||
|
||||
assert_trip = -1 # developer tool to trip assert's one by one
|
||||
|
||||
@staticmethod
|
||||
def assert_called():
|
||||
NexusTestBase.current_assert+=1
|
||||
ca = NexusTestBase.current_assert
|
||||
if ca==NexusTestBase.assert_trip:
|
||||
raise NexusTestTripped
|
||||
#end if
|
||||
#end def assert_called
|
||||
|
||||
#end class NexusTestBase
|
||||
|
||||
|
||||
|
||||
|
||||
def nlabel(label):
|
||||
os.chdir(NexusTestBase.launch_path)
|
||||
NexusTestBase.current_label = label
|
||||
NexusTestBase.label_count += 1
|
||||
#end def nlabel
|
||||
|
||||
|
||||
def nenter(path):
|
||||
test = NexusTestBase.current_test
|
||||
label = NexusTestBase.current_label
|
||||
tcount = str(NexusTestBase.test_count).zfill(2)
|
||||
lcount = str(NexusTestBase.label_count).zfill(2)
|
||||
test_dir = '{0}_{1}'.format(tcount,test)
|
||||
label_dir = '{0}_{1}'.format(lcount,label)
|
||||
ntdir = NexusTestBase.nexus_test_dir
|
||||
nlpath = NexusTestBase.launch_path
|
||||
if len(label)==0:
|
||||
enter_path = os.path.join(nlpath,ntdir,test_dir)
|
||||
else:
|
||||
enter_path = os.path.join(nlpath,ntdir,test_dir,label_dir)
|
||||
#end if
|
||||
os.makedirs(enter_path)
|
||||
#end def nenter
|
||||
|
||||
|
||||
def nleave():
|
||||
os.chdir(NexusTestBase.launch_path)
|
||||
#end def nleave
|
||||
|
||||
|
||||
def npass():
|
||||
None
|
||||
#end def npass
|
||||
|
||||
|
||||
def nfail(exception=NexusTestFail('Nexus test failed.')):
|
||||
raise exception
|
||||
#end def nfail
|
||||
|
||||
|
||||
def nassert(result):
|
||||
if not isinstance(result,bool):
|
||||
raise NexusTestMisconstructed
|
||||
elif not result:
|
||||
nfail()
|
||||
else:
|
||||
npass()
|
||||
#end if
|
||||
NexusTestBase.assert_called()
|
||||
#end def nassert
|
||||
|
||||
|
||||
|
||||
class NexusTest(NexusTestBase):
|
||||
|
||||
status_options = dict(
|
||||
unused = 0,
|
||||
passed = 1,
|
||||
failed = 2,
|
||||
)
|
||||
|
||||
status_map = dict()
|
||||
for k,v in status_options.iteritems():
|
||||
status_map[v] = k
|
||||
#end for
|
||||
|
||||
test_list = []
|
||||
test_dict = {}
|
||||
|
||||
|
||||
@staticmethod
|
||||
def setup():
|
||||
NexusTestBase.launch_path = os.path.getcwd()
|
||||
#end def setup
|
||||
|
||||
|
||||
def __init__(self,name,operation):
|
||||
if not isinstance(name,str):
|
||||
raise NexusTestMisconstructed
|
||||
#end if
|
||||
self.name = name
|
||||
self.operation = operation
|
||||
self.exception = None
|
||||
self.status = NexusTest.status_options['unused']
|
||||
NexusTest.test_list.append(self)
|
||||
NexusTest.test_dict[self.name] = self
|
||||
#end def __init__
|
||||
|
||||
@property
|
||||
def unused(self):
|
||||
return self.status==NexusTest.status_options['unused']
|
||||
#end def unused
|
||||
|
||||
@property
|
||||
def passed(self):
|
||||
return self.status==NexusTest.status_options['passed']
|
||||
#end def passed
|
||||
|
||||
@property
|
||||
def failed(self):
|
||||
return self.status==NexusTest.status_options['failed']
|
||||
#end def failed
|
||||
|
||||
def run(self):
|
||||
NexusTestBase.current_test = self.name
|
||||
NexusTestBase.current_label = ''
|
||||
NexusTestBase.test_count += 1
|
||||
NexusTestBase.label_count = 0
|
||||
os.chdir(NexusTestBase.launch_path)
|
||||
try:
|
||||
self.operation()
|
||||
self.status=NexusTest.status_options['passed']
|
||||
except Exception,e:
|
||||
self.exception = e
|
||||
self.traceback = sys.exc_info()[2]
|
||||
self.status=NexusTest.status_options['failed']
|
||||
#end try
|
||||
#end def run
|
||||
|
||||
def message(self):
|
||||
s = ''
|
||||
s+='test name : {0}\n'.format(self.name)
|
||||
status = NexusTest.status_map[self.status]
|
||||
s+='test status : {0}\n'.format(status)
|
||||
if self.failed and self.exception is not None:# and not isinstance(self.exception,NexusTestFail):
|
||||
if len(NexusTestBase.current_label)>0:
|
||||
s+='test sublabel: {0}\n'.format(NexusTestBase.current_label)
|
||||
#end if
|
||||
e = self.exception
|
||||
btrace = traceback.format_tb(self.traceback)
|
||||
if isinstance(e,NexusTestFail):
|
||||
btrace = btrace[:-1]
|
||||
elif isinstance(e,NexusTestMisconstructed):
|
||||
btrace = btrace[:-1]
|
||||
s+='exception : Nexus test is misconstructed. Please contact developers.\n'
|
||||
else:
|
||||
s+='exception : "{0}"\n'.format(e.__class__.__name__+': '+str(e).replace('\n','\n '))
|
||||
#end if
|
||||
s+='backtrace :\n'
|
||||
for s2 in btrace:
|
||||
s+=s2
|
||||
#end for
|
||||
#end if
|
||||
return s
|
||||
#end def message
|
||||
#end class NexusTest
|
Loading…
Reference in New Issue