Inference utilities#
Condition-spec input#
Orchestration for the YAML/JSON condition-spec format.
See design_yaml_condition_spec.md / docs/condition_spec_yaml.md: a
condition spec is a shorthand for building an annotated CIF – load input
structure(s) (§4.2), subset + insert expandable segments via one contig
string (§4.3), set Conditions/StandardAnnotations by name (§4.4), then
finalize (§4.5: pre-save validation + a “summarize changes” report, no
explicit back-fill). build_annotated_atom_array_from_condition_spec()
does all of this for one example; resolve_condition_spec_inputs()
does it for every example in a spec file and writes each to disk.
- rfproteina.inference_utils.condition_spec.split_global_args(spec: dict) dict[str, dict][source]#
Return
{example_id: merged_example}, folding top-levelglobal_argsinto each example.- Raises:
ValueError – If
global_argsor any example is not a mapping. Skipping such entries instead would silently drop a whole example on a small indentation mistake, producing a run with fewer designs than the author asked for.
- rfproteina.inference_utils.condition_spec.is_legacy_dialect(data: dict) bool[source]#
Whether
datais written in the removed legacy contig-JSON dialect.There’s no explicit marker to check for – the legacy dialect predated condition_spec existing at all. Instead, this looks at each example’s own field names (with
global_argsdefaults folded in): condition_spec’sinputkey is required (missing it raises KeyError downstream), so an example lacking it can’t be condition_spec; and any field name outside condition_spec’s small vocabulary – i.e. any of the legacy-only names in_LEGACY_ONLY_FIELDS(select_fixed_atoms,unindex, the per-exampledialectint, …) – is unambiguous evidence of the legacy one. Every legacy example ends up naming at least one such field (a fully-diffused example useslength/contigalone, neither of which condition_spec needs). The legacy path itself is gone, so callers use this only to reject such inputs with a clear migration error.- Parameters:
data – A loaded spec file (as returned by
load_spec_file()),global_argskey included.- Returns:
Trueif any example (orglobal_args) looks like the legacy dialect.
- rfproteina.inference_utils.condition_spec.load_condition_spec_inputs(paths: list[str | PathLike], *, as_annotated_cif: bool = False) AtomArrayPlus[source]#
Parse and combine one or more structure files into a single AtomArrayPlus (§4.2). Loads the asymmetric unit only (
build_assembly=None).- Parameters:
paths – One or more CIF or BinaryCIF paths, optionally gzip- or Zstandard-compressed.
as_annotated_cif – If
True, load any existing Condition/StandardAnnotation columns already present (e.g. re-editing a previous output of this tool). IfFalse(default), any existing conditioning is ignored.
- Returns:
The combined structure.
- Raises:
ValueError – If any input isn’t a CIF/BCIF file, or if chain_id collides across multiple input files.
- rfproteina.inference_utils.condition_spec.load_example_input(spec: dict, spec_dir: Path) AtomArrayPlus[source]#
Load one example’s
input:structure(s), beforecontigsubsetting (§4.2).
- rfproteina.inference_utils.condition_spec.build_annotated_atom_array_from_condition_spec(spec: dict, *, spec_dir: Path, example_id: str = 'example', strict: bool = True, validate: bool = False) dict[source]#
Build one example’s fully assembled + annotated structure from its condition-spec dict.
Runs the fixed order of operations (companion doc): load (§4.2), contig (§4.3), conditions (§4.4), finalize (§4.5).
- Parameters:
spec – One example’s
{input, input_as_annotated_cif, contig, conditions}dict.spec_dir – Directory the spec file itself lives in (relative
inputpaths resolve against this).example_id – Name used in the printed summary and validation error messages.
strict – If
True(default), a failed pre-save validation check raises instead of only logging a warning.validate – If
True, run the (slow) pre-save validation. Defaults toFalse– online inference validates via the dataset transform instead; only the CIF-writer script andprevalidate_inputs=trueopt in (see_prevalidate()).
- Returns:
{atom_array, chain_info, ligand_info, metadata}, the same shapeparse_atom_array()returns.
- rfproteina.inference_utils.condition_spec.load_spec_file(path: Path) dict[source]#
Load a condition-spec file (YAML or JSON, by extension) into a raw dict.
- rfproteina.inference_utils.condition_spec.write_condition_spec_cif(example_id: str, spec: dict, out_path: Path, *, spec_dir: Path, validate: bool = True) Path[source]#
Build one example and write it to disk as an annotated CIF.
- Parameters:
example_id – Example name (used in the printed summary).
spec – One example’s condition-spec dict.
out_path – Destination CIF path.
spec_dir – Directory the spec file lives in (for resolving relative
inputpaths).validate – If
True(default), run pre-save validation on the built structure.
- Returns:
out_path.
- rfproteina.inference_utils.condition_spec.resolve_condition_spec_inputs(path: str | PathLike, out_dir: str | PathLike | None = None, *, validate: bool = True) list[Path][source]#
Build every example in a condition-spec file and write each to disk as an annotated CIF.
- Parameters:
path – Path to a condition_spec YAML/JSON file.
out_dir – Directory to write the CIFs into. Defaults to
<spec_stem>_cifs/beside the spec.validate – If
True(default), run pre-save validation on each built structure.
- Returns:
The list of written CIF paths, in file declaration order.
- Raises:
ValueError – If
pathis a legacy contig-JSON file (unsupported by this writer).
Metric aggregation#
Concatenate and aggregate per-example metrics from multi-job evaluation runs.
- rfproteina.inference_utils.aggregate_metrics.aggregate_sequence_probability_errors(per_example_df: DataFrame, workers: int | None = None) DataFrame[source]#
Pool soft probability observations across designs before computing per-task errors.
- Returns:
One row per dataset/task with n (number of pairs), absolute_mass_error (abs(sum(q - p))), mean_absolute_error, and median_absolute_error. Empty when no soft probability conditions were evaluated. Missing or unreadable structures are skipped with a warning.
- rfproteina.inference_utils.aggregate_metrics.aggregate_metrics_from_per_example_df(per_example_df: DataFrame, title: str = 'Aggregated Metrics', group_by: str = 'dataset_name') DataFrame[source]#
Aggregate per-example metrics by a grouping column.
- Parameters:
per_example_df – DataFrame with columns including ‘example_id’, ‘dataset_name’, and metric columns.
title – Title for the printed table.
group_by – Column to group by.
- Returns:
<group_by>, n, and one column per metric.
- Return type:
DataFrame with one row per group value, columns
- rfproteina.inference_utils.aggregate_metrics.concatenate_results(input: str, cluster_with_foldseek: bool = False, cleanup: bool = True, cleanup_chains: bool = True, output_dir: str | None = None, foldseek_threads: int | None = None, sequence_probability_workers: int | None = None) None[source]#
Concatenate per-example and aggregated metrics from multiple jobs.
Can also be used to run foldseek post-hoc by calling on the output dataframe.
- Parameters:
input – Path to either the directory containing the individual job result files, or the already-concatenated per_example_metrics.csv file.
cluster_with_foldseek – Whether to cluster results using Foldseek.
cleanup – If True, move individual job files to a subdirectory after concatenation.
cleanup_chains – If True (default), delete the
foldseek_input_chains/directory after clustering completes. The chain CIF files are derived from the designed structures and can be regenerated, so removal is safe.output_dir – Directory where results should be saved. Defaults to the input directory (or parent directory when input is a file).
foldseek_threads – Number of CPU threads to pass to foldseek. Defaults to all available CPUs. Set explicitly when running multiple clustering jobs in parallel on the same node to avoid resource contention.
sequence_probability_workers – Number of processes used to reconstruct probability observations from output CIFs. Defaults to up to eight CPUs from the SLURM allocation or process affinity; set explicitly to use more.
