public class CompFlatteningConverter extends SBMLConverter
This class of objects is defined by libSBML only and has no direct equivalent in terms of SBML components. It is a class used in the implementation of extra functionality provided by libSBML.
This converter translates a hierarchical model defined with the SBML
Level 3 Hierarchical Model Composition package to a so-called
'flattened' version of the same model. A 'flattened' model is one that
results from interpreting the hierarchical structure and creating an
equivalent model that does not use any Hierarchical Model Composition
package constructs all of the mathematics of the model remain as
intended, but the hierarchical structure is removed.
CompFlatteningConverter
achieves this by performing the following actions
on a model:
Model
object
referenced by every Submodel
object is created. This is a recursive
process: if the instantiated Model
itself has Submodel
children, they are
also instantiated.
Model
that is
instantiated is modified by prepending a prefix to it, to make the
identifier unique in the overall flattened SBML model. The prefix
consists of the Submodel
object identifier, plus a small integer if
necessary to ensure uniqueness, plus two underscore characters
('__'
). Typically, this results in a final identifier of the
form SubmodelIdentifier__ObjectIdentifier, where ObjectIdentifier is the object's original
identifier and SubmodelIdentifier__ is
the prefix. The same process is applied to metaid (meta-identifier)
values of every component object as well.
Model
object this Model
object is made the new child of the SBMLDocument
container. The original
Model
, ModelDefinition
, and ExternalModelDefinition
objects are all
deleted.
Note an implication of this process is that if conversion is successful,
all old pointers to the SBMLDocument
object's Model
object as well as all
of its children, will be rendered obsolete, and will no longer work.
CompFlatteningConverter
CompFlatteningConverter
is enabled by creating a ConversionProperties
object with the option 'flatten comp', and passing this
ConversionProperties
object to SBMLDocument.convert(ConversionProperties)
. The CompFlatteningConverter
converter
accepts numerous options influencing its behavior. The following list
briefly summarizes the options:
'true'
or 'false'.
Setting the option to true
(the default) means enable the flattening
converter.
'all'
, @c
'requiredOnly' (the default), or 'none'.
Controls what happens upon
encountering an SBML Level 3 package with no flattener
implementation.
'true'
or @c
'false' (the default). Controls whether the constructs of Level 3
packages with no flattener implementation are stripped from the output.
ExternalModelDefinition
objects.
(Default value: '.', meaning, the current directory.)
'true'
or 'false'
(the
default). Controls what happens to Port
constructs in the output.
'true'
or @c
'false' (the default). Controls what happens to ModelDefinition
and
ExternalModelDefinition
objects in the final output.
'true'
(the default)
or 'false'.
Controls whether whether libSBML validates the model
before attempting to flatten it.
The following sections examine in detail the options understood by
CompFlatteningConverter
and their effects on the flattening process.
If other SBML Level 3 packages are used in the SBMLDocument
, the same
rules apply to each package's constructs if an implementation of the
flattener exists for that Level 3 package. If no implementation
exists, the behavior of this CompFlatteningConverter
depends on the values
of the options 'abortIfUnflattenable' and
'stripUnflattenablePackages'. Specifically:
'all'
, then if any
construct is found for a package that has no flattening algorithm
available, the converter will abort, return failure, and avoid
changing the original SBMLDocument
object.
'requiredOnly'
(the default),
then if any SBML Level 3 package construct is found for a package
that is labeled 'required=true'
and for which no flattening
algorithm is available, the converter will abort, return failure, and
avoid changing the original SBMLDocument
object. SBML Level 3
package constructs from packages set 'required=false'
for which no
flattening algorithm is implemented will be ignored and the constructs
will be kept or removed depending on the value of the
'stripUnflattenablePackages' option described below.
'none'
, constructs from all
unflattenable SBML Level 3 packages will be ignored, and their
constructs will be kept or removed depending on the value of the
'stripUnflattenablePackages' option.
'true'
, and
the option 'abortIfUnflattenable' has the value 'requiredOnly'
or 'none'
, then CompFlatteningConverter
will remove all constructs
belonging to packages that lack a flattening converter. The XML
namespace declaration for unflattenable SBML Level 3 packages
will also be removed.
'false'
(the default), CompFlatteningConverter
will leave any package
constructs that cannot be flattened due to the lack of a flattening
implementation. These Level 3 package constructs will remain in
the final model. Note that any package constructs from an
instantiated Submodel
object that was not a child of a retained
component will be lost (because the SBML component where it was
located was removed from the final, flattened model).
CompFlatteningConverter
The following are other, general options offered by CompFlatteningConverter:
ExternalModelDefinition
objects that are to
be instantiated in a flattened Submodel
, the 'basePath' option may
be set to a location where those external models may be found. The
default is the working directory ('.'
).
'false'
(the default), the
flattened model will have no Port
objects in it. Conversely, if
'leavePorts' is set to 'true'
, any Port
objects not referenced by any
Replacement or Deletion
will be left in the resulting flattened Model
.
'false'
(the
default), no ModelDefinition
or ExternalModelDefinition
objects will
be present in the flattened SBMLDocument
. If 'listModelDefinitions'
is set to 'true'
, they will remain, although they will no longer be
referenced by any Submodel
in the flattened Model
child of the
SBMLDocument
.
'true'
(the
default), the SBMLDocument
will first be validated before flattening
is attempted. If there are any validation errors, those errors will
be logged with the SBMLDocument
, which will remain otherwise
unchanged, and the conversion process will return a failure code.
Similarly, if the flattened Model
is not valid, those validation
errors will be added to the SBMLDocument
, which will remain otherwise
unchanged, and the conversion attempt will return failure.
Conversely, if the option 'performValidation' is set to @c
'false', the SBMLDocument
will be flattened regardless of any
validation errors. The conversion may yet fail if insurmountable
errors are encountered in the course of trying to flatten the model
(for instance, if an element is replaced by something that does not
exist), but no separate validation steps are performed.
Note that if both the option 'leavePorts' and 'listModelDefinitions'
are set to 'false'
(which they are by default), the Hierarchical Model
Composition namespace will be removed from the resulting SBMLDocument
.
CompFlatteningConverter
In this section, we present a complete example of a program that can take
an SBML model containing Level 3 Hierarchical Model Composition
constructs and flatten it to a plain SBML Level 3 model.
A version of this program is available in the libSBML distribution's
examples/java/comp
directory as the
program named
'flattenModel.java'
. The example
XML models shown below are the same models as given in sections
4.1&ndash4.2 in the specification document for SBML Level 3
Hierarchical Model Composition.
For brevity, we do not give the general scaffolding that a real program would have (such as inclusion of header files, command-line argument checks, additional error checks throughout the code, and so on), and focus instead on the parts relevant to an application using the libSBML 'comp' extension.
First, our program checks that this copy of libSBML has the 'comp' extension available. The process for doing that simply involves a call to the extension registry in libSBML:
if (! SBMLExtensionRegistry
.isPackageEnabled('comp'))
{
System.out.println('This copy of libSBML does not contain the 'comp' extension')
System.out.println('Unable to proceed with flattening the model.')
System.exit(1)
}
Next, we read the SBML input file. For this example, we simply assume that the path to the file is given as the first argument to the program a real program would perform more sophisticated command-line argument processing and error checking.
SBMLReader
reader = newSBMLReader
()SBMLDocument
doc = reader.readSBML(args[0]) if (doc.getErrorLog().getNumFailsWithSeverity(libsbml.LIBSBML_SEV_ERROR) > 0) { doc.printErrors() System.exit(1) }
Continuing, we set up options for the call to the converter.
The use of ConversionProperties
and the general scheme behind
conversion options is explained further below for the purposes
of this example, it is enough to know that the following are the
basic lines of code needed to obtain a copy of a libSBML
converter object that will invoke CompFlatteningConverter:
ConversionProperties
props = newConversionProperties
() props.addOption('flatten comp', true)
Now comes the actual invocation of CompFlatteningConverter
.
As always, it is critical to check for possible errors by
checking the status code returned by the call we do this
in the code below too.
if (doc.convert(props) != libsbml.LIBSBML_OPERATION_SUCCESS) { doc.printErrors() System.exit(1) }
If successful, we simply write out the resulting flattened model to an output file which, for the purposes of this simple example, we assume is indicated by the second argument handed to the program on the command line by the user.
SBMLWriter
writer = newSBMLWriter
() writer.writeSBML(doc, args[1])
What is the result of the above on an actual model? Suppose we
have the following SBML Level 3 model stored in a file named
'enzyme_model.xml':
<?xml version="1.0" encoding="UTF-8"?>
<sbml xmlns="http://www.sbml.org/sbml/level3/version1/core" level="3" version="1"
xmlns:comp="http://www.sbml.org/sbml/level3/version1/comp/version1" comp:required="true">
<model id="aggregate">
<comp:listOfSubmodels>
<comp:submodel comp:id="submod1" comp:modelRef="enzyme"/>
<comp:submodel comp:id="submod2" comp:modelRef="enzyme"/>
</comp:listOfSubmodels>
</model>
<comp:listOfModelDefinitions>
<comp:modelDefinition id="enzyme" name="enzyme">
<listOfCompartments>
<compartment id="compartment" spatialDimensions="3" size="1" constant="true"/>
</listOfCompartments>
<listOfSpecies>
<species id="S" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="E" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="D" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="ES" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
</listOfSpecies>
<listOfReactions>
<reaction id="J0" reversible="true" fast="false">
<listOfReactants>
<speciesReference species="S" stoichiometry="1" constant="true"/>
<speciesReference species="E" stoichiometry="1" constant="true"/>
</listOfReactants>
<listOfProducts>
<speciesReference species="ES" stoichiometry="1" constant="true"/>
</listOfProducts>
</reaction>
<reaction id="J1" reversible="true" fast="false">
<listOfReactants>
<speciesReference species="ES" stoichiometry="1" constant="true"/>
</listOfReactants>
<listOfProducts>
<speciesReference species="E" stoichiometry="1" constant="true"/>
<speciesReference species="D" stoichiometry="1" constant="true"/>
</listOfProducts>
</reaction>
</listOfReactions>
</comp:modelDefinition>
</comp:listOfModelDefinitions>
</sbml>
Also suppose we have the following SBML Level 3 model stored
in a file called 'main.xml'
in the same directory as the
file above. The model below imports the model 'enzyme'
from
the model file above twice this is used to create two submodels
whose identifiers are 'A'
and 'B'.
<?xml version="1.0" encoding="UTF-8"?>
<sbml xmlns="http://www.sbml.org/sbml/level3/version1/core" level="3" version="1"
xmlns:comp="http://www.sbml.org/sbml/level3/version1/comp/version1" comp:required="true">
<model>
<listOfCompartments>
<compartment id="compartment" spatialDimensions="3" size="1" constant="true">
<comp:listOfReplacedElements>
<comp:replacedElement comp:idRef="compartment" comp:submodelRef="A"/>
<comp:replacedElement comp:idRef="compartment" comp:submodelRef="B"/>
</comp:listOfReplacedElements>
</compartment>
</listOfCompartments>
<listOfSpecies>
<species id="S" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false">
<comp:listOfReplacedElements>
<comp:replacedElement comp:idRef="S" comp:submodelRef="A"/>
<comp:replacedElement comp:idRef="S" comp:submodelRef="B"/>
</comp:listOfReplacedElements>
</species>
</listOfSpecies>
<comp:listOfSubmodels>
<comp:submodel comp:id="A" comp:modelRef="ExtMod1"/>
<comp:submodel comp:id="B" comp:modelRef="ExtMod1"/>
</comp:listOfSubmodels>
</model>
<comp:listOfExternalModelDefinitions>
<comp:externalModelDefinition comp:id="ExtMod1" comp:source="enzyme_model.xml"
comp:modelRef="enzyme"/>
</comp:listOfExternalModelDefinitions>
</sbml>
Finally, invoking the example program developed the previous section on the
file 'main.xml'
, we would obtain the following XML output as result a
result
<?xml version="1.0" encoding="UTF-8"?>
<sbml xmlns="http://www.sbml.org/sbml/level3/version1/core" level="3" version="1">
<model>
<listOfCompartments>
<compartment id="compartment" spatialDimensions="3" size="1" constant="true"/>
</listOfCompartments>
<listOfSpecies>
<species id="S" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="A__E" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="A__D" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="A__ES" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="B__E" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="B__D" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
<species id="B__ES" compartment="compartment" hasOnlySubstanceUnits="false"
boundaryCondition="false" constant="false"/>
</listOfSpecies>
<listOfReactions>
<reaction id="A__J0" reversible="true" fast="false">
<listOfReactants>
<speciesReference species="S" stoichiometry="1" constant="true"/>
<speciesReference species="A__E" stoichiometry="1" constant="true"/>
</listOfReactants>
<listOfProducts>
<speciesReference species="A__ES" stoichiometry="1" constant="true"/>
</listOfProducts>
</reaction>
<reaction id="A__J1" reversible="true" fast="false">
<listOfReactants>
<speciesReference species="A__ES" stoichiometry="1" constant="true"/>
</listOfReactants>
<listOfProducts>
<speciesReference species="A__E" stoichiometry="1" constant="true"/>
<speciesReference species="A__D" stoichiometry="1" constant="true"/>
</listOfProducts>
</reaction>
<reaction id="B__J0" reversible="true" fast="false">
<listOfReactants>
<speciesReference species="S" stoichiometry="1" constant="true"/>
<speciesReference species="B__E" stoichiometry="1" constant="true"/>
</listOfReactants>
<listOfProducts>
<speciesReference species="B__ES" stoichiometry="1" constant="true"/>
</listOfProducts>
</reaction>
<reaction id="B__J1" reversible="true" fast="false">
<listOfReactants>
<speciesReference species="B__ES" stoichiometry="1" constant="true"/>
</listOfReactants>
<listOfProducts>
<speciesReference species="B__E" stoichiometry="1" constant="true"/>
<speciesReference species="B__D" stoichiometry="1" constant="true"/>
</listOfProducts>
</reaction>
</listOfReactions>
</model>
</sbml>
The final model is a concrete realization of the effective
model defined by 'main.xml'
, with a single compartment and two
reactions the species 'S'
can either bind with enzyme 'E'
(from
submodel 'A'
) to form 'D'
(from submodel 'A'
), or with enzyme
'E'
(from submodel 'B'
) to form 'D'
(from submodel 'B'
).
In the flattened model above, note how the identifiers of components
inside the ModelDefinition
objects 'A'
and 'B'
of our file @c
'enzyme_model.xml' have been rewritten as (for example) 'A__E'
@c
'B__E', etc.
The use of all the converters follows a similar approach. First, one
creates a ConversionProperties
object and calls
ConversionProperties.addOption(ConversionOption)
on this object with one arguments: a text string that identifies the desired
converter. (The text string is specific to each converter consult the
documentation for a given converter to find out how it should be enabled.)
Next, for some converters, the caller can optionally set some
converter-specific properties using additional calls to
ConversionProperties.addOption(ConversionOption)
.
Many converters provide the ability to
configure their behavior to some extent this is realized through the use
of properties that offer different options. The default property values
for each converter can be interrogated using the method
SBMLConverter.getDefaultProperties()
on the converter class in question .
Finally, the caller should invoke the method
SBMLDocument.convert(ConversionProperties)
with the ConversionProperties
object as an argument.
The following code fragment illustrates an example using
SBMLReactionConverter
, which is invoked using the option string
'replaceReactions':
ConversionProperties
props = newConversionProperties
() if (props != null) { props.addOption('replaceReactions') } else { // Deal with error. }
In the case of SBMLReactionConverter
, there are no options to affect
its behavior, so the next step is simply to invoke the converter on
an SBMLDocument
object. Continuing the example code:
// Assume that the variable 'document' has been set to an SBMLDocument
object.
status = document.convert(config)
if (status != libsbml.LIBSBML_OPERATION_SUCCESS)
{
// Handle error somehow.
System.out.println('Error: conversion failed due to the following:')
document.printErrors()
}
Here is an example of using a converter that offers an option. The
following code invokes SBMLStripPackageConverter
to remove the
SBML Level 3 Layout package from a model. It sets the name
of the package to be removed by adding a value for the option named
'package'
defined by that converter:
ConversionProperties
config = newConversionProperties
() if (config != None) { config.addOption('stripPackage') config.addOption('package', 'layout') status = document.convert(config) if (status != LIBSBML_OPERATION_SUCCESS) { // Handle error somehow. System.out.println('Error: unable to strip theLayout
package') document.printErrors() } } else { // Handle error somehow. System.out.println('Error: unable to createConversionProperties
object') }
LibSBML provides a number of built-in converters by convention, their names end in Converter. The following are the built-in converters provided by libSBML 5.13.0 :
CobraToFbcConverter
CompFlatteningConverter
FbcToCobraConverter
FbcV1ToV2Converter
FbcV2ToV1Converter
SBMLFunctionDefinitionConverter
SBMLIdConverter
SBMLInferUnitsConverter
SBMLInitialAssignmentConverter
SBMLLevel1Version1Converter
SBMLLevelVersionConverter
SBMLLocalParameterConverter
SBMLReactionConverter
SBMLRuleConverter
SBMLStripPackageConverter
SBMLUnitsConverter
Constructor and Description |
---|
CompFlatteningConverter()
Creates a new
CompFlatteningConverter object. |
CompFlatteningConverter(CompFlatteningConverter orig)
Copy constructor.
|
Modifier and Type | Method and Description |
---|---|
SBMLConverter |
cloneObject()
Creates and returns a deep copy of this
CompFlatteningConverter . |
int |
convert()
Performs the conversion.
|
void |
delete()
Explicitly deletes the underlying native object.
|
ConversionProperties |
getDefaultProperties()
Returns the default properties of this converter.
|
boolean |
matchesProperties(ConversionProperties props)
Returns
true if this converter matches the given properties. |
getDocument, getName, getProperties, getTargetNamespaces, setDocument, setProperties
public CompFlatteningConverter()
CompFlatteningConverter
object.public CompFlatteningConverter(CompFlatteningConverter orig)
This creates a copy of a CompFlatteningConverter
object.
orig
- the CompFlatteningConverter
instance to copy.public void delete()
In general, application software will not need to call this method directly. The Java language binding for libSBML is implemented as a language wrapper that provides a Java interface to libSBML's underlying C++/C code. Some of the Java methods return objects that are linked to objects created not by Java code, but by C++ code. The Java objects wrapped around them will be deleted when the garbage collector invokes the corresponding C++ finalize()
methods for the objects. The finalize()
methods in turn call the CompFlatteningConverter.delete()
method on the libSBML object.
This method is exposed in case calling programs want to ensure that the underlying object is freed immediately, and not at some arbitrary time determined by the Java garbage collector. In normal usage, callers do not need to invoke CompFlatteningConverter.delete()
themselves.
delete
 in class SBMLConverter
public SBMLConverter cloneObject()
CompFlatteningConverter
.
cloneObject
 in class SBMLConverter
CompFlatteningConverter
.public boolean matchesProperties(ConversionProperties props)
true
if this converter matches the given properties.
Given a ConversionProperties
object props
, this method checks that @p
props possesses an option value to enable the CompFlatteningConverter
. If
it does, this method returns true.
matchesProperties
 in class SBMLConverter
props
- the properties to match.
true
if the properties props
would match the necessary
properties for CompFlatteningConverter
type of converter, false
otherwise.public int convert()
This method causes CompFlatteningConverter
to do the actual conversion
work, that is, to convert the SBMLDocument
object set by
SBMLConverter.setDocument(SBMLDocument)
and with
the configuration options set by SBMLConverter.setProperties(ConversionProperties)
.
convert
 in class SBMLConverter
public ConversionProperties getDefaultProperties()
A given converter exposes one or more properties that can be adjusted in
order to influence the behavior of the converter. This method returns
the default property settings for CompFlatteningConverter
. It is
meant to be called in order to be able to programmatically discover all
the settings for the converter object.
CompFlatteningConverter
is enabled by creating a ConversionProperties
object with the option 'flatten comp', and passing this
ConversionProperties
object to SBMLDocument.convert(ConversionProperties)
. The CompFlatteningConverter
converter
accepts numerous options influencing its behavior. The following list
briefly summarizes the options:
'true'
or 'false'.
Setting the option to true
(the default) means enable the flattening
converter.
'all'
, @c
'requiredOnly' (the default), or 'none'.
Controls what happens upon
encountering an SBML Level 3 package with no flattener
implementation.
'true'
or @c
'false' (the default). Controls whether the constructs of Level 3
packages with no flattener implementation are stripped from the output.
ExternalModelDefinition
objects.
(Default value: '.', meaning, the current directory.)
'true'
or 'false'
(the
default). Controls what happens to Port
constructs in the output.
'true'
or @c
'false' (the default). Controls what happens to ModelDefinition
and
ExternalModelDefinition
objects in the final output.
'true'
(the default)
or 'false'.
Controls whether whether libSBML validates the model
before attempting to flatten it.
getDefaultProperties
 in class SBMLConverter
ConversionProperties
object describing the default properties
for this converter.
SBMLConverter.setProperties(ConversionProperties)
,
SBMLConverter.matchesProperties(ConversionProperties)
CompFlatteningConverter
also offered an
'ignorePackages' option, whose name proved to be confusing. This option
has been deprecated and replaced by the 'stripUnflattenablePackages'
option.