def test_read_sbml_from_str() -> None: """Read SBML str.""" doc1 = read_sbml(str(BASIC_SBML)) sbml_str = write_sbml(doc1) doc = read_sbml(sbml_str) assert doc assert doc.getModel()
def test_read_sbml_from_gzstr(): """Read SBML str.""" doc1 = read_sbml(str(GZ_SBML)) sbml_str = write_sbml(doc1) doc = read_sbml(sbml_str) assert doc assert doc.getModel()
def annotate_sbml( source: Union[Path, str], annotations_path: Path, filepath: Path ) -> libsbml.SBMLDocument: """ Annotate a given SBML file with the provided annotations. :param source: SBML to annotation :param annotations_path: external file with annotations :param filepath: annotated SBML file :return: annotated SBMLDocument """ doc: libsbml.SBMLDocument = read_sbml(source=source) # annotate if not os.path.exists(str(annotations_path)): raise IOError(f"Annotation file does not exist: {annotations_path}") external_annotations = ModelAnnotator.read_annotations( annotations_path, file_format="*" ) doc = annotate_sbml_doc(doc, external_annotations) # type: ignore # write annotated sbml write_sbml(doc, filepath=filepath) console.print(f"Model annotated: file://{filepath}", style="success") return doc
def test_model_annotation(tmp_path: Path) -> None: """Create minimal model and check that annotation is written correctly.""" model_dict = { "mid": "example_annotation", "compartments": [ Compartment( sid="C", value=1.0, sboTerm=SBO_PHYSICAL_COMPARTMENT, annotations=[ (BQB.IS, "chebi/CHEBI:28061"), # alpha-D-galactose ], ) ], } results = create_model(model_dict, output_dir=tmp_path, filename="annotation1.xml") # check annotations doc: libsbml.SBMLDocument = read_sbml(source=results.sbml_path) model: libsbml.Model = doc.getModel() compartment: libsbml.Compartment = model.getCompartment(0) assert compartment cvterms: libsbml.CVTermList = compartment.getCVTerms() assert len(cvterms) == 1 cv: libsbml.CVTerm = cvterms[0] assert cv.getNumResources() == 1
def test_write_sbml(tmp_path): doc = libsbml.SBMLDocument() # type: libsbml.SBMLDocument model = doc.createModel() # type: libsbml.Model model.setId("test_id") sbml_path = tmp_path / "test.xml" write_sbml(doc=doc, filepath=sbml_path) assert sbml_path.exists() doc2 = read_sbml(source=sbml_path) assert doc2 assert doc2.getModel()
def test_mass_balance(tmp_path): doc = read_sbml(DEMO_SBML) # add defaults add_default_flux_bounds(doc) filepath = tmp_path / "test.xml" write_sbml(doc, filepath=filepath) model = read_cobra_model(filepath) # mass/charge balance for r in model.reactions: mb = r.check_mass_balance() # all metabolites are balanced assert len(mb) == 0
def fba_model(sbml_file, directory): """ Create FBA submodel. """ # Read the model fba_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'data/iAB_RBC_283.xml') doc_fba = sbml.read_sbml(fba_path) # add comp doc_fba.enablePackage( "http://www.sbml.org/sbml/level3/version1/comp/version1", "comp", True) doc_fba.setPackageRequired("comp", True) # add notes model = doc_fba.getModel() fba_notes = notes.format("""DFBA FBA submodel.""") utils.set_model_info(model, notes=fba_notes, creators=None, units=units, main_units=main_units) # clip R_ reaction and M_ metabolite prefixes utils.clip_prefixes_in_model(model) # set id & framework model.setId('{}_fba'.format(settings.MODEL_ID)) model.setName('{} (FBA)'.format(settings.MODEL_ID)) model.setSBOTerm(comp.SBO_FLUX_BALANCE_FRAMEWORK) # add units and information for species in model.getListOfSpecies(): species.setInitialConcentration(0.0) species.setHasOnlySubstanceUnits(False) species.setUnits(UNIT_AMOUNT) for compartment in model.getListOfCompartments(): compartment.setUnits(UNIT_VOLUME) # update the existing exchange reactions builder.update_exchange_reactions(model, flux_unit=UNIT_FLUX) # write SBML file sbml.write_sbml(doc_fba, filepath=pjoin(directory, sbml_file), validate=True) return doc_fba
def test_report_uncertainty_example(tmp_path: Path) -> None: """Test creation of report to check uncertainty feature""" doc = read_sbml( source=TESTSUITE_PATH / "distrib" / "testsuite" / "uncertainty.xml", promote=True, validate=True, log_errors=True, units_consistency=True, modeling_practice=True, ) model = doc.getModel() model_info = sbmlinfo.SBMLModelInfo(doc=doc, model=model, math_render="cmathml") assert isinstance(model_info.info, Dict) params_info = model_info.info["parameters"] assert isinstance(params_info, List) param = params_info[0] uncertainties = param["uncertainties"] assert isinstance(uncertainties, List) first_uncertainty = uncertainties[0] assert first_uncertainty["metaId"] == "<code>meta_uncertainty1</code>" assert first_uncertainty["cvterm"] == ( '<div class="cvterm"><span class="collection">BQB_IS_DESCRIBED_BY</span>' + '<br /><a href="https://identifiers.org/pubmed/123456" target="_blank">' + '123456</a><br /><span class="collection">BQB_HAS_PROPERTY</span><br />' + '<a href="http://purl.obolibrary.org/obo/ECO_0006016" target="_blank">' + "ECO_0006016</a></div>" ) assert first_uncertainty["name"] == "Basic example: 5.0 +- 0.3 [2.0 - 8.0]" uncert_parameters = first_uncertainty["uncert_parameters"] assert isinstance(uncert_parameters, List) first_uncert_param = uncert_parameters[0] assert first_uncert_param["value"] == 5.0 assert first_uncert_param["units"] == "mole" assert first_uncert_param["type"] == "mean"
def test_read_sbml_from_path(): """Read from path.""" doc = read_sbml(BASIC_SBML) assert doc assert doc.getModel()
def test_read_sbml_validate(): """Read and validate.""" doc = read_sbml(BASIC_SBML, validate=True) assert doc assert doc.getModel()
def test_read_sbml_from_strpath(): """Read from strpath (os.path).""" doc = read_sbml(str(BASIC_SBML)) assert doc assert doc.getModel()
def create_report( sbml_path: Path, output_dir: Path, promote: bool = False, template: str = "report.html", math_type: str = "cmathml", validate: bool = True, log_errors: bool = True, units_consistency: bool = True, modeling_practice: bool = True, ) -> str: """Create HTML report and return the content as a variable. The SBML file can be validated during report generation. Local parameters can be promoted during report generation. :param sbml_path: path to SBML file :param output_dir: target directory where the SBML file is written :param promote: boolean flag to promote local parameters :param template: which template file to use for rendering :param math_type: specifies the math rendering mode for the report :param validate: boolean flag if SBML file be validated (warnings and errors are logged) :param log_errors: boolean flag of errors should be logged :param units_consistency: boolean flag units consistency :param modeling_practice: boolean flag modeling practise :return: string variable containing content of the generated HTML report """ # validate and check arguments _check_report_math_type(math_type) if not isinstance(sbml_path, Path): logger.warning(f"All paths should be of type 'Path', " f"but '{type(sbml_path)}' found for: {sbml_path}") sbml_path = Path(sbml_path) if not isinstance(output_dir, Path): logger.warning(f"All paths should be of type 'Path', " f"but '{type(output_dir)}' found for: {output_dir}") output_dir = Path(output_dir) if not sbml_path.exists(): raise IOError(f"'sbml_path' does not exist: '{sbml_path}'") if not output_dir.exists(): raise IOError(f"'output_dir' does not exist: '{output_dir}'") if not output_dir.is_dir(): raise IOError(f"'output_dir' is not a directory: '{output_dir}'") # read sbml doc = read_sbml( source=sbml_path, promote=promote, validate=validate, log_errors=log_errors, units_consistency=units_consistency, modeling_practice=modeling_practice, ) # write sbml basename = sbml_path.name write_sbml(doc, filepath=output_dir / basename) # write html html = _create_html(doc, basename, html_template=template, math_type=math_type) return html
def fba_model(sbml_file, directory): """ Create FBA submodel. """ # Read the model fba_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'data/ecoli_fba.xml') doc_fba = sbml.read_sbml(fba_path) # add comp doc_fba.enablePackage( "http://www.sbml.org/sbml/level3/version1/comp/version1", "comp", True) doc_fba.setPackageRequired("comp", True) # add notes model = doc_fba.getModel() fba_notes = notes.format("""DFBA FBA submodel.""") utils.set_model_info(model, notes=fba_notes, creators=None, units=units, main_units=main_units) # clip R_ reaction and M_ metabolite prefixes utils.clip_prefixes_in_model(model) # set id & framework model.setId('ecoli_fba') model.setName('ecoli (FBA)') model.setSBOTerm(comp.SBO_FLUX_BALANCE_FRAMEWORK) # add units and information for species in model.getListOfSpecies(): species.setInitialConcentration(0.0) species.setHasOnlySubstanceUnits(False) species.setUnits(UNIT_AMOUNT) for compartment in model.getListOfCompartments(): compartment.setUnits(UNIT_VOLUME) # The ATPM (atp maintainance reactions creates many problems in the DFBA) # mainly resulting in infeasible solutions when some metabolites run out. # ATP -> ADP is part of the biomass, so we set the lower bound to zero r_ATPM = model.getReaction('ATPM') r_ATPM_fbc = r_ATPM.getPlugin(builder.SBML_FBC_NAME) lb_id = r_ATPM_fbc.getLowerFluxBound() model.getParameter(lb_id).setValue(0.0) # 8.39 before # make unique upper and lower bounds for exchange reaction if not biomass_weighting: builder.update_exchange_reactions(model=model, flux_unit=UNIT_FLUX) else: builder.update_exchange_reactions(model=model, flux_unit=UNIT_FLUX_PER_G) # add exchange reaction for biomass (X) # we are adding the biomass component to the biomass function and create an # exchange reaction for it r_biomass = model.getReaction('BIOMASS_Ecoli_core_w_GAM') # FIXME: refactor in function # FIXME: annotate biomass species (SBO for biomass missing) mc.create_objects(model, [ mc.Parameter(sid='cf_X', value=1.0, unit="g_per_mmol", name="biomass conversion factor", constant=True), mc.Species(sid='X', initialAmount=0.001, compartment='c', name='biomass', substanceUnit='g', hasOnlySubstanceUnits=True, conversionFactor='cf_X') ]) pr_biomass = r_biomass.createProduct() pr_biomass.setSpecies('X') pr_biomass.setStoichiometry(1.0) pr_biomass.setConstant(True) # FIXME: the flux units must fit to the species units. if not biomass_weighting: builder.create_exchange_reaction(model, species_id='X', flux_unit=UNIT_FLUX, exchange_type=builder.EXCHANGE_EXPORT) else: builder.create_exchange_reaction(model, species_id='X', flux_unit=UNIT_FLUX_PER_G, exchange_type=builder.EXCHANGE_EXPORT) # write SBML file sbml.write_sbml(doc_fba, filepath=pjoin(directory, sbml_file), validate=True) # Set kinetic laws to zero for kinetic simulation ''' for reaction in model.getListOfReactions(): ast_node = mc.ast_node_from_formula(model=model, formula='0 {}'.format(UNIT_FLUX)) law = reaction.createKineticLaw() law.setMath(ast_node) ''' return doc_fba
def test_demo_annotation(tmp_path): """ Annotate the demo network. """ tmp_sbml_path = tmp_path / "sbml_annotated.xml" annotator.annotate_sbml( DEMO_SBML_NO_ANNOTATIONS, DEMO_ANNOTATIONS, filepath=tmp_sbml_path ) # document doc = read_sbml(source=tmp_sbml_path) assert doc.getSBOTerm() == 293 assert doc.getSBOTermID() == "SBO:0000293" cvterms = doc.getCVTerms() # check: is one cv term with 3 resources in bag assert len(cvterms) == 1 assert cvterms[0].getNumResources() == 1 # model model = doc.getModel() cvterms = model.getCVTerms() assert len(cvterms) == 0 # compartments ce = model.getCompartment("e") assert ce.getSBOTerm() == 290 assert ce.getSBOTermID() == "SBO:0000290" cvterms = ce.getCVTerms() # check: is one cv term with 3 resources in bag assert len(cvterms) == 1 assert cvterms[0].getNumResources() == 3 cm = model.getCompartment("m") assert cm.getSBOTerm() == 290 assert cm.getSBOTermID() == "SBO:0000290" cvterms = cm.getCVTerms() assert len(cvterms) == 1 assert cvterms[0].getNumResources() == 3 cc = model.getCompartment("c") assert cc.getSBOTerm() == 290 assert cc.getSBOTermID() == "SBO:0000290" cvterms = cm.getCVTerms() assert len(cvterms) == 1 assert cvterms[0].getNumResources() == 3 # parameters for p in model.parameters: cvterms = p.getCVTerms() if re.match(r"^Km_\w+$", p.id): assert p.getSBOTerm() == 27 assert p.getSBOTermID() == "SBO:0000027" assert len(cvterms) == 1 if re.match(r"^Keq_\w+$", p.id): assert p.getSBOTerm() == 281 assert p.getSBOTermID() == "SBO:0000281" assert len(cvterms) == 1 if re.match(r"^Vmax_\w+$", p.id): assert p.getSBOTerm() == 186 assert p.getSBOTermID() == "SBO:0000186" assert len(cvterms) == 1 # species for s in model.species: cvterms = s.getCVTerms() if re.match(r"^\w{1}__[ABC]$", s.id): assert s.getSBOTerm() == 247 assert s.getSBOTermID() == "SBO:0000247" assert len(cvterms) == 1 # reactions for r in model.reactions: cvterms = r.getCVTerms() if re.match(r"^b\w{1}$", r.id): assert r.getSBOTerm() == 185 assert r.getSBOTermID() == "SBO:0000185" assert len(cvterms) == 1 if re.match(r"^v\w{1}$", r.id): assert r.getSBOTerm() == 176 assert r.getSBOTermID() == "SBO:0000176" assert len(cvterms) == 1 # fbc:geneProduct modelFBCPlugin = model.getPlugin("fbc") for geneProduct in modelFBCPlugin.getListOfGeneProducts(): if geneProduct.getId() == "PSHA_RS08100": cvterms = geneProduct.getCVTerms() assert len(cvterms) == 1
def create_report( sbml_path: Path, output_dir: Path, promote: bool = False, template: str = "report.html", validate: bool = True, log_errors: bool = True, units_consistency: bool = True, modeling_practice: bool = True, ): """Creates HTML report for SBML file. The SBML file can be validated during report generation. Local parameters can be promoted during report generation. :param sbml_path: path to SBML file :param output_dir: target directory where the report is written :param promote: boolean flag to promote local parameters :param template: which template file to use for rendering :param validate: boolean flag if SBML file be validated (warnings and errors are logged) :param log_errors: boolean flag of errors should be logged :param units_consistency: boolean flag units consistency :param modeling_practice: boolean flag modeling practise :return: """ if not isinstance(sbml_path, Path): logger.warning( f"All paths should be of type 'Path', but '{type(sbml_path)}' found for: {sbml_path}" ) sbml_path = Path(sbml_path) if not isinstance(output_dir, Path): logger.warning( f"All paths should be of type 'Path', but '{type(output_dir)}' found for: {output_dir}" ) output_dir = Path(output_dir) # check paths if not sbml_path.exists(): raise IOError(f"'sbml_path' does not exist: '{sbml_path}'") if not output_dir.exists(): raise IOError(f"'output_dir' does not exist: '{output_dir}'") if not output_dir.is_dir(): raise IOError(f"'output_dir' is not a directory: '{output_dir}'") # read sbml doc = read_sbml( source=sbml_path, promote=promote, validate=validate, log_errors=log_errors, units_consistency=units_consistency, modeling_practice=modeling_practice, ) # write sbml to report directory basename = sbml_path.name name = ".".join(basename.split(".")[:-1]) write_sbml(doc, filepath=output_dir / basename) # write html (unicode) html = _create_html(doc, basename, html_template=template) path_html = output_dir / f"{name}.html" # FIXME: ist this still necessary f_html = codecs.open(path_html, encoding="utf-8", mode="w") f_html.write(html) f_html.close() logger.info(f"SBML report created: '{path_html.resolve()}'")