Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
f868dd1
Revert mistaken merge (#209)
JoshLoecker Dec 13, 2024
941e073
chore(deps): bump astral-sh/ruff-action from 2 to 3 (#213)
dependabot[bot] Jan 6, 2025
fdfd0ec
chore(deps): bump astral-sh/setup-uv from 4 to 5
dependabot[bot] Jan 6, 2025
6d74649
Merge pull request #212 from HelikarLab/dependabot/github_actions/ast…
JoshLoecker Jan 6, 2025
2779e83
hotfix: log full name of directory if not found
JoshLoecker Sep 22, 2025
60d0908
fix: log specific file, not directory
JoshLoecker Oct 2, 2025
73d96eb
fix: compute counts, means, and mean fragments outside loop
JoshLoecker Oct 2, 2025
b2e8f38
Merge remote-tracking branch 'origin/develop' into preprocess-hotfix
JoshLoecker Oct 2, 2025
ca189c8
fix(ruff): fix lint errors
JoshLoecker Oct 2, 2025
de94fce
fix(ruff): fix import
JoshLoecker Oct 2, 2025
7ee044a
style(ruff): automatic formatting
JoshLoecker Oct 2, 2025
bc5a4d4
style: format code, Jupyter Notebook(s), and Python imports with `ruff`
JoshLoecker Oct 2, 2025
feb0a27
style(ruff): increase line length
JoshLoecker Oct 2, 2025
bdf7910
Merge remote-tracking branch 'origin/preprocess-hotfix' into preproce…
JoshLoecker Oct 2, 2025
cee3f5a
style(ruff): increase line length
JoshLoecker Oct 2, 2025
012d422
style: format code, Jupyter Notebook(s), and Python imports with `ruff`
JoshLoecker Oct 2, 2025
dd40225
chore: retrigger checks
JoshLoecker Oct 2, 2025
6a8d6a9
Merge branch 'preprocess-hotfix' of github.com:HelikarLab/COMO into p…
JoshLoecker Oct 2, 2025
e9660bc
fix(ruff): lint error
JoshLoecker Oct 2, 2025
8a5989a
fix(ruff): fix lint errors
JoshLoecker Oct 2, 2025
6d408e6
fix(ruff): fix lint errors
JoshLoecker Oct 2, 2025
015f9be
style: format code, Jupyter Notebook(s), and Python imports with `ruff`
JoshLoecker Oct 2, 2025
b523822
chore: retrigger checks
JoshLoecker Oct 2, 2025
75b8dd1
fix(ruff): fix RUF043
JoshLoecker Oct 2, 2025
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
54 changes: 27 additions & 27 deletions main/COMO.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@
" 3. Compare results between perturbed and unperturbed models (i.e., knocked-out models vs non-knocked-out models)\n",
" 4. Integrate with disease genes and create a score of drug targets"
],
"id": "ea1c9614518c30bc"
"id": "90fba8b56a999517"
},
{
"metadata": {},
Expand Down Expand Up @@ -223,7 +223,7 @@
" </tbody>\n",
"</table>"
],
"id": "28d59417491e63db"
"id": "dcc8d38caab63fab"
},
{
"metadata": {},
Expand Down Expand Up @@ -254,7 +254,7 @@
"scrna_matrix_filepath = {context: Path(f\"data/results/{context}/scrna/scrna_{context}.csv\") for context in context_names}\n",
"# scrna_matrix_filepath = [Path(f\"data/results/{context}/scrna/scrna_{context}.h5ad\") for context in context_names]\n"
],
"id": "18061578964ca096"
"id": "fd4c387eab48e9ee"
},
{
"metadata": {},
Expand All @@ -266,7 +266,7 @@
"- `taxon_id`: The [NCBI Taxon ID](https://www.ncbi.nlm.nih.gov/taxonomy) to use\n",
"- `preprocess_mode`: This should be set to `\"create-matrix\"` if you are **not** providing a matrix, otherwise set it to `\"provide-matrix\"`"
],
"id": "b475e41b000d0cb5"
"id": "24a8475316ff6d70"
},
{
"metadata": {},
Expand All @@ -291,7 +291,7 @@
" log_level=\"INFO\",\n",
" )"
],
"id": "dbfb32f2a0f7b8ef"
"id": "cb04960f17cc9b75"
},
{
"metadata": {},
Expand Down Expand Up @@ -324,7 +324,7 @@
"\n",
"This method is not recommended, as zFPKM is much more robust for a similar level of \"hands-off\" model building\n"
],
"id": "a820a3985a2601c7"
"id": "4bd864328c93b27a"
},
{
"metadata": {},
Expand All @@ -345,7 +345,7 @@
"#### Single Cell RNA Sequencing\n",
"While the Snakemake pipeline does not yet support single-cell alignment, and COMO does not yet support automated configuration file and counts matrix file creation for single-cell alignment output from STAR, it is possible to use single-cell data to create a model with COMO. Because normalization strategies can be applied to single-cell data in the same way it is applied to bulk RNA sequencing, `como/rnaseq_gen.py` can be used with a provided counts matrix and configuration file, from [Step 1](Step-1:-Initialize-and-Preprocess-RNA-seq-data), above. Just like `\"total\"` and `\"mRNA\"`, `como/rnaseq_gen.py` can be executed with `\"SC\"` as the \"`--library-prep`\" argument to help COMO differentiate it from any bulk RNA sequencing data if multiple strategies are being used."
],
"id": "a1d6608d045c7399"
"id": "e99e612919298aa8"
},
{
"metadata": {},
Expand All @@ -364,7 +364,7 @@
"- `min_zfpkm`: The cutoff for Counts-Per-Million filtering\n",
"- `prep_method`: The library method used for preparation. Options are: `\"total\"`, `\"mRNA\"`, or `\"SC\"`,\n"
],
"id": "1fcf38e9cbc3de48"
"id": "8e550961a4a443b3"
},
{
"metadata": {},
Expand Down Expand Up @@ -400,7 +400,7 @@
" cutoff=cutoff\n",
" )"
],
"id": "5a2e17b646d6de36"
"id": "d98c023e7738eb64"
},
{
"metadata": {},
Expand All @@ -420,7 +420,7 @@
"- `min_zfpkm`: The cutoff for Counts-Per-Million filtering\n",
"- `prep_method`: The library method used for preparation. Options are: `\"total\"`, `\"mRNA\"`, or `\"SC\"`,\n"
],
"id": "87b5397301541650"
"id": "28848c3d315fa78c"
},
{
"metadata": {},
Expand Down Expand Up @@ -456,7 +456,7 @@
" cutoff=cutoff\n",
" )"
],
"id": "3e73c07fa4a9e49a"
"id": "3e87f9890bc76e43"
},
{
"metadata": {},
Expand All @@ -476,7 +476,7 @@
"- `min_zfpkm`: The cutoff for Counts-Per-Million filtering\n",
"- `prep_method`: The library method used for preparation. Options are: `\"total\"`, `\"mRNA\"`, or `\"scrna\"`,\n"
],
"id": "ae1278480199f415"
"id": "bfa9e2cd4152f961"
},
{
"metadata": {},
Expand Down Expand Up @@ -512,7 +512,7 @@
" cutoff=cutoff\n",
" )"
],
"id": "567734d827571d6f"
"id": "c45085c6c12d9a3c"
},
{
"metadata": {},
Expand All @@ -529,7 +529,7 @@
"- `high_batch_ratio`: The ratio required before a gene is considered \"high-confidence\" in the study\n",
"- `quantile`: The cutoff Transcripts-Per-Million quantile for filtering"
],
"id": "ea7004d23807dd1"
"id": "f01f21670b1e6956"
},
{
"metadata": {},
Expand All @@ -556,7 +556,7 @@
" quantile=25,\n",
" )"
],
"id": "a7715d2cf9b0191a"
"id": "dcbae45189dd2eba"
},
{
"metadata": {},
Expand All @@ -582,7 +582,7 @@
"- `n_neighbors_context`: N nearest neighbors for context clustering. The default is `\"default\"`, which is the total number of contexts\n",
"- `seed`: The random seed for clustering algorithm initialization. If not specified, `np.random.randint(0, 100000)` is used"
],
"id": "f4f395e25eeb1185"
"id": "354abde9f52ff9cf"
},
{
"metadata": {},
Expand Down Expand Up @@ -626,7 +626,7 @@
"\n",
"!{cmd}"
],
"id": "cc61326b8df01fc4"
"id": "be527c98a8523323"
},
{
"metadata": {},
Expand Down Expand Up @@ -666,7 +666,7 @@
"\n",
"Each of the \"weights\" (`total_rna_weight`, `mrna_weight`, etc.) are used to place a significance on each method. Becuase there are many steps in the Dogma from transcription to translation, the gene expression as seen by total RNA or mRNA sequencing may not be representative of the gene's protein expression, and this its metabolic impact. Because of this, you are able to weight each source more (or less) than another."
],
"id": "236fb36fa41f60b"
"id": "db0cfbec103d7d35"
},
{
"metadata": {},
Expand Down Expand Up @@ -703,7 +703,7 @@
"\n",
"!{cmd}"
],
"id": "3ce78fc277c55885"
"id": "75b84df4d88d7cbe"
},
{
"metadata": {},
Expand Down Expand Up @@ -770,7 +770,7 @@
"- `force_reactions_filename`: The filename of the force reactions to be used. Force reactions will (as the name implies) force the optimizer to use these reactions, **no matter their expression**\n",
"- `exclude_reactions_filename`: The filename of reactions to exclude from the model, no matter their expression"
],
"id": "b3a182617ff3eb7a"
"id": "30da70d405a80d23"
},
{
"metadata": {},
Expand Down Expand Up @@ -839,7 +839,7 @@
" # fmt: on\n",
" !{cmd}"
],
"id": "e94c36e65ba46e38"
"id": "19918f482629d4fe"
},
{
"metadata": {},
Expand All @@ -864,7 +864,7 @@
"- `exampleTissue`: This is the name of the tissue context\n",
"- `ALGORITHM`: This is the algorithm (`recon_algorithm`) used in the above model creation step\n"
],
"id": "47e3e576b43a040d"
"id": "38640adc60fe1909"
},
{
"metadata": {},
Expand Down Expand Up @@ -941,7 +941,7 @@
"\n",
" !{cmd}"
],
"id": "4a064f3322a3991e"
"id": "ef639305627a4a4"
},
{
"metadata": {},
Expand All @@ -960,7 +960,7 @@
"- `data_source`: The datasource you are using for disease analysis. This should be`\"rnaseq\"`\n",
"- `taxon_id`: The [NCBI Taxon ID](https://www.ncbi.nlm.nih.gov/taxonomy) to use for disease analysis"
],
"id": "3aa49b19ab4fc4b9"
"id": "ad06b9e81d3d5f39"
},
{
"metadata": {},
Expand Down Expand Up @@ -992,7 +992,7 @@
"\n",
" !{cmd}"
],
"id": "7f946d38cac3a18c"
"id": "c9d0e6dfd35adefb"
},
{
"metadata": {},
Expand Down Expand Up @@ -1027,7 +1027,7 @@
"\n",
"- `solver`: The solver you would like to use. Available options are `\"gurobi\"` or `\"glpk\"`\n"
],
"id": "feb9da60acb9a3b3"
"id": "7093fbd5a6551c18"
},
{
"metadata": {},
Expand Down Expand Up @@ -1099,7 +1099,7 @@
" cmd = \" \".join(cmd)\n",
" !{cmd}"
],
"id": "c999b3f953381f9f"
"id": "281a24eba5e06fc9"
}
],
"metadata": {},
Expand Down
12 changes: 3 additions & 9 deletions main/como/cluster_rnaseq.py
Original file line number Diff line number Diff line change
Expand Up @@ -57,19 +57,13 @@ def __post_init__(self): # noqa: C901, ignore too complex
if 0 > self.min_distance > 1.0:
raise ValueError("--min_dist must be a float between 0 and 1")

