"""Control of the application runtime
Example of use:
.. code-block:: python
import SofaRuntime
SofaRuntime.importPlugin("Sofa.Component.LinearSolver")
"""
import SofaRuntime.SofaRuntime as cpp
import Sofa
import sys
import os
import inspect
import traceback
import importlib
###############################################################################
###################### MODULES INPORTS & UNLOAD FEATURES ######################
###############################################################################
# Keep a list of the modules always imported in the Sofa-PythonEnvironment
try:
__SofaPythonEnvironment_importedModules__
except:
__SofaPythonEnvironment_importedModules__ = sys.modules.copy()
# some modules could be added here manually and can be modified procedurally
# e.g. plugin's modules defined from c++
__SofaPythonEnvironment_modulesExcludedFromReload = []
[docs]def importPlugin(a):
""" Import a plugin"""
return cpp.importPlugin(a)
[docs]def unloadModules():
""" call this function to unload python modules and to force their reload
(useful to take into account their eventual modifications since
their last import).
"""
global __SofaPythonEnvironment_importedModules__
toremove = [name for name in sys.modules if not name in __SofaPythonEnvironment_importedModules__ and not name in __SofaPythonEnvironment_modulesExcludedFromReload ]
for name in toremove:
del(sys.modules[name]) # unload it
################################################################
###################### CALLSTACK FEATURES ######################
################################################################
[docs]def getStackForSofa():
"""returns the current stack with a "informal" formatting. """
## we exclude the first level in the stack because it is the getStackForSofa() function itself.
ss=inspect.stack()[1:]
return formatStackForSofa(ss)
[docs]def getPythonCallingPointAsString():
"""returns the last entry with an "informal" formatting. """
## we exclude the first level in the stack because it is the getStackForSofa() function itself.
ss=inspect.stack()[-1:]
return formatStackForSofa(ss)
[docs]def getPythonCallingPoint():
"""returns the tupe with closest filename & line. """
## we exclude the first level in the stack because it is the getStackForSofa() function itself.
ss=inspect.stack()[1]
tmp=(os.path.abspath(ss[1]), ss[2])
return tmp
#############################################################################
###################### EXCEPTION HANDLING (NECESSARY?) ######################
#############################################################################
[docs]def sendMessageFromException(e):
exc_type, exc_value, exc_tb = sys.exc_info()
sofaExceptHandler(exc_type, exc_value, exc_tb)
[docs]def sofaExceptHandler(type, value, tb):
global oldexcepthook
"""This exception handler, convert python exceptions & traceback into more classical sofa error messages of the form:
Message Description
Python Stack (most recent are at the end)
File file1.py line 4 ...
File file1.py line 10 ...
File file1.py line 40 ...
File file1.py line 23 ...
faulty line
"""
h = type.__name__
if str(value) != '':
h += ': ' + str(value)
s = "Traceback (most recent call last):\n"
s += ''.join(traceback.format_tb(tb))
Sofa.msg_error("SofaRuntime", h + '\n' + s)
sys.excepthook=sofaExceptHandler