UMA / scripts /create_uma_finetune_dataset.py
OneScience's picture
Upload folder using huggingface_hub
bf314e8 verified
Raw
History Blame Contribute Delete
4.77 kB
from __future__ import annotations
import argparse
import logging
import os
from pathlib import Path
import yaml
from onescience.utils.uma.scripts.create_finetune_dataset import (
compute_normalizer_and_linear_reference,
launch_processing,
)
from onescience.utils.uma.units.mlip_unit.api.inference import UMATask
logging.basicConfig(level=logging.INFO)
TEMPLATE_DIR = Path("configs")
DATA_YAML_DIR = Path("data")
REGRESSION_LABEL_TO_TASK_YAML = {
"e": DATA_YAML_DIR / Path("uma_conserving_data_task_energy.yaml"),
"ef": DATA_YAML_DIR / Path("uma_conserving_data_task_energy_force.yaml"),
"efs": DATA_YAML_DIR / Path("uma_conserving_data_task_energy_force_stress.yaml"),
}
UMA_SM_FINETUNE_YAML = Path("uma_sm_finetune_template.yaml")
def create_yaml(
train_path: str,
val_path: str,
force_rms: float,
linref_coeff: list,
output_dir: str,
dataset_name: str,
regression_tasks: str,
# base_model_name: str,
):
data_task_yaml = TEMPLATE_DIR / REGRESSION_LABEL_TO_TASK_YAML[regression_tasks]
with open(data_task_yaml) as file:
template = yaml.safe_load(file)
template["dataset_name"] = dataset_name
template["normalizer_rmsd"] = force_rms
template["elem_refs"] = linref_coeff
template["train_dataset"]["splits"]["train"]["src"] = train_path
template["val_dataset"]["splits"]["val"]["src"] = val_path
# add extra large vaccum box for molecules
# if dataset_name == str(UMATask.OMOL):
# template["train_dataset"]["a2g_args"]["molecule_cell_size"] = 1000.0
os.makedirs(output_dir / DATA_YAML_DIR, exist_ok=True)
with open(
output_dir / REGRESSION_LABEL_TO_TASK_YAML[regression_tasks], "w"
) as yaml_file:
yaml.dump(template, yaml_file, default_flow_style=False, sort_keys=False)
uma_finetune_yaml = TEMPLATE_DIR / UMA_SM_FINETUNE_YAML
with open(uma_finetune_yaml) as file:
template_ft = yaml.safe_load(file)
#template_ft["base_model_name"] = base_model_name
template_ft["defaults"][0]["data"] = REGRESSION_LABEL_TO_TASK_YAML[
regression_tasks
].stem
with open(output_dir / UMA_SM_FINETUNE_YAML, "w") as yaml_file:
yaml.dump(template_ft, yaml_file, default_flow_style=False, sort_keys=False)
if __name__ == "__main__":
parser = argparse.ArgumentParser()
parser.add_argument(
"--train-dir",
type=str,
required=True,
help="Directory of ASE atoms objects to convert for training.",
)
parser.add_argument(
"--val-dir",
type=str,
required=True,
help="Directory of ASE atoms objects to convert for validation.",
)
parser.add_argument(
"--uma-task",
type=str,
required=True,
choices=[t.value for t in UMATask],
help="choose a uma task to finetune",
)
parser.add_argument(
"--regression-tasks",
type=str,
choices=["e", "ef", "efs"],
required=True,
help="Choose to finetune based on regression task set (you must have the corresponding labels in your dataset), can be energy (e), energy+force (ef) or energy+force+stress(efs)",
)
#parser.add_argument(
# "--base-model",
# type=str,
# default="uma-s-1",
# help="Name of base uma model",
#)
parser.add_argument(
"--output-dir",
type=Path,
required=True,
help="Output directory to save required finetuning artifacts.",
)
parser.add_argument(
"--num-workers",
type=int,
default=8,
help="Number of parallel workers for processing files.",
)
args = parser.parse_args()
assert not Path(
args.output_dir
).exists(), f"{args.output_dir} can't already exist, please choose a different dir"
# Launch processing for training data
train_path = args.output_dir / "train"
launch_processing(args.train_dir, train_path, args.num_workers)
force_rms, linref_coeff = compute_normalizer_and_linear_reference(
train_path, args.num_workers
)
val_path = args.output_dir / "val"
launch_processing(args.val_dir, val_path, args.num_workers)
create_yaml(
train_path=str(train_path),
val_path=str(val_path),
force_rms=float(force_rms),
linref_coeff=linref_coeff,
output_dir=args.output_dir,
dataset_name=args.uma_task,
regression_tasks=args.regression_tasks,
# base_model_name=args.base_model,
)
logging.info(f"Generated dataset and data config yaml in {args.output_dir}")
logging.info(
f"To run finetuning, run fairchem -c {args.output_dir}/{UMA_SM_FINETUNE_YAML}"
)