if (
isdigit(self.num_replicate_neighbors) and self.num_replicate_neighbors < 1
) or self.num_replicate_neighbors != "default":
if (isdigit(self.num_replicate_neighbors) and self.num_replicate_neighbors < 1) or self.num_replicate_neighbors != "default":
raise ValueError("--n-neighbors-rep must be either 'default' or an integer > 1")

if (
isdigit(self.num_batch_neighbors) and self.num_batch_neighbors < 1
) or self.num_batch_neighbors != "default":
if (isdigit(self.num_batch_neighbors) and self.num_batch_neighbors < 1) or self.num_batch_neighbors != "default":
raise ValueError("--n-neighbors-batch must be either 'default' or an integer > 1")

if (
isdigit(self.num_context_neighbors) and self.num_context_neighbors < 1
) or self.num_context_neighbors != "default":
if (isdigit(self.num_context_neighbors) and self.num_context_neighbors < 1) or self.num_context_neighbors != "default":
raise ValueError("--n-neighbors-context must be either 'default' or an integer > 1")


Expand Down
54 changes: 10 additions & 44 deletions main/como/combine_distributions.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,12 +59,7 @@ def _merge_batch(wd, context, batch):
zmat.columns = rep_names

stack_df = pd.concat(
[
pd.DataFrame(
{"entrez_gene_id": zmat["entrez_gene_id"], "zscore": zmat[col].astype(float), "source": col}
)
for col in zmat.columns[1:]
]
[pd.DataFrame({"entrez_gene_id": zmat["entrez_gene_id"], "zscore": zmat[col].astype(float), "source": col}) for col in zmat.columns[1:]]
)

