"""
Main tellurium entry point.
The module tellurium provides support routines.
As part of this module an ExendedRoadRunner class is defined which provides helper methods for
model export, plotting or the Jarnac compatibility layer.
"""
##############################################
# Core imports
##############################################
from __future__ import print_function, division, absolute_import
import sys
import os
import random
import warnings
import importlib
import json
import numpy as np
import antimony
import matplotlib
PLOTTING_ENGINE_MATPLOTLIB = 'matplotlib'
PLOTTING_ENGINE_PLOTLY = 'plotly'
__default_plotting_engine = PLOTTING_ENGINE_MATPLOTLIB
# enable fixes for Spyder (no Plotly support, no Agg support)
SPYDER = False
if any('SPYDER' in name for name in os.environ):
SPYDER = True
# use Agg backend in notebooks or when Tkinter is not present
try:
get_ipython()
if not SPYDER:
matplotlib.use('Agg')
except:
try:
import Tkinter
except ImportError:
if not SPYDER:
matplotlib.use('Agg')
##############################################
# Ipython helpers
##############################################
# determine if we're running in IPython
__in_ipython = True
__plotly_enabled = False
if not SPYDER:
try:
get_ipython()
# init plotly notebook mode
try:
import plotly
plotly.offline.init_notebook_mode(connected=True)
__plotly_enabled = True
__default_plotting_engine = PLOTTING_ENGINE_PLOTLY
except:
warnings.warn("plotly could not be initialized. Unable to use Plotly for plotting.")
except:
__in_ipython = False
[docs]def inIPython():
""" Checks if tellurium is used in IPython.
Returns true if tellurium is being using in
an IPython environment, false otherwise.
:return: boolean
"""
global __in_ipython
return __in_ipython
[docs]def getDefaultPlottingEngine():
""" Get the default plotting engine.
Options are 'matplotlib' or 'plotly'.
:return:
"""
global __default_plotting_engine
return __default_plotting_engine
[docs]def setDefaultPlottingEngine(engine):
""" Set the default plotting engine. Overrides current value.
:param engine: A string describing which plotting engine to use. Valid values are 'matplotlib' and 'pyplot'.
"""
if engine not in [PLOTTING_ENGINE_PLOTLY,
PLOTTING_ENGINE_MATPLOTLIB]:
raise ValueError('Plotting engine is not supported: {}'.format(engine))
global __default_plotting_engine
__default_plotting_engine = engine
__save_plots_to_pdf = False # flag which decides if plotted to pdf
[docs]def setSavePlotsToPDF(value):
""" Sets whether plots should be saved to PDF. """
global __save_plots_to_pdf
__save_plots_to_pdf = value
##############################################
# Plotting helpers
##############################################
import matplotlib.pyplot as plt
# make this the default style for matplotlib
# plt.style.use('fivethirtyeight')
from .plotting import getPlottingEngineFactory as __getPlottingEngineFactory, plot, show
[docs]def getPlottingEngineFactory(engine=None):
global __save_plots_to_pdf
if engine is None:
engine = getDefaultPlottingEngine()
factory = __getPlottingEngineFactory(engine)
factory.save_plots_to_pdf = __save_plots_to_pdf
return factory
__plotting_engines = {}
[docs]def getPlottingEngine(engine=None):
global __plotting_engines
if engine is None:
engine = getDefaultPlottingEngine()
if not engine in __plotting_engines:
__plotting_engines[engine] = getPlottingEngineFactory(engine)()
return __plotting_engines[engine]
getPlottingEngineFactory.__doc__ = __getPlottingEngineFactory.__doc__
##############################################
# Remaining imports
##############################################
import roadrunner
try:
import tesedml as libsedml
except ImportError as e:
try:
import libsedml
except ImportError:
libsedml = None
roadrunner.Logger.log(roadrunner.Logger.LOG_WARNING, str(e))
warnings.warn("'libsedml' could not be imported", ImportWarning, stacklevel=2)
try:
try:
import tesbml as libsbml
except ImportError:
import libsbml
except ImportError as e:
libsbml = None
roadrunner.Logger.log(roadrunner.Logger.LOG_WARNING, str(e))
warnings.warn("'libsbml' could not be imported", ImportWarning, stacklevel=2)
try:
import phrasedml
except ImportError as e:
phrasedml = None
roadrunner.Logger.log(roadrunner.Logger.LOG_WARNING, str(e))
warnings.warn("'phrasedml' could not be imported", ImportWarning, stacklevel=2)
try:
import sbol
except ImportError as e:
sbol = None
warnings.warn("'pySBOL' could not be imported, cannot import/export SBOL files", ImportWarning, stacklevel=2)
try:
from sbml2matlab import sbml2matlab
except ImportError as e:
sbml2matlab = None
roadrunner.Logger.log(roadrunner.Logger.LOG_WARNING, str(e))
warnings.warn("'sbml2matlab' could not be imported", ImportWarning)
from . import teconverters
# ---------------------------------------------------------------------
# Group: Utility
# ---------------------------------------------------------------------
[docs]def getVersionInfo():
""" Returns version information for tellurium included packages.
:returns: list of tuples (package, version)
"""
versions = [
('tellurium', getTelluriumVersion()),
('roadrunner', roadrunner.__version__),
('antimony', antimony.__version__),
]
if libsbml:
versions.append(('libsbml', libsbml.getLibSBMLDottedVersion()))
if libsedml:
versions.append(('libsedml', libsedml.getLibSEDMLVersionString()))
if phrasedml:
versions.append(('phrasedml', phrasedml.__version__))
if sbol:
versions.append(('pySBOL', sbol.__version__))
return versions
[docs]def printVersionInfo():
""" Prints version information for tellurium included packages.
see also: :func:`getVersionInfo`
"""
versions = getVersionInfo()
for v in versions:
print(v[0], ':', v[1])
[docs]def getTelluriumVersion():
""" Version number of tellurium.
:returns: version
:rtype: str
"""
try:
with open(os.path.join(os.path.dirname(__file__), '..', 'VERSION.txt'), 'r') as f:
version = f.read().rstrip()
except:
with open(os.path.join(os.path.dirname(__file__), 'VERSION.txt'), 'r') as f:
version = f.read().rstrip()
return version
[docs]def noticesOff():
"""Switch off the generation of notices to the user.
Call this to stop roadrunner from printing warning message to the console.
See also :func:`noticesOn`
"""
roadrunner.Logger.setLevel(roadrunner.Logger.LOG_WARNING)
[docs]def noticesOn():
""" Switch on notice generation to the user.
See also :func:`noticesOff`
"""
roadrunner.Logger.setLevel(roadrunner.Logger.LOG_NOTICE)
# ---------------------------------------------------------------------
# Group: Loading Models
# ---------------------------------------------------------------------
__te_models = {}
def __set_model(model_name, rr):
__te_models[model_name] = rr
[docs]def model(model_name):
"""Retrieve a model which has already been loaded.
:param model_name: the name of the model
:type model_name: str
"""
if not model_name in __te_models:
raise KeyError('No such model has been loaded: {}'.format(model_name))
return __te_models[model_name]
def _checkAntimonyReturnCode(code):
""" Helper for checking the antimony response code.
Raises Exception if error in antimony.
:param code: antimony response
:type code: int
"""
if code < 0:
raise Exception('Antimony: {}'.format(antimony.getLastError()))
[docs]def colorCycle(color,polyNumber):
""" Adjusts contents of self.color as needed for plotting methods."""
if len(color) < polyNumber:
for i in range(polyNumber - len(color)):
color.append(color[i])
else:
for i in range(len(color) - polyNumber):
del color[-(i+1)]
return color
[docs]def sample_plot(result):
color = ['#0F0F3D', '#141452', '#1A1A66', '#1F1F7A', '#24248F', '#2929A3',
'#2E2EB8', '#3333CC', '#4747D1', '#5C5CD6']
if len(color) != result.shape[1]:
color = colorCycle(color,10)
for i in range(result.shape[1] - 1):
plt.plot(result[:, 0], result[:, i + 1], color=color[i],
linewidth=2.5, label="SomeLabel")
plt.xlabel('time')
plt.ylabel('concentration')
plt.suptitle("Sample Plot")
plt.legend()
plt.show()
[docs]def plotImage(img):
imgplot = plt.imshow(img)
plt.show()
plt.close()
[docs]def custom_plot(x, y, min_y,max_y, label_name , **kwargs):
ax = kwargs.pop('ax', plt.gca())
base_line, = ax.plot(x, y, label=label_name,**kwargs)
ax.fill_between(x, min_y, max_y, facecolor=base_line.get_color(), alpha=0.3)
# Now add the legend with some customizations.
[docs]def plot_stochastic_result(result):
plt.close()
if(len(result) < 1):
return
col_names = result[0][0]
sim_result = np.array([item[1] for item in result])
mean_result = sim_result.mean(0)
min_result = sim_result.min(0)
max_result = sim_result.max(0)
for col in range(1,len(col_names)):
X = mean_result[:,0]
Y = mean_result[:,col]
min_y = min_result[:,col]
max_y = max_result[:,col]
custom_plot(X,Y,min_y,max_y,col_names[col])
#plt.legend(bbox_to_anchor=(1.05, 1), loc=2, borderaxespad=0.)
plt.legend()
plt.show()
[docs]def distributed_stochastic_simulation(sc,stochastic_model_object, num_simulations, model_type="antimony"):
def stochastic_work(model_object):
import tellurium as te
if model_type == "antimony":
model_roadrunner = te.loada(model_object.model)
else:
model_roadrunner = te.loadSBMLModel(model_object.model)
model_roadrunner.integrator = model_object.integrator
# seed the randint method with the current time
random.seed()
# it is now safe to use random.randint
model_roadrunner.setSeed(random.randint(1000, 99999))
model_roadrunner.integrator.variable_step_size = model_object.variable_step_size
model_roadrunner.reset()
simulated_data = model_roadrunner.simulate(model_object.from_time, model_object.to_time, model_object.step_points)
return([simulated_data.colnames,np.array(simulated_data)])
return(sc.parallelize([stochastic_model_object]*num_simulations,num_simulations).map(stochastic_work).collect())
[docs]def plot_distributed_stochastic(plot_data):
fig = getPlottingEngine().newFigure(title='Stochastic Result')
for each_data in plot_data:
for i_column in range(1,len(each_data[0])):
name = each_data[0][i_column]
fig.addXYDataset([i_data[0] for i_data in each_data[1]],[i_data[i_column] for i_data in each_data[1]], name=name)
fig.plot()
[docs]def distributed_parameter_scanning(sc,list_of_models, function_name,antimony="antimony"):
def spark_work(model_with_parameters):
import tellurium as te
if(antimony == "antimony"):
model_roadrunner = te.loada(model_with_parameters[0])
else:
model_roadrunner = te.loadSBMLModel(model_with_parameters[0])
parameter_scan_initilisation = te.ParameterScan(model_roadrunner,**model_with_parameters[1])
simulator = getattr(parameter_scan_initilisation, function_name)
return(simulator())
return(sc.parallelize(list_of_models,len(list_of_models)).map(spark_work).collect())
[docs]def distributed_sensitivity_analysis(sc,senitivity_analysis_model,calculation=None):
def spark_sensitivity_analysis(model_with_parameters):
import tellurium as te
sa_model = model_with_parameters[0]
parameters = model_with_parameters[1]
class_name = importlib.import_module(sa_model.filename)
user_defined_simulator = getattr(class_name, dir(class_name)[0])
sa_model.simulation = user_defined_simulator()
if(sa_model.sbml):
model_roadrunner = te.loadAntimonyModel(te.sbmlToAntimony(sa_model.model))
else:
model_roadrunner = te.loadAntimonyModel(sa_model.model)
model_roadrunner.conservedMoietyAnalysis = sa_model.conservedMoietyAnalysis
#Running PreSimulation
model_roadrunner = sa_model.simulation.presimulator(model_roadrunner)
#Running Analysis
computations = {}
model_roadrunner = sa_model.simulation.simulator(model_roadrunner,computations)
_analysis = [None,None]
#Setting the Parameter Variables
_analysis[0] = {}
for i_param,param_names in enumerate(sa_model.bounds.keys()):
_analysis[0][param_names] = parameters[i_param]
setattr(model_roadrunner, param_names, parameters[i_param])
_analysis[1] = computations
return _analysis
if(senitivity_analysis_model.bounds is None):
print("Bounds are Undefined.")
return
#Get the Filename
sc.addPyFile(senitivity_analysis_model.filename)
senitivity_analysis_model.filename = os.path.basename(senitivity_analysis_model.filename).split(".")[0]
params = []
if(senitivity_analysis_model.allowLog):
for bound_values in senitivity_analysis_model.bounds.values():
if(len(bound_values) > 2):
params.append(np.logspace(bound_values[0], bound_values[1], bound_values[2]))
elif(len(bound_values == 2)):
params.append(np.logspace(bound_values[0], bound_values[1], 3))
else:
print("Improper Boundaries Defined")
return;
else:
for bound_values in senitivity_analysis_model.bounds.values():
if(len(bound_values) > 2):
params.append(np.linspace(bound_values[0], bound_values[1], bound_values[2]))
elif(len(bound_values == 2)):
params.append(np.linspace(bound_values[0], bound_values[1], 3))
else:
print("Improper Boundaries Defined")
return;
samples = perform_sampling(np.meshgrid(*params))
samples = zip([senitivity_analysis_model]*len(samples),samples)
if(calculation is "avg"):
group_rdd = sc.parallelize(samples,len(samples)).map(spark_sensitivity_analysis).\
flatMap(lambda x: x[1].items()).groupByKey()
KEYS = group_rdd.map(lambda x: (x[0])).collect()
VALUES = group_rdd.map(lambda x: np.array(list(x[1])))
values_array = np.array(VALUES.collect())
MEANS = (np.average(values_array, axis=1))
STD = (np.std(values_array, axis=1))
stats = {}
for key_i,each_key in enumerate(KEYS):
stats[each_key] = {}
stats[each_key]["mean"] = MEANS[key_i]
stats[each_key]["stdev"] = STD[key_i]
return stats
elif(type(calculation) is dict):
bins = sc.broadcast(calculation)
group_rdd = sc.parallelize(samples,len(samples)).map(spark_sensitivity_analysis)\
.flatMap(lambda x: x[1].items()).map(
lambda x: (x[0], [int(items[0] <= x[1] <= items[1]) for items in bins.value[x[0]]])).reduceByKey(
lambda first, second: [x + y for x, y in zip(first, second)])
return group_rdd.collect()
else:
return(sc.parallelize(samples,len(samples)).map(spark_sensitivity_analysis).collect())
[docs]def loada(ant):
"""Load model from Antimony string.
See also: :func:`loadAntimonyModel`
::
r = te.loada('S1 -> S2; k1*S1; k1=0.1; S1=10.0; S2 = 0.0')
:param ant: Antimony model
:type ant: str | file
:returns: RoadRunner instance with model loaded
:rtype: roadrunner.ExtendedRoadRunner
"""
return loadAntimonyModel(ant)
[docs]def loadAntimonyModel(ant):
"""Load Antimony model with tellurium.
See also: :func:`loada`
::
r = te.loadAntimonyModel('S1 -> S2; k1*S1; k1=0.1; S1=10.0; S2 = 0.0')
:param ant: Antimony model
:type ant: str | file
:returns: RoadRunner instance with model loaded
:rtype: roadrunner.ExtendedRoadRunner
"""
sbml = antimonyToSBML(ant)
return roadrunner.RoadRunner(sbml)
[docs]def loads(ant):
"""Load SBML model with tellurium
See also: :func:`loadSBMLModel`
:param ant: SBML model
:type ant: str | file
:returns: RoadRunner instance with model loaded
:rtype: roadrunner.ExtendedRoadRunner
"""
return loadSBMLModel(ant)
[docs]def loadSBMLModel(sbml):
""" Load SBML model from a string or file.
:param sbml: SBML model
:type sbml: str | file
:returns: RoadRunner instance with model loaded
:rtype: roadrunner.ExtendedRoadRunner
"""
return roadrunner.RoadRunner(sbml)
[docs]def loadCellMLModel(cellml):
""" Load CellML model with tellurium.
:param cellml: CellML model
:type cellml: str | file
:returns: RoadRunner instance with model loaded
:rtype: roadrunner.ExtendedRoadRunner
"""
sbml = cellmlToSBML(cellml)
return roadrunner.RoadRunner(sbml)
# ---------------------------------------------------------------------
# Interconversion Methods
# ---------------------------------------------------------------------
[docs]def antimonyTosbml(ant):
warnings.warn("'antimonyTosbml' is deprecated. Use 'antimonyToSBML' instead. Will be removed in tellurium v1.4",
DeprecationWarning, stacklevel=2)
return antimonyToSBML(ant)
[docs]def antimonyToSBML(ant):
""" Convert Antimony to SBML string.
:param ant: Antimony string or file
:type ant: str | file
:return: SBML
:rtype: str
"""
if os.path.isfile(ant):
code = antimony.loadAntimonyFile(ant)
else:
code = antimony.loadAntimonyString(ant)
_checkAntimonyReturnCode(code)
mid = antimony.getMainModuleName()
return antimony.getSBMLString(mid)
[docs]def antimonyToCellML(ant):
""" Convert Antimony to CellML string.
:param ant: Antimony string or file
:type ant: str | file
:return: CellML
:rtype: str
"""
if os.path.isfile(ant):
code = antimony.loadAntimonyFile(ant)
else:
code = antimony.loadAntimonyString(ant)
_checkAntimonyReturnCode(code)
mid = antimony.getMainModuleName()
return antimony.getCellMLString(mid)
[docs]def sbmlToAntimony(sbml):
""" Convert SBML to antimony string.
:param sbml: SBML string or file
:type sbml: str | file
:return: Antimony
:rtype: str
"""
isfile = False
try:
isfile = os.path.isfile(sbml)
except:
pass
if isfile:
code = antimony.loadSBMLFile(sbml)
else:
code = antimony.loadSBMLString(str(sbml))
_checkAntimonyReturnCode(code)
return antimony.getAntimonyString(None)
[docs]def sbmlToCellML(sbml):
""" Convert SBML to CellML string.
:param sbml: SBML string or file
:type sbml: str | file
:return: CellML
:rtype: str
"""
if os.path.isfile(sbml):
code = antimony.loadSBMLFile(sbml)
else:
code = antimony.loadSBMLString(sbml)
_checkAntimonyReturnCode(code)
return antimony.getCellMLString(None)
[docs]def cellmlToAntimony(cellml):
""" Convert CellML to antimony string.
:param cellml: CellML string or file
:type cellml: str | file
:return: antimony
:rtype: str
"""
if os.path.isfile(cellml):
code = antimony.loadCellMLFile(cellml)
else:
code = antimony.loadCellMLString(cellml)
_checkAntimonyReturnCode(code)
return antimony.getAntimonyString(None)
[docs]def cellmlToSBML(cellml):
""" Convert CellML to SBML string.
:param cellml: CellML string or file
:type cellml: str | file
:return: SBML
:rtype: str
"""
if os.path.isfile(cellml):
code = antimony.loadCellMLFile(cellml)
else:
code = antimony.loadCellMLString(cellml)
_checkAntimonyReturnCode(code)
return antimony.getSBMLString(None)
[docs]def exportInlineOmex(inline_omex, export_location):
""" Export an inline OMEX string to a COMBINE archive.
:param inline_omex: String containing inline OMEX describing models and simulations.
:param export_location: Filepath of Combine archive to create.
"""
from .teconverters import saveInlineOMEX
saveInlineOMEX(inline_omex, export_location)
[docs]def executeInlineOmex(inline_omex):
""" Execute inline phrasedml and antimony.
:param inline_omex: String containing inline phrasedml and antimony.
"""
in_omex = teconverters.inlineOmex.fromString(inline_omex)
in_omex.executeOmex()
[docs]def executeInlineOmexFromFile(filepath):
""" Execute inline OMEX with simulations described in phrasedml and models described in antimony.
:param filepath: Path to file containing inline phrasedml and antimony.
"""
with open(filepath) as f:
executeInlineOmex(f.read())
[docs]def convertCombineArchive(location):
""" Read a COMBINE archive and convert its contents to an
inline Omex.
:param location: Filesystem path to the archive.
"""
from .teconverters import inlineOmexImporter
return inlineOmexImporter.fromFile(location).toInlineOmex()
[docs]def convertAndExecuteCombineArchive(location):
""" Read and execute a COMBINE archive.
:param location: Filesystem path to the archive.
"""
from .teconverters import inlineOmexImporter
inlineomex = inlineOmexImporter.fromFile(location).toInlineOmex()
executeInlineOmex(inlineomex)
# ---------------------------------------------------------------------
# Math Utilities
# ---------------------------------------------------------------------
[docs]def getEigenvalues(m):
""" Eigenvalues of matrix.
Convenience method for computing the eigenvalues of a matrix m
Uses numpy eig to compute the eigenvalues.
:param m: numpy array
:returns: numpy array containing eigenvalues
"""
from numpy import linalg
w, v = linalg.eig(m)
return w
# ---------------------------------------------------------------------
# Plotting Utilities
# ---------------------------------------------------------------------
[docs]def plotArray(result, loc='upper right', show=True, resetColorCycle=True,
xlabel=None, ylabel=None, title=None, xlim=None, ylim=None,
xscale='linear', yscale="linear", grid=False, labels=None, **kwargs):
""" Plot an array.
The first column of the array must be the x-axis and remaining columns the y-axis. Returns
a handle to the plotting object. Note that you can add plotting options as named key values after
the array. To add a legend, include the label legend values:
te.plotArray (m, labels=['Label 1, 'Label 2', etc])
Make sure you include as many labels as there are curves to plot!
Use show=False to add multiple curves. Use color='red' to use the same color for every curve.
::
import numpy as np
result = np.array([[1,2,3], [7.2,6.5,8.8], [9.8, 6.5, 4.3]])
te.plotArray(result, title="My graph', xlim=((0, 5)))
"""
warnings.warn("plotArray is deprecated, use plot instead", DeprecationWarning)
# FIXME: unify r.plot & te.plot (lots of code duplication)
# reset color cycle (columns in repeated simulations have same color)
if resetColorCycle:
plt.gca().set_prop_cycle(None)
if 'linewidth' not in kwargs:
kwargs['linewidth'] = 2.0
# get the labeles
Ncol = result.shape[1]
if labels is None:
labels = result.dtype.names
for k in range(1, Ncol):
if loc is None or labels is None:
# no legend or labels
p = plt.plot(result[:, 0], result[:, k], **kwargs)
else:
p = plt.plot(result[:, 0], result[:, k], label=labels[k-1], **kwargs)
# labels
if xlabel is not None:
plt.xlabel(xlabel)
if ylabel is not None:
plt.ylabel(ylabel)
if title is not None:
plt.title(title)
if xlim is not None:
plt.xlim(xlim)
if ylim is not None:
plt.ylim(ylim)
# axis and grids
plt.xscale(xscale)
plt.yscale(yscale)
plt.grid(grid)
# show legend
if loc is not None and labels is not None:
plt.legend(loc=loc)
# show plot
if show:
plt.show()
return p
[docs]def plotWithLegend(r, result=None, loc='upper left', show=True, **kwargs):
warnings.warn("'plotWithLegend' is deprecated. Use 'r.plot' instead. Will be removed in tellurium v1.4",
DeprecationWarning, stacklevel=2)
return r.plot(result=result, loc=loc, show=show, **kwargs)
# ---------------------------------------------------------------------
# Test Models
# ---------------------------------------------------------------------
[docs]def loadTestModel(string):
"""Loads particular test model into roadrunner.
::
rr = te.loadTestModel('feedback.xml')
:returns: RoadRunner instance with test model loaded
"""
import roadrunner.testing
return roadrunner.testing.getRoadRunner(string)
[docs]def getTestModel(string):
"""SBML of given test model as a string.
::
# load test model as SBML
sbml = te.getTestModel('feedback.xml')
r = te.loadSBMLModel(sbml)
# simulate
r.simulate(0, 100, 20)
:returns: SBML string of test model
"""
import roadrunner.testing
return roadrunner.testing.getData(string)
[docs]def listTestModels():
""" List roadrunner SBML test models.
::
print(te.listTestModels())
:returns: list of test model paths
"""
import roadrunner.testing
modelList = []
fileList = roadrunner.testing.dir('*.xml')
for pathName in fileList:
modelList.append(os.path.basename(pathName))
return modelList
# ---------------------------------------------------------------
# Extended roadrunner
# ---------------------------------------------------------------
from .roadrunner import ExtendedRoadRunner
def _model_function_factory(key):
""" Dynamic creation of model functions.
:param key: function key, i.e. the name of the function
:type key: str
:return: function object
:rtype: function
"""
def f(self):
return getattr(self.model, key).__call__()
# set the name
f.__name__ = key
# copy the docstring
f.__doc__ = getattr(roadrunner.ExecutableModel, key).__doc__
return f
# Add model functions to ExendedRoadRunner class
for key in ExtendedRoadRunner._model_functions:
setattr(ExtendedRoadRunner, key, _model_function_factory(key))
# Now we assign the ExtendedRoadRunner to RoadRunner
[docs]def RoadRunner(*args):
# return roadrunner.RoadRunner(*args)
return ExtendedRoadRunner(*args)
roadrunner.RoadRunner = ExtendedRoadRunner
[docs]def VersionDict():
'''Return dict of version strings.'''
import tesbml, tesedml, tecombine
return {
'tellurium': getTelluriumVersion(),
'roadrunner': roadrunner.getVersionStr(roadrunner.VERSIONSTR_BASIC),
'antimony': antimony.__version__,
'phrasedml': phrasedml.__version__,
'tesbml': libsbml.getLibSBMLDottedVersion(),
'tesedml': tesedml.__version__,
'tecombine': tecombine.__version__
}
[docs]def DumpJSONInfo():
'''Tellurium dist info. Goes into COMBINE archive.'''
return json.dumps({
'authoring_tool': 'tellurium',
'info': 'Created with Tellurium (tellurium.analogmachine.org).',
'version_info': VersionDict()})
[docs]def getAppDir():
import os
from sys import platform
if platform == "linux" or platform == "linux2":
return os.path.join(os.path.expanduser('~'), '.config', 'Tellurium')
else:
import appdirs
return appdirs.user_data_dir('Tellurium', 'Tellurium')
_last_report = None
[docs]def setLastReport(report):
'''Used by SED-ML to save the last report created (for validation).'''
global _last_report
_last_report = report
[docs]def getLastReport():
'''Get the last report generated by SED-ML.'''
global _last_report
return _last_report
from .testcases import getSupportedTestCases