feat: plot plddt
Browse files- Dockerfile +1 -0
- app.py +44 -15
Dockerfile
CHANGED
@@ -27,6 +27,7 @@ RUN cd /app/folding-studio && uv pip install -e .
|
|
27 |
COPY app.py /app/app.py
|
28 |
COPY molecule.py /app/molecule.py
|
29 |
# COPY pred.cif /app/boltz_results/pred_model_0.cif
|
|
|
30 |
|
31 |
EXPOSE 7860
|
32 |
ENV GRADIO_SERVER_NAME="0.0.0.0"
|
|
|
27 |
COPY app.py /app/app.py
|
28 |
COPY molecule.py /app/molecule.py
|
29 |
# COPY pred.cif /app/boltz_results/pred_model_0.cif
|
30 |
+
# COPY plddt_0.npz /app/boltz_results/plddt_0.npz
|
31 |
|
32 |
EXPOSE 7860
|
33 |
ENV GRADIO_SERVER_NAME="0.0.0.0"
|
app.py
CHANGED
@@ -1,12 +1,13 @@
|
|
1 |
-
import hashlib
|
2 |
-
import gradio as gr
|
3 |
-
from pathlib import Path
|
4 |
from Bio.PDB import MMCIFParser, PDBIO
|
5 |
-
import logging
|
6 |
-
import os
|
7 |
from folding_studio.client import Client
|
8 |
from folding_studio.query.boltz import BoltzQuery, BoltzParameters
|
9 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
10 |
|
11 |
from molecule import molecule
|
12 |
|
@@ -21,7 +22,7 @@ logging.basicConfig(
|
|
21 |
logger = logging.getLogger(__name__)
|
22 |
|
23 |
|
24 |
-
def convert_cif_to_pdb(cif_path, pdb_path):
|
25 |
"""Convert a .cif file to .pdb format using Biopython.
|
26 |
|
27 |
Args:
|
@@ -117,10 +118,13 @@ def predict(sequence: str, api_key: str) -> str:
|
|
117 |
mol = _create_molecule_visualization(
|
118 |
converted_pdb_path,
|
119 |
sequence,
|
120 |
-
|
121 |
-
|
122 |
-
|
123 |
-
|
|
|
|
|
|
|
124 |
|
125 |
|
126 |
def _write_fasta_file(filepath: Path, sequence: str) -> None:
|
@@ -129,7 +133,7 @@ def _write_fasta_file(filepath: Path, sequence: str) -> None:
|
|
129 |
f.write(f">A|protein\n{sequence}")
|
130 |
|
131 |
|
132 |
-
def _create_molecule_visualization(pdb_path: Path, sequence: str
|
133 |
"""Create molecular visualization using molecule module."""
|
134 |
return molecule(
|
135 |
str(pdb_path),
|
@@ -160,6 +164,28 @@ def _wrap_in_iframe(content: str) -> str:
|
|
160 |
srcdoc='{content}'
|
161 |
></iframe>"""
|
162 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
163 |
demo = gr.Blocks(title="Folding Studio: structure prediction with Boltz-1")
|
164 |
|
165 |
with demo:
|
@@ -172,12 +198,15 @@ with demo:
|
|
172 |
with gr.Row():
|
173 |
predict_btn = gr.Button("Predict")
|
174 |
with gr.Row():
|
175 |
-
|
176 |
-
|
|
|
|
|
|
|
177 |
predict_btn.click(
|
178 |
fn=predict,
|
179 |
inputs=[sequence, api_key],
|
180 |
-
outputs=[mol_output]
|
181 |
)
|
182 |
|
183 |
demo.launch()
|
|
|
|
|
|
|
|
|
1 |
from Bio.PDB import MMCIFParser, PDBIO
|
|
|
|
|
2 |
from folding_studio.client import Client
|
3 |
from folding_studio.query.boltz import BoltzQuery, BoltzParameters
|
4 |
+
from pathlib import Path
|
5 |
+
import gradio as gr
|
6 |
+
import hashlib
|
7 |
+
import logging
|
8 |
+
import numpy as np
|
9 |
+
import os
|
10 |
+
import plotly.graph_objects as go
|
11 |
|
12 |
from molecule import molecule
|
13 |
|
|
|
22 |
logger = logging.getLogger(__name__)
|
23 |
|
24 |
|
25 |
+
def convert_cif_to_pdb(cif_path: str, pdb_path: str) -> None:
|
26 |
"""Convert a .cif file to .pdb format using Biopython.
|
27 |
|
28 |
Args:
|
|
|
118 |
mol = _create_molecule_visualization(
|
119 |
converted_pdb_path,
|
120 |
sequence,
|
121 |
+
)
|
122 |
+
|
123 |
+
plddt_file = list(pred_cif.parent.glob("plddt_*.npz"))[0]
|
124 |
+
logger.info("plddt file: %s", plddt_file)
|
125 |
+
plddt_vals = np.load(plddt_file)["plddt"]
|
126 |
+
|
127 |
+
return _wrap_in_iframe(mol), add_plddt_plot(plddt_vals=plddt_vals)
|
128 |
|
129 |
|
130 |
def _write_fasta_file(filepath: Path, sequence: str) -> None:
|
|
|
133 |
f.write(f">A|protein\n{sequence}")
|
134 |
|
135 |
|
136 |
+
def _create_molecule_visualization(pdb_path: Path, sequence: str) -> str:
|
137 |
"""Create molecular visualization using molecule module."""
|
138 |
return molecule(
|
139 |
str(pdb_path),
|
|
|
164 |
srcdoc='{content}'
|
165 |
></iframe>"""
|
166 |
|
167 |
+
def add_plddt_plot(plddt_vals: list[float]) -> str:
|
168 |
+
"""Create a plot of metrics."""
|
169 |
+
visible = True
|
170 |
+
plddt_trace = go.Scatter(
|
171 |
+
x=np.arange(len(plddt_vals)),
|
172 |
+
y=plddt_vals,
|
173 |
+
hovertemplate="<i>pLDDT</i>: %{y:.2f} <br><i>Residue index:</i> %{x}<br>",
|
174 |
+
name="seq",
|
175 |
+
visible=visible,
|
176 |
+
)
|
177 |
+
|
178 |
+
plddt_fig = go.Figure(data=[plddt_trace])
|
179 |
+
plddt_fig.update_layout(
|
180 |
+
title="pLDDT",
|
181 |
+
xaxis_title="Residue index",
|
182 |
+
yaxis_title="pLDDT",
|
183 |
+
height=500,
|
184 |
+
template="simple_white",
|
185 |
+
legend=dict(yanchor="bottom", y=0.01, xanchor="left", x=0.99),
|
186 |
+
)
|
187 |
+
return plddt_fig
|
188 |
+
|
189 |
demo = gr.Blocks(title="Folding Studio: structure prediction with Boltz-1")
|
190 |
|
191 |
with demo:
|
|
|
198 |
with gr.Row():
|
199 |
predict_btn = gr.Button("Predict")
|
200 |
with gr.Row():
|
201 |
+
with gr.Column():
|
202 |
+
mol_output = gr.HTML()
|
203 |
+
with gr.Column():
|
204 |
+
metrics_plot = gr.Plot(label="pLDDT")
|
205 |
+
|
206 |
predict_btn.click(
|
207 |
fn=predict,
|
208 |
inputs=[sequence, api_key],
|
209 |
+
outputs=[mol_output, metrics_plot]
|
210 |
)
|
211 |
|
212 |
demo.launch()
|