pquintero's picture
tidy up default to anon submission
01d1575
raw
history blame
8.57 kB
import pandas as pd
import gradio as gr
from gradio_leaderboard import Leaderboard
from utils import fetch_hf_results, show_output_box
from constants import (
ASSAY_LIST,
ASSAY_RENAME,
ASSAY_EMOJIS,
ASSAY_DESCRIPTION,
EXAMPLE_FILE_DICT,
ANONYMOUS_SUBMISSION_USERNAME,
)
from about import ABOUT_TEXT, FAQS
from submit import make_submission
def format_leaderboard_table(df_results: pd.DataFrame, assay: str | None = None):
# Previous things that were nice in the constellaration leaderboard:
# Having a submission time column, and a user column where the username is clickable (this is a pro for usability but con for anonymity)
# full_df.rename(columns={'submission_time': 'submission time', 'problem_type': 'problem type'}, inplace=True)
# to_show['user'] = to_show['user'].apply(lambda x: make_user_clickable(x)).astype(str)
column_order = ["model", "property", "spearman", "spearman_cross_val"]
df = df_results.query("assay.isin(@ASSAY_RENAME.keys())").copy()
if assay is not None:
df = df[df["assay"] == assay]
df = df[column_order]
return df.sort_values(by="spearman", ascending=False)
# Cache the results to avoid multiple downloads
_cached_results = None
def get_cached_results():
global _cached_results
if _cached_results is None:
_cached_results = fetch_hf_results()
return _cached_results
def get_leaderboard_object(assay: str | None = None):
filter_columns = ["model"]
if assay is None:
filter_columns.append("property")
# TODO how to sort filter columns alphabetically?
Leaderboard(
# TODO(Lood) check that this actually refreshes using the function
value=format_leaderboard_table(df_results=get_cached_results(), assay=assay),
datatype=["str", "str", "str", "number"],
select_columns=["model", "property", "spearman", "spearman_cross_val"],
search_columns=["model"],
filter_columns=filter_columns,
every=60,
render=True,
)
with gr.Blocks() as demo:
gr.Markdown("""
## Welcome to the Ginkgo Antibody Developability Benchmark!
**Beta version, not publicly launched yet**
Participants can submit their model to the leaderboard by uploading a CSV file (see the "✉️ Submit" tab).
See more details in the "❔About" tab.
""")
with gr.Tabs(elem_classes="tab-buttons"):
with gr.TabItem("❔About", elem_id="abdev-benchmark-tab-table"):
gr.Image(
value="./assets/competition_logo.jpg",
show_label=False,
# elem_classes=["resized-image"],
show_download_button=False,
width="50vw", # 50% of the "viewport width"
)
gr.Markdown(ABOUT_TEXT)
for question, answer in FAQS.items():
with gr.Accordion(question):
gr.Markdown(answer)
# Procedurally make these 5 tabs
for assay in ASSAY_LIST:
with gr.TabItem(
f"{ASSAY_EMOJIS[assay]} {ASSAY_RENAME[assay]}",
elem_id="abdev-benchmark-tab-table",
):
gr.Markdown(f"# {ASSAY_DESCRIPTION[assay]}")
get_leaderboard_object(assay=assay)
with gr.TabItem("🚀 Overall", elem_id="abdev-benchmark-tab-table"):
gr.Markdown(
"# Antibody Developability Benchmark Leaderboard over all properties"
)
get_leaderboard_object()
with gr.TabItem("✉️ Submit", elem_id="boundary-benchmark-tab-table"):
gr.Markdown(
"""
# Antibody Developability Submission
Upload a CSV to get a score!
Please use your Hugging Face account name to submit your model - we use this to track separate submissions, but only Hugging Face/Ginkgo will see these usernames (unless you choose to make them public).
Your submission will be evaluated and added to the leaderboard.
"""
)
filename = gr.State(value=None)
eval_state = gr.State(value=None)
user_state = gr.State(value=None)
submission_type_state = gr.State(value="GDPa1")
download_file_state = gr.State(value=EXAMPLE_FILE_DICT["GDPa1"])
with gr.Row():
with gr.Column():
username_input = gr.Textbox(
label="Username",
placeholder="Enter your Hugging Face username or leave blank for anonymous submissions",
info="This will be used to track your submissions, and to update your results if you submit again.",
)
model_name_input = gr.Textbox(
label="Model Name",
placeholder="Enter your model name (e.g., 'MyProteinLM-v1')",
info="This will be displayed on the leaderboard.",
)
model_description_input = gr.Textbox(
label="Model Description",
placeholder="Brief description of your model and approach",
info="Describe your model, training data, or methodology.",
lines=3,
)
with gr.Column():
submission_type_dropdown = gr.Dropdown(
choices=["GDPa1", "GDPa1_cross_validation"],
value="GDPa1",
label="Submission Type",
)
download_button = gr.DownloadButton(
label="📥 Download example submission CSV",
value=EXAMPLE_FILE_DICT["GDPa1"],
variant="secondary",
)
submission_file = gr.File(label="Submission CSV")
# If username is empty, set to anonymous submission
username_input.change(
fn=lambda x: x if x.strip() else ANONYMOUS_SUBMISSION_USERNAME,
inputs=username_input,
outputs=user_state,
)
def update_submission_type_and_file(submission_type):
"""
Based on the submission type selected in the dropdown,
Update the submission type state
Dynamically update example file for download
"""
download_file = EXAMPLE_FILE_DICT.get(
submission_type, EXAMPLE_FILE_DICT["GDPa1"]
)
return (
submission_type,
download_file,
gr.DownloadButton(
label="📥 Download example submission CSV",
value=download_file,
variant="secondary",
),
)
# Update submission type state and download button when dropdown changes
submission_type_dropdown.change(
fn=update_submission_type_and_file,
inputs=submission_type_dropdown,
outputs=[submission_type_state, download_file_state, download_button],
)
submit_btn = gr.Button("Evaluate")
message = gr.Textbox(label="Status", lines=1, visible=False)
# help message
gr.Markdown(
"If you have issues with submission or using the leaderboard, please start a discussion in the Community tab of this Space."
)
submit_btn.click(
make_submission,
inputs=[
submission_file,
user_state,
submission_type_state,
model_name_input,
model_description_input,
],
outputs=[message],
).then(
fn=show_output_box,
inputs=[message],
outputs=[message],
)
# Footnote
gr.Markdown(
"""
<div style="text-align: center; font-size: 14px; color: gray; margin-top: 2em;">
📬 For questions or feedback, contact <a href="mailto:[email protected]">[email protected]</a> or visit the Community tab at the top of this page.
</div>
""",
elem_id="contact-footer",
)
if __name__ == "__main__":
demo.launch()