Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

adding gem_tools #6598

Merged
merged 16 commits into from
Dec 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 25 additions & 0 deletions tools/gem_tools/.shed.yml
emikar marked this conversation as resolved.
Show resolved Hide resolved
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
name: gem_tools
owner: iuc
categories:
- Metabolomics
- Systems Biology
- Synthetic Biology
description: "Tools for analyzing genome-scale metabolic models (GEMs) using COBRApy and related libraries."
long_description: |
This repository contains a collection of Galaxy tools for performing various analyses on genome-scale
metabolic models (GEMs). The tools leverage COBRApy and other Python libraries to provide functionalities
such as phenotype phase plane analysis, gene knockout analysis, flux variability analysis, and more.
homepage_url: https://github.com/AlmaasLab/elixir-galaxy-tools-systemsbiology
remote_repository_url: https://github.com/AlmaasLab/elixir-galaxy-tools-systemsbiology
type: unrestricted
license: GNU GENERAL PUBLIC LICENSE
auto_tool_repositories:
name_template: "{{ tool_id }}"
description_template: "Wrapper for the gem_tools tool suite: {{ tool_name }}"
suite:
name: "suite_gem_tools"
description: "A suite of tools for analyzing genome-scale metabolic models (GEMs) using COBRApy and related libraries."
long_description: |
This repository contains a collection of Galaxy tools for performing various analyses on genome-scale metabolic models (GEMs).
The tools leverage COBRApy and other Python libraries to provide functionalities such as phenotype phase plane analysis, gene
knockout analysis, flux variability analysis, and more.
69 changes: 69 additions & 0 deletions tools/gem_tools/gem_check_memote.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
<tool id="gem_check_memote" name="Make GEM quality report" version="@VERSION@" profile="@PROFILE@">
<description>
using memote
</description>
<macros>
<import>gem_macros.xml</import>
</macros>
<expand macro="requirements"/>
<expand macro="version_command_memote"/>
<command>
memote report snapshot
'${cb_model_location}'
--filename '${output}'
</command>
<inputs>
<expand macro="input_model"/>
</inputs>
<outputs>
<data name="output" format="html" label="${tool.name} on ${on_string}"/>
</outputs>
<tests>
<!-- Test 1: Valid E. coli core model -->
<test>
<param name="cb_model_location" value="textbook_model_cobrapy.xml"/>
<output name="output">
<assert_contents>
<has_text text="Stoichiometric Consistency"/>
</assert_contents>
</output>
</test>
<!-- Test 2: Invalid model format -->
<test expect_failure="true">
<param name="cb_model_location" value="invalid_format.txt"/>
<assert_stderr>
<has_text text="Most likely the SBML model is not valid"/>
</assert_stderr>
</test>
</tests>
<help><![CDATA[
Memote Model Quality Check

The GEM Check Memote tool runs the Memote test suite to generate a detailed report on the quality of a genome-scale metabolic model (GEM). Memote assesses various model characteristics such as stoichiometric consistency and model annotations.

Inputs

`Model to check with memote`: The metabolic model in SBML format (.xml or .sbml) to be analyzed by Memote. Ensure the file conforms to SBML standards.

Outputs

`Memote report`: An HTML file that contains the full results of the Memote assessment. This report includes overall model quality scores and highlights any issues that need correction.

Usage Example

1. Upload your SBML model file.
2. Run the tool to generate the Memote report.
3. Review the report to identify any errors or areas for improvement in the model.

Troubleshooting

If the tool fails to run, ensure that your input file is a valid SBML model. Incorrect file formats or non-compliant models may trigger errors.

References

Full documentation and further examples can be found at: https://doi.org/10.1038/s41587-020-0446-y
]]></help>
<citations>
<expand macro="citation_memote"/>
</citations>
</tool>
233 changes: 233 additions & 0 deletions tools/gem_tools/gem_escher_visualization.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,233 @@
import argparse

import cobra
import pandas as pd
from escher import Builder