plot_name_png = wd / "figures" / f"plot_{context}_{Path(f).stem}.png"
Expand Down Expand Up @@ -108,9 +103,7 @@ def weighted_z(x):

stack_df = pd.concat(
[
pd.DataFrame(
{"entrez_gene_id": merge_df["entrez_gene_id"], "zscore": merge_df[col].astype(float), "source": col}
)
pd.DataFrame({"entrez_gene_id": merge_df["entrez_gene_id"], "zscore": merge_df[col].astype(float), "source": col})
for col in merge_df.columns[1:]
]
)
Expand Down Expand Up @@ -157,9 +150,7 @@ def weighted_z(x, n_reps):

stack_df = pd.concat(
[
pd.DataFrame(
{"entrez_gene_id": merge_df["entrez_gene_id"], "zscore": merge_df[col].astype(float), "source": col}
)
pd.DataFrame({"entrez_gene_id": merge_df["entrez_gene_id"], "zscore": merge_df[col].astype(float), "source": col})
for col in merge_df.columns[1:]
]
)
Expand Down Expand Up @@ -259,9 +250,7 @@ def weighted_z(x, weights):

stack_df = pd.concat(
[
pd.DataFrame(
{"entrez_gene_id": merge_df["entrez_gene_id"], "zscore": merge_df[col].astype(float), "source": col}
)
pd.DataFrame({"entrez_gene_id": merge_df["entrez_gene_id"], "zscore": merge_df[col].astype(float), "source": col})
for col in merge_df.columns[1:]
]
)
Expand Down Expand Up @@ -343,11 +332,7 @@ def _combine_zscores( # noqa: C901
num_reps.extend(res[1])
combine_z_matrix = _combine_batch_zdistro(trna_workdir, context, batch, z_matrix)
combine_z_matrix.columns = ["entrez_gene_id", batch]
merge_z_data = (
combine_z_matrix
if merge_z_data.empty
else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")
)
merge_z_data = combine_z_matrix if merge_z_data.empty else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")

comb_batches_z_trna = _combine_context_zdistro(trna_workdir, context, num_reps, merge_z_data)
filename = trna_workdir / f"combined_zFPKM_{context}.csv"
Expand All @@ -369,11 +354,7 @@ def _combine_zscores( # noqa: C901
num_reps.extend(res[1])
combine_z_matrix = _combine_batch_zdistro(mrna_workdir, context, batch, z_matrix)
combine_z_matrix.columns = ["entrez_gene_id", batch]
merge_z_data = (
combine_z_matrix
if merge_z_data.empty
else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")
)
merge_z_data = combine_z_matrix if merge_z_data.empty else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")

comb_batches_z_mrna = _combine_context_zdistro(mrna_workdir, context, num_reps, merge_z_data)
filename = mrna_workdir / f"combined_zFPKM_{context}.csv"
Expand All @@ -395,11 +376,7 @@ def _combine_zscores( # noqa: C901
num_reps.extend(res[1])
combine_z_matrix = _combine_batch_zdistro(scrna_workdir, context, batch, z_matrix)
combine_z_matrix.columns = ["entrez_gene_id", batch]
merge_z_data = (
combine_z_matrix
if merge_z_data.empty
else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")
)
merge_z_data = combine_z_matrix if merge_z_data.empty else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")

comb_batches_z_scrna = _combine_context_zdistro(scrna_workdir, context, num_reps, merge_z_data)
filename = scrna_workdir / f"combined_zFPKM_{context}.csv"
Expand All @@ -421,11 +398,7 @@ def _combine_zscores( # noqa: C901
num_reps.extend(res[1])
combine_z_matrix = _combine_batch_zdistro(protein_workdir, context, batch, z_matrix)
combine_z_matrix.columns = ["entrez_gene_id", batch]
merge_z_data = (
combine_z_matrix
if merge_z_data.empty
else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")
)
merge_z_data = combine_z_matrix if merge_z_data.empty else pd.merge(merge_z_data, combine_z_matrix, on="entrez_gene_id", how="outer")

comb_batches_z_prot = _combine_context_zdistro(protein_workdir, context, num_reps, merge_z_data)
filename = protein_workdir / f"combined_zscore_proteinAbundance_{context}.csv"
Expand All @@ -435,15 +408,8 @@ def _combine_zscores( # noqa: C901
filename = protein_workdir / f"model_scores_{context}.csv"
comb_batches_z_prot.to_csv(filename, index=False)

if (
comb_batches_z_mrna is None
and comb_batches_z_trna is None
and comb_batches_z_scrna is None
and comb_batches_z_prot is None
):
logger.critical(
f"The context '{context}' was found in the configuration file but no data was found on disk!"
)
if comb_batches_z_mrna is None and comb_batches_z_trna is None and comb_batches_z_scrna is None and comb_batches_z_prot is None:
logger.critical(f"The context '{context}' was found in the configuration file but no data was found on disk!")
continue

comb_omics_z = _combine_omics_zdistros(
Expand Down
Loading