Run Your First Prediction

View as Markdown

In this tutorial, you run a complete Boltz-2 structure prediction with the installed BioNeMo Inference Runtime (BioIR) wheel. You create a protein request with an inline multiple sequence alignment (MSA), configure the serial inference pipeline, generate a CIF structure, and inspect its confidence scores.

The complete runnable script is available at examples/quickstart/boltz2.py. The following steps explain its inputs, configuration, and output.

Before You Begin

Complete the installation, including its system requirements. If you do not have a repository checkout, create quickstart.py and add the following code blocks in order.

The first run downloads the Boltz-2 checkpoint and chemical metadata from Hugging Face. Later runs reuse the local copies. Refer to Model Weights for cache locations and offline staging.

Start at the top-level import.

1import json
2
3from bionemo_ir.data.schemas import InputRequest, MSARecord, Polymer
4from bionemo_ir.pipeline.processor.engine_proc import (
5 EngineProcessorConfig,
6 build_processor,
7)
8from bionemo_ir.pipeline.stages.configs import (
9 FeatureGeneratorStageConfig,
10 WriterStageConfig,
11)

Understand the Input Request

The first part of quickstart.py creates the prediction request:

1SEQUENCE = "ACKIENIKYKGKEVESKLGSQLIDIFNDLDRAKEEYDKLSSPEFIAKFGDWINDEVERNVNEDGEPLLIQDVRQDSSKHYFFILKNGERFDLLTR"
2
3request = InputRequest(
4 input_id="T1031",
5 polymers=[
6 Polymer(
7 chain_id=["A1"],
8 sequence=SEQUENCE,
9 msas=[MSARecord(content=f">T1031\n{SEQUENCE}\n")],
10 )
11 ],
12)
13rows = [{"record": request, "__record_id": request["input_id"]}]

This block creates one prediction request:

  • InputRequest describes one biomolecular complex and gives it the identifier T1031.
  • Polymer defines protein chain A1 and its amino-acid sequence.
  • MSARecord provides an inline A3M alignment containing only the query sequence. This keeps the example self-contained. Production requests should use a full MSA.
  • rows wraps the request in the row format consumed by build_processor. __record_id becomes the output filename.

Refer to Input Requests for MSAs, templates, nucleic acids, ligands, and multiple chains.

Understand the Pipeline Configuration

The next block configures the serial prediction pipeline:

1config = EngineProcessorConfig(
2 model_source="boltz-2",
3 runtime_args={"num_sampling_steps": 50},
4 feature_generator_stage=FeatureGeneratorStageConfig(
5 init_context={"random_seed": 42},
6 ),
7 writer_stage=WriterStageConfig(
8 output_path="output/serial",
9 format="cif",
10 ),
11 engine_kwargs={"profile_inference": True},
12)

The configuration controls the complete prediction pipeline:

  • model_source="boltz-2" selects the Boltz-2 model, tokenizer, feature generator, checkpoint, and default runtime arguments.
  • num_sampling_steps=50 shortens the diffusion stage for this example. Other Boltz-2 arguments retain their registered defaults.
  • random_seed=42 makes feature generation reproducible.
  • WriterStageConfig writes a CIF structure under output/serial.
  • profile_inference=True adds the GPU model-forward time to the output row.
  • Omitting executor_backend selects the serial processor. Ray replicas are intended for processing many independent requests across several GPUs.

Refer to EngineProcessorConfig, Runtime Args, and Ray Multi-GPU Replicas for the available controls.

Understand Inference and Results

The final block runs inference and builds a compact score summary:

1row = build_processor(config)(rows)[0]
2scores = json.loads(row["scores"])
3
4summary = {
5 "record_id": row["__record_id"],
6 "output_path": row["output_path"],
7 "model_inference_time_s": round(row["model_inference_time"], 2),
8 "score_keys": sorted(scores),
9 "ptm": scores["ptm"],
10 "mean_plddt": round(sum(scores["plddt"]) / len(scores["plddt"]), 2),
11 "pae_shape": [len(scores["pae"]), len(scores["pae"][0])],
12}
13print(json.dumps(summary, indent=2))

build_processor(config) assembles the parser, tokenizer, feature generator, folding engine, and writer. Calling the processor returns one row for each input row. The writer stores scores as JSON, so the example decodes it before reading individual metrics.

The summary prints scalar values and array shapes instead of the full pLDDT and PAE arrays. Refer to build_processor and Outputs for the complete row schema.

Run the Example

From the repository root, run the maintained example:

$python examples/quickstart/boltz2.py

If you copied the code blocks into a standalone file, run that file instead:

$python quickstart.py

BioIR logs model and asset loading before printing the summary. A successful run resembles:

1{
2 "record_id": "T1031",
3 "output_path": "output/serial/T1031.cif",
4 "model_inference_time_s": 2.69,
5 "score_keys": [
6 "iptm",
7 "max_pae",
8 "pae",
9 "plddt",
10 "ptm"
11 ],
12 "ptm": 0.508,
13 "mean_plddt": 0.65,
14 "pae_shape": [
15 95,
16 95
17 ]
18}

Inference time and scores can vary across GPUs and releases. The stable result is a non-empty output/serial/T1031.cif structure and a score payload with the keys shown in the previous example.

The summary contains:

  • output_path — the predicted CIF structure.
  • model_inference_time_s — the synchronized GPU model-forward time. It does not include asset downloads, preprocessing, or output writing.
  • ptm — the predicted TM score returned by Boltz-2.
  • mean_plddt — the mean of the returned pLDDT confidence values.
  • pae_shape — the dimensions of the predicted aligned error matrix.

Next Steps