def __main__():
parser = argparse.ArgumentParser(
prog="EscherVisualization",
description="This program visualizes an Escher map",
epilog="Adding an epilog, but doubt it's needed.",
)
parser.add_argument(
"-m",
"--cb_model_location",
dest="cb_model_location",
action="store",
type=str,
default=None,
required=False,
help="The model to use."
)
parser.add_argument(
"-f",
"--flux_distribution_location",
dest="flux_distribution_location",
action="store",
type=str,
default=None,
required=False,
help="The flux distribution to visualize."
)
parser.add_argument(
"-e",
"--expect_map",
dest="expect_map",
action="store",
type=str,
default=None,
required=True,
help="Is a map expected to be uploaded?"
)
parser.add_argument(
"-l",
"--model_to_download",
dest="model_to_download",
action="store",
type=str,
default=None,
required=False,
help="The model to download."
)
parser.add_argument(
"--map_load_name",
dest="map_load_name",
action="store",
type=str,
default=None,
required=False,
help="The name of the map to use."
)
parser.add_argument(
"--map_upload_name",
dest="map_upload_name",
action="store",
type=str,
default=None,
required=False,
help="The name of the map to use."
)
parser.add_argument(
"-u",
"--uptake_constraints_file",
dest="uptake_constraints_file",
action="store",
type=str,
default=None,
required=False,
help="File containing new uptake constraits."
)
parser.add_argument(
"-output",
"--output",
dest="out_file",
action="store",
type=str,
default=None,
required=True,
help="The output file."
)

args = parser.parse_args()

if args.expect_map not in ["True", "False"]:
raise Exception("The expect_map argument must be either True or False.")
if args.expect_map == "True" and args.map_load_name is None and \
args.map_upload_name is None:
raise Exception(
"You must specify a map name if a map is expected to be uploaded."
)

cb_model = None
model_name = None
if args.model_to_download is not None and args.model_to_download != "None":
if args.cb_model_location is not None \
and args.cb_model_location != "None":
raise Exception(
"You cannot specify both a model to "
"download and a model to use."
)
model_name = args.model_to_download
elif args.cb_model_location is not None\
and args.cb_model_location != "None":
try:
cb_model = cobra.io.read_sbml_model(args.cb_model_location)
except Exception as e:
raise Exception(
"The model could not be read. "
"Ensure it is in correct SBML format."
) from e

map_name = None
map_location = None
if args.map_upload_name is not None and args.map_upload_name != "None":
if args.map_load_name is not None and args.map_load_name != "None":
raise Exception(
"You cannot specify both a map to upload and a map to load."
)
map_location = args.map_upload_name
elif args.map_load_name is not None and args.map_load_name != "None":
map_name = args.map_load_name

if args.uptake_constraints_file is not None and \
args.uptake_constraints_file != "None":
if cb_model is None:
raise Exception(
"You cannot specify uptake constraints "
"without uploading a model."
)
else:
constraints_df = pd.read_csv(
args.uptake_constraints_file,
sep=";",
header=0,
index_col=False
)
for index, row in constraints_df.iterrows():
rxn_id = row["reaction_id"]
cb_model.reactions.get_by_id(rxn_id).lower_bound = \
row["lower_bound"]
cb_model.reactions.get_by_id(rxn_id).upper_bound = \
row["upper_bound"]

flux_dict = None
if args.flux_distribution_location is not None and \
args.flux_distribution_location != "None":
if cb_model is None:
raise Exception(
"You cannot specify a flux distribution "
"without uploading a model."
)
if args.uptake_constraints_file is not None and \
args.uptake_constraints_file != "None":
raise Exception(
"You cannot specify both uptake constraints and a flux "
"distribution."
)
try:
flux_df = pd.read_csv(
args.flux_distribution_location,
sep=";",
header=0,
index_col=False
)
flux_dict = {
key: value for key, value in zip(
flux_df['reaction_name'],
flux_df['flux']
)
}
except Exception as e:
raise Exception(
"The flux distribution file could not be read. "
"Ensure the file has semicolon-separated "
"columns and a header row."
) from e

if cb_model is not None and flux_dict is None:
solution = cobra.flux_analysis.pfba(cb_model)

# make a dataframe with the reaction names, reaction ids, and flux
flux_distribution = pd.DataFrame(
columns=["reaction_name", "reaction_id", "flux"]
)
flux_distribution["reaction_name"] = [
reaction.name for reaction in cb_model.reactions
]
flux_distribution["reaction_id"] = [
reaction.id for reaction in cb_model.reactions
]
flux_distribution["flux"] = [
solution.fluxes[reaction.id] for reaction in cb_model.reactions
]
flux_dict = {
key: value for key, value in zip(
flux_distribution['reaction_name'],
flux_distribution['flux']
)
}

builder = Builder()
if map_name is not None:
builder.map_name = map_name
print("Downloading map...")
if map_location is not None:
builder.map_json = map_location
print("Uploading map...")
if model_name is not None:
builder.model_name = model_name
print("Downloading model...")
if cb_model is not None:
builder.model = cb_model
print("Uploading model...")

if flux_dict is not None:
builder.reaction_data = flux_dict

builder.save_html(args.out_file)


if __name__ == "__main__":
__main__()
Loading
Loading