From 1ebccbc10ebde5f9d9f849d77d3f0f544222f460 Mon Sep 17 00:00:00 2001 From: aramoto99 Date: Thu, 12 Dec 2024 14:29:21 +0900 Subject: [PATCH 01/18] change resumable --- aiaccel/hpo/apps/config/__init__.py | 0 aiaccel/hpo/apps/config/default.yaml | 14 ++ aiaccel/hpo/apps/config/resumable.yaml | 7 + aiaccel/hpo/apps/optimize.py | 29 ++- examples/job/optuna/config.yaml | 19 -- tests/hpo/apps/main/config.yaml | 32 +++ tests/hpo/apps/main/objective.sh | 10 + tests/hpo/apps/main/objective_for_test.py | 22 ++ tests/hpo/apps/main/test_resume.py | 241 ++++++++++++++++++++++ 9 files changed, 347 insertions(+), 27 deletions(-) create mode 100644 aiaccel/hpo/apps/config/__init__.py create mode 100644 aiaccel/hpo/apps/config/default.yaml create mode 100644 aiaccel/hpo/apps/config/resumable.yaml create mode 100644 tests/hpo/apps/main/config.yaml create mode 100644 tests/hpo/apps/main/objective.sh create mode 100644 tests/hpo/apps/main/objective_for_test.py create mode 100644 tests/hpo/apps/main/test_resume.py diff --git a/aiaccel/hpo/apps/config/__init__.py b/aiaccel/hpo/apps/config/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/aiaccel/hpo/apps/config/default.yaml b/aiaccel/hpo/apps/config/default.yaml new file mode 100644 index 000000000..b9c44479c --- /dev/null +++ b/aiaccel/hpo/apps/config/default.yaml @@ -0,0 +1,14 @@ +study: + _target_: optuna.create_study + direction: minimize + storage: + _target_: optuna.storages.InMemoryStorage + study_name: aiaccel_study + load_if_exists: false + sampler: + _target_: optuna.samplers.TPESampler + seed: 0 + +params: + _convert_: partial + _target_: aiaccel.hpo.apps.optimize.HparamsManager diff --git a/aiaccel/hpo/apps/config/resumable.yaml b/aiaccel/hpo/apps/config/resumable.yaml new file mode 100644 index 000000000..50b40a7a5 --- /dev/null +++ b/aiaccel/hpo/apps/config/resumable.yaml @@ -0,0 +1,7 @@ +study: + storage: + _target_: optuna.storages.RDBStorage + url: sqlite:///aiaccel.db + engine_kwargs: + connect_args: + timeout: 30 diff --git a/aiaccel/hpo/apps/optimize.py b/aiaccel/hpo/apps/optimize.py index 96cb9ae38..79808e9e7 100644 --- a/aiaccel/hpo/apps/optimize.py +++ b/aiaccel/hpo/apps/optimize.py @@ -2,6 +2,7 @@ import argparse from collections.abc import Callable +import importlib.resources from pathlib import Path import pickle as pkl @@ -110,14 +111,8 @@ def main() -> None: ~~~ """ - parser = argparse.ArgumentParser() - parser.add_argument("job_filename", type=Path, help="The shell script to execute.") - parser.add_argument("--config", nargs="?", default=None) - parser.add_argument("--executor", nargs="?", default="local") - parser.add_argument("--resume", action="store_true", default=False) - - args, unk_args = parser.parse_known_args() - config = oc.merge(oc.load(args.config), oc.from_cli(unk_args)) + """ + onfig = oc.merge(oc.load(args.config), oc.from_cli(unk_args)) if "storage" not in config.study: config.study.storage = { @@ -129,6 +124,24 @@ def main() -> None: if "study_name" not in config.study: config.study.study_name = "aiaccel_study" + """ + + parser = argparse.ArgumentParser() + parser.add_argument("job_filename", type=Path, help="The shell script to execute.") + parser.add_argument("--config", default="config.yaml", help="Configuration file path") + parser.add_argument("--executor", nargs="?", default="local") + parser.add_argument("--resume", action="store_true", default=False) + parser.add_argument("--resumable", action="store_true", default=False) + + args, unk_args = parser.parse_known_args() + + default_config = oc.load(importlib.resources.open_text("aiaccel.hpo.apps.config", "default.yaml")) + config = oc.merge(default_config, oc.load(args.config)) + config = oc.merge(config, oc.from_cli(unk_args)) + + if args.resumable or args.resume: + config = oc.merge(config, oc.load(importlib.resources.open_text("aiaccel.hpo.apps.config", "resumable.yaml"))) + if args.resume: config.study.load_if_exists = True diff --git a/examples/job/optuna/config.yaml b/examples/job/optuna/config.yaml index 91b9da5c0..47f4aa9d1 100644 --- a/examples/job/optuna/config.yaml +++ b/examples/job/optuna/config.yaml @@ -1,20 +1,3 @@ -storage: - _target_: optuna.storages.RDBStorage - url: sqlite:///example.db - engine_kwargs: - connect_args: - timeout: 30 - -study: - _target_: optuna.create_study - direction: minimize - storage: ${storage} - study_name: my_study - load_if_exists: false - sampler: - _target_: optuna.samplers.TPESampler - seed: 0 - params: _convert_: partial _target_: aiaccel.hpo.apps.optimize.HparamsManager @@ -28,5 +11,3 @@ params: n_trials: 30 n_max_jobs: 4 - -group: gaa50000 diff --git a/tests/hpo/apps/main/config.yaml b/tests/hpo/apps/main/config.yaml new file mode 100644 index 000000000..9c6098675 --- /dev/null +++ b/tests/hpo/apps/main/config.yaml @@ -0,0 +1,32 @@ +storage: + _target_: optuna.storages.RDBStorage + url: sqlite:///aiaccel_storage.db + engine_kwargs: + connect_args: + timeout: 30 + +study: + _target_: optuna.create_study + direction: minimize + storage: ${storage} + study_name: my_study + load_if_exists: false + sampler: + _target_: optuna.samplers.TPESampler + seed: 0 + +params: + _convert_: partial + _target_: aiaccel.hpo.apps.optimize.HparamsManager + x1: [0, 1] + x2: + _target_: aiaccel.hpo.optuna.suggest_wrapper.SuggestFloat + name: x2 + low: 0.0 + high: 1.0 + log: false + +n_trials: 30 +n_max_jobs: 1 + +group: gaa50000 diff --git a/tests/hpo/apps/main/objective.sh b/tests/hpo/apps/main/objective.sh new file mode 100644 index 000000000..3c849c2d7 --- /dev/null +++ b/tests/hpo/apps/main/objective.sh @@ -0,0 +1,10 @@ +#!/bin/bash + +#$-l rt_C.small=1 +#$-cwd + +source /etc/profile.d/modules.sh +module load gcc/13.2.0 +module load python/3.10/3.10.14 + +python objective_for_test.py $@ diff --git a/tests/hpo/apps/main/objective_for_test.py b/tests/hpo/apps/main/objective_for_test.py new file mode 100644 index 000000000..028bc03d7 --- /dev/null +++ b/tests/hpo/apps/main/objective_for_test.py @@ -0,0 +1,22 @@ +from argparse import ArgumentParser +from pathlib import Path +import pickle as pkl + + +def main() -> None: + parser = ArgumentParser() + parser.add_argument("dst_filename", type=Path) + parser.add_argument("--x1", type=float) + parser.add_argument("--x2", type=float) + args = parser.parse_args() + + x1, x2 = args.x1, args.x2 + + y = (x1**2) - (4.0 * x1) + (x2**2) - x2 - (x1 * x2) + + with open(args.dst_filename, "wb") as f: + pkl.dump(y, f) + + +if __name__ == "__main__": + main() diff --git a/tests/hpo/apps/main/test_resume.py b/tests/hpo/apps/main/test_resume.py new file mode 100644 index 000000000..0b37e5f8f --- /dev/null +++ b/tests/hpo/apps/main/test_resume.py @@ -0,0 +1,241 @@ +from collections.abc import Generator +import os +from pathlib import Path +import shutil +import sqlite3 +import tempfile +from unittest.mock import patch +import uuid + +import pytest + + +@pytest.fixture +def temp_dir() -> Generator[Path]: + """Create a temporary directory with test files and clean up afterwards""" + with tempfile.TemporaryDirectory() as tmp_dir: + temp_path = Path(tmp_dir) + original_dir = os.getcwd() + os.chdir(tmp_dir) + + source_dir = Path(__file__).parent + test_files = ["config.yaml", "objective.sh", "objective_for_test.py"] + + for file_name in test_files: + source_file = source_dir / file_name + target_file = temp_path / file_name + + if source_file.exists(): + shutil.copy2(source_file, target_file) + print(f"\n=== Content of {file_name} ===") + print((target_file).read_text()) + print("=" * 40) + else: + pytest.skip(f"Required test file {file_name} not found in {source_dir}") + + os.chmod(temp_path / "objective.sh", 0o755) + yield temp_path + os.chdir(original_dir) + + +def get_trial_count(db_path: Path, study_name: str) -> int: + """Get the number of trials from the SQLite database for a specific study + + Args: + db_path (Path): Path to the SQLite database + study_name (str): Name of the study to query + + Returns: + int: Number of trials for the specified study + """ + conn = sqlite3.connect(db_path) + cursor = conn.cursor() + cursor.execute( + """ + SELECT COUNT(*) FROM trials + WHERE study_id = (SELECT study_id FROM studies WHERE study_name = ?) + """, + (study_name,), + ) + count = cursor.fetchone()[0] + conn.close() + if count is None: + return 0 + return int(count) + + +def get_trial_values(db_path: Path, study_name: str) -> list[float]: + """Get the values of all completed trials for a specific study + + Args: + db_path (Path): Path to the SQLite database + study_name (str): Name of the study to query + + Returns: + list[float]: List of trial values in order of trial number + """ + + conn = sqlite3.connect(db_path) + cursor = conn.cursor() + cursor.execute( + """ + SELECT trial_values.value + FROM trials + JOIN studies ON trials.study_id = studies.study_id + JOIN trial_values ON trials.trial_id = trial_values.trial_id + WHERE studies.study_name = ? + AND trials.state = 'COMPLETE' + ORDER BY trials.number + """, + (study_name,), + ) + # Fetch all values from the query result + + values = [row[0] for row in cursor.fetchall()] + conn.close() + return values + + +def modify_config(config_path: Path, study_name: str, n_trials: int, db_name: str) -> Path: + """Modify config file with new study name and number of trials""" + with open(config_path) as f: + content = f.read() + + content = content.replace("study_name: my_study", f"study_name: {study_name}") + content = content.replace("n_trials: 30", f"n_trials: {n_trials}") + + if db_name: + content = content.replace("aiaccel_storage.db", db_name) + + new_config_path = config_path.parent / f"config_{study_name}.yaml" + with open(new_config_path, "w") as f: + f.write(content) + + return new_config_path + + +def test_optimization_consistency(temp_dir: Path) -> None: + """Test that split execution (resumable + resume) gives same results as normal execution. + + Test steps: + 1. Run 30 trials in normal mode: python optimize.py objective.sh --config config.yaml + 2. Run 15 trials in resumable mode: python optimize.py objective.sh --config config.yaml --resumable + 3. Run 15 trials in resume mode: python optimize.py objective.sh --config config.yaml --resume + + Assertions: + - Both executions should complete 30 trials + - The best values from both executions should be nearly identical (within 1e-6) + """ + from aiaccel.hpo.apps.optimize import main + + # Use different database files for normal and split execution + normal_db = "normal_storage.db" + split_db = "split_storage.db" + + # Normal execution with 30 trials + study_name_normal = f"test_study_{uuid.uuid4().hex[:8]}" + normal_config = modify_config(temp_dir / "config.yaml", study_name_normal, 30, normal_db) + + with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(normal_config)]): + main() + + normal_results = get_trial_values(temp_dir / normal_db, study_name_normal) + assert len(normal_results) == 30, "Normal execution should have 30 trials" + normal_best = min(normal_results) + + # Split execution with 15 + 15 trials + study_name_split = f"test_study_{uuid.uuid4().hex[:8]}" + split_config = modify_config(temp_dir / "config.yaml", study_name_split, 15, split_db) + + # First 15 trials + with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(split_config), "--resumable"]): + main() + + db_path = temp_dir / split_db + trial_count = get_trial_count(db_path, study_name_split) + assert trial_count == 15 + + # Second 15 trials + with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(split_config), "--resume"]): + main() + + trial_count = get_trial_count(db_path, study_name_split) + assert trial_count == 30 + + # Compare results + split_results = get_trial_values(db_path, study_name_split) + split_best = min(split_results) + assert len(split_results) == 30, "Split execution should have 30 trials" + assert abs(normal_best - split_best) < 1e-6, f"Best values differ: normal={normal_best}, split={split_best}" + + +def test_normal_execution(temp_dir: Path) -> None: + """Test normal execution without resume functionality""" + from aiaccel.hpo.apps.optimize import main + + db_name = "normal_test.db" + study_name = f"test_study_{uuid.uuid4().hex[:8]}" + config_path = modify_config(temp_dir / "config.yaml", study_name, 30, db_name) + + with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(config_path)]): + main() + + trial_count = get_trial_count(temp_dir / db_name, study_name) + assert trial_count == 30 + + +def test_resumable_execution(temp_dir: Path) -> None: + """Test execution with `--resumable` + This should run only the first half of the trials and save the state to a database file. + """ + from aiaccel.hpo.apps.optimize import main + + db_name = "resumable_test.db" + study_name = f"test_study_{uuid.uuid4().hex[:8]}" + config_path = modify_config(temp_dir / "config.yaml", study_name, 15, db_name) + + with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(config_path), "--resumable"]): + main() + + db_path = temp_dir / db_name + assert db_path.exists(), "Database file was not created" + trial_count = get_trial_count(db_path, study_name) + assert trial_count == 15 + + +def test_resume_execution(temp_dir: Path) -> None: + """Test the resume functionality of the optimization process. + + This test verifies that the optimization process can be resumed correctly + from a saved state. It performs the following steps: + 1. Runs the optimization process with the `--resumable` flag and checks + that the correct number of trials are completed. + 2. Resumes the optimization process with the `--resume` flag and checks + that the remaining trials are completed correctly. + + Args: + temp_dir (pathlib.Path): Temporary directory for test files. + + Raises: + AssertionError: If the number of trials after each run does not match + the expected values. + """ + + from aiaccel.hpo.apps.optimize import main + + db_name = "resume_test.db" + study_name = f"test_study_{uuid.uuid4().hex[:8]}" + config_path = modify_config(temp_dir / "config.yaml", study_name, 15, db_name) + + with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(config_path), "--resumable"]): + main() + + db_path = temp_dir / db_name + trial_count = get_trial_count(db_path, study_name) + assert trial_count == 15 + + with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(config_path), "--resume"]): + main() + + trial_count = get_trial_count(db_path, study_name) + assert trial_count == 30 From 5b8956a5636a7459ebd672e409e9382900230642 Mon Sep 17 00:00:00 2001 From: aramoto99 Date: Thu, 12 Dec 2024 14:42:16 +0900 Subject: [PATCH 02/18] fix test --- tests/hpo/apps/main/test_resume.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/hpo/apps/main/test_resume.py b/tests/hpo/apps/main/test_resume.py index 0b37e5f8f..306697f14 100644 --- a/tests/hpo/apps/main/test_resume.py +++ b/tests/hpo/apps/main/test_resume.py @@ -97,7 +97,6 @@ def get_trial_values(db_path: Path, study_name: str) -> list[float]: def modify_config(config_path: Path, study_name: str, n_trials: int, db_name: str) -> Path: - """Modify config file with new study name and number of trials""" with open(config_path) as f: content = f.read() @@ -105,7 +104,8 @@ def modify_config(config_path: Path, study_name: str, n_trials: int, db_name: st content = content.replace("n_trials: 30", f"n_trials: {n_trials}") if db_name: - content = content.replace("aiaccel_storage.db", db_name) + db_path = config_path.parent / db_name + content = content.replace("aiaccel_storage.db", str(db_path.absolute())) new_config_path = config_path.parent / f"config_{study_name}.yaml" with open(new_config_path, "w") as f: From efad8c356b484b43c96c091cc83bef5483a111fa Mon Sep 17 00:00:00 2001 From: aramoto99 Date: Fri, 13 Dec 2024 11:02:02 +0900 Subject: [PATCH 03/18] fix resume test --- .github/workflows/ci.yaml | 11 +++++------ aiaccel/hpo/apps/optimize.py | 2 +- tests/hpo/apps/main/in_memory.yaml | 24 ++++++++++++++++++++++++ tests/hpo/apps/main/test_resume.py | 26 ++++++++++++++------------ 4 files changed, 44 insertions(+), 19 deletions(-) create mode 100644 tests/hpo/apps/main/in_memory.yaml diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml index aba999a1e..921133595 100644 --- a/.github/workflows/ci.yaml +++ b/.github/workflows/ci.yaml @@ -9,20 +9,19 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: ['ubuntu-22.04'] - python-version: ['3.10'] - test_target: ['apps', 'hpo', 'torch'] + os: ["ubuntu-22.04"] + python-version: ["3.10"] + test_target: ["apps", "hpo", "torch"] steps: - uses: actions/checkout@v4 - uses: actions/setup-python@v5 with: python-version: ${{ matrix.python-version }} - cache: 'pip' + cache: "pip" cache-dependency-path: pyproject.toml - name: Install dependencies run: | pip install --upgrade pip pip install -e .[dev,github-actions] - name: Run pytest - run: pytest -v --cov=aiaccel/${{ strategy.target }} --cov-branch --cov-report=term-missing tests/${{ strategy.target }} - + run: pytest -v --cov=aiaccel/${{ matrix.test_target }} --cov-branch --cov-report=term-missing tests/${{ matrix.test_target }} diff --git a/aiaccel/hpo/apps/optimize.py b/aiaccel/hpo/apps/optimize.py index 79808e9e7..ffa7a2fdb 100644 --- a/aiaccel/hpo/apps/optimize.py +++ b/aiaccel/hpo/apps/optimize.py @@ -139,7 +139,7 @@ def main() -> None: config = oc.merge(default_config, oc.load(args.config)) config = oc.merge(config, oc.from_cli(unk_args)) - if args.resumable or args.resume: + if (args.resumable or args.resume) and "storage" not in config.study: config = oc.merge(config, oc.load(importlib.resources.open_text("aiaccel.hpo.apps.config", "resumable.yaml"))) if args.resume: diff --git a/tests/hpo/apps/main/in_memory.yaml b/tests/hpo/apps/main/in_memory.yaml new file mode 100644 index 000000000..67030e029 --- /dev/null +++ b/tests/hpo/apps/main/in_memory.yaml @@ -0,0 +1,24 @@ +study: + _target_: optuna.create_study + direction: minimize + study_name: my_study + load_if_exists: false + sampler: + _target_: optuna.samplers.TPESampler + seed: 0 + +params: + _convert_: partial + _target_: aiaccel.hpo.apps.optimize.HparamsManager + x1: [0, 1] + x2: + _target_: aiaccel.hpo.optuna.suggest_wrapper.SuggestFloat + name: x2 + low: 0.0 + high: 1.0 + log: false + +n_trials: 30 +n_max_jobs: 1 + +group: gaa50000 diff --git a/tests/hpo/apps/main/test_resume.py b/tests/hpo/apps/main/test_resume.py index 306697f14..5e636315b 100644 --- a/tests/hpo/apps/main/test_resume.py +++ b/tests/hpo/apps/main/test_resume.py @@ -24,9 +24,9 @@ def temp_dir() -> Generator[Path]: for file_name in test_files: source_file = source_dir / file_name target_file = temp_path / file_name - if source_file.exists(): shutil.copy2(source_file, target_file) + os.chmod(target_file, 0o755) print(f"\n=== Content of {file_name} ===") print((target_file).read_text()) print("=" * 40) @@ -48,6 +48,8 @@ def get_trial_count(db_path: Path, study_name: str) -> int: Returns: int: Number of trials for the specified study """ + if not db_path.exists(): + raise AssertionError("Database file does not exist") conn = sqlite3.connect(db_path) cursor = conn.cursor() cursor.execute( @@ -74,7 +76,8 @@ def get_trial_values(db_path: Path, study_name: str) -> list[float]: Returns: list[float]: List of trial values in order of trial number """ - + if not db_path.exists(): + raise AssertionError("Database file does not exist") conn = sqlite3.connect(db_path) cursor = conn.cursor() cursor.execute( @@ -97,20 +100,16 @@ def get_trial_values(db_path: Path, study_name: str) -> list[float]: def modify_config(config_path: Path, study_name: str, n_trials: int, db_name: str) -> Path: + """Modify config file with new study name and number of trials""" with open(config_path) as f: content = f.read() - content = content.replace("study_name: my_study", f"study_name: {study_name}") content = content.replace("n_trials: 30", f"n_trials: {n_trials}") - if db_name: - db_path = config_path.parent / db_name - content = content.replace("aiaccel_storage.db", str(db_path.absolute())) - + content = content.replace("url: sqlite:///aiaccel_storage.db", f"url: sqlite:///{db_name}") new_config_path = config_path.parent / f"config_{study_name}.yaml" with open(new_config_path, "w") as f: f.write(content) - return new_config_path @@ -143,6 +142,9 @@ def test_optimization_consistency(temp_dir: Path) -> None: assert len(normal_results) == 30, "Normal execution should have 30 trials" normal_best = min(normal_results) + trial_count = get_trial_count(temp_dir / normal_db, study_name_normal) + assert trial_count == 30 + # Split execution with 15 + 15 trials study_name_split = f"test_study_{uuid.uuid4().hex[:8]}" split_config = modify_config(temp_dir / "config.yaml", study_name_split, 15, split_db) @@ -151,19 +153,19 @@ def test_optimization_consistency(temp_dir: Path) -> None: with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(split_config), "--resumable"]): main() - db_path = temp_dir / split_db - trial_count = get_trial_count(db_path, study_name_split) + trial_count = get_trial_count(temp_dir / split_db, study_name_split) + assert trial_count == 15 # Second 15 trials with patch("sys.argv", ["optimize.py", "objective.sh", "--config", str(split_config), "--resume"]): main() - trial_count = get_trial_count(db_path, study_name_split) + trial_count = get_trial_count(temp_dir / split_db, study_name_split) assert trial_count == 30 # Compare results - split_results = get_trial_values(db_path, study_name_split) + split_results = get_trial_values(temp_dir / split_db, study_name_split) split_best = min(split_results) assert len(split_results) == 30, "Split execution should have 30 trials" assert abs(normal_best - split_best) < 1e-6, f"Best values differ: normal={normal_best}, split={split_best}" From c224300e59938c5d4e0bdec5e10284b1c0505d18 Mon Sep 17 00:00:00 2001 From: Yoshiaki Bando Date: Mon, 9 Dec 2024 17:17:27 +0900 Subject: [PATCH 04/18] Update documents (#402) * Update index.rst * Update docs * Fix dependencies --- docs/source/api_reference/index.rst | 7 +---- docs/source/api_reference/torch.rst | 6 ++--- docs/source/api_reference/utils.rst | 13 ++++++++++ docs/source/conf.py | 1 + docs/source/index.rst | 40 +++++++++++++++++------------ pyproject.toml | 1 + 6 files changed, 43 insertions(+), 25 deletions(-) create mode 100644 docs/source/api_reference/utils.rst diff --git a/docs/source/api_reference/index.rst b/docs/source/api_reference/index.rst index 57be2de2b..f1d204dc6 100644 --- a/docs/source/api_reference/index.rst +++ b/docs/source/api_reference/index.rst @@ -3,15 +3,10 @@ API Reference ************* -* :ref:`genindex` -* :ref:`modindex` - ----- - .. toctree:: :maxdepth: 2 torch hpo - .. utils \ No newline at end of file + utils \ No newline at end of file diff --git a/docs/source/api_reference/torch.rst b/docs/source/api_reference/torch.rst index 49cfd44be..e90c0962b 100644 --- a/docs/source/api_reference/torch.rst +++ b/docs/source/api_reference/torch.rst @@ -1,5 +1,5 @@ -PyTorch Utilities -================= +PyTorch/Lightning Toolkit +========================= Datasets @@ -29,4 +29,4 @@ Lightning Utilities ABCIEnvironment OptimizerLightningModule - OptimizerConfig \ No newline at end of file + OptimizerConfig diff --git a/docs/source/api_reference/utils.rst b/docs/source/api_reference/utils.rst new file mode 100644 index 000000000..a67f286a5 --- /dev/null +++ b/docs/source/api_reference/utils.rst @@ -0,0 +1,13 @@ +Miscellaneous Utilities +======================= + + +Config Utilities +---------------- + +.. currentmodule:: aiaccel.utils +.. autosummary:: + :toctree: generated/ + + print_config + pathlib2str_config diff --git a/docs/source/conf.py b/docs/source/conf.py index 0bbaf73e6..d26fa4d46 100644 --- a/docs/source/conf.py +++ b/docs/source/conf.py @@ -43,6 +43,7 @@ "myst_parser", "pydata_sphinx_theme", "sphinx.ext.doctest", + "sphinx_design", ] # Add any paths that contain templates here, relative to this directory. diff --git a/docs/source/index.rst b/docs/source/index.rst index c2437398e..2605adefd 100644 --- a/docs/source/index.rst +++ b/docs/source/index.rst @@ -4,18 +4,34 @@ contain the root `toctree` directive. -aiaccel Documentation -=================== +Aiaccel +======= + +AIST toolkit for accelerating machine learning research. + + +:octicon:`cpu;1em;sd-text-primary` High-Performance Computing (HPC) + Intended to use in the HPC clusters including AI Bridging Cloud Infrastructure (ABCI). + +:octicon:`server;1em;sd-text-primary` Highly Modular Design + Designed to let you pick up any part of aiaccel with minimal dependencies as you prefer. + +:octicon:`zap;1em;sd-text-primary` High Compatibility + Compatible with the modern standard frameworks such as PyTorch Lightning and Optuna. -Overview --------- -This software is a hyperparameter optimization library designed for the AI Bridging Cloud Infrastructure (ABCI). -It addresses hyperparameter optimization challenges in AI technologies such as deep learning and multi-agent simulations. -Currently, it supports five optimization algorithms: Random Search, Grid Search, Sobol Sequence, Nelder-Mead Method, and TPE. +.. grid:: + .. grid-item-card:: PyTorch/Lightning Toolkit + :link: api_reference/torch.html + + Training toolkit for HPC clusters. + + .. grid-item-card:: Hyperparameter Optimization (HPO) + :link: api_reference/hpo.html + + Ready-to-use HPO algorithms/tools. -.. _`AI Bridging Cloud Infrastructure (ABCI)`: https://abci.ai/ Getting Started @@ -49,20 +65,12 @@ API Reference Contribution Guide -------- - .. toctree:: :maxdepth: 2 contribution_guide.md -Index and Search --------- - -* :ref:`genindex` -* :ref:`modindex` -* :ref:`search` - Acknowledgments -------- * Part of this work was developed under a commissioned project of the New Energy and Industrial Technology Development Organization (NEDO). diff --git a/pyproject.toml b/pyproject.toml index 193480426..f42b1a275 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -49,6 +49,7 @@ dev = [ "sphinx-fontawesome", "sphinx-rtd-theme", "pydata-sphinx-theme", + "sphinx_design", "types-colorama", "undecorated", "pandas", From 1dea616c8efcbbffdecd147c382c7ac58578abcb Mon Sep 17 00:00:00 2001 From: 3bisuoka <117958864+3bisuoka@users.noreply.github.com> Date: Wed, 11 Dec 2024 00:48:56 +0900 Subject: [PATCH 05/18] Added docs for v2 (#403) * updated contribution_guide.md * Split contribution_guide.md --------- Co-authored-by: Yoshiaki Bando --- docs/source/contribution_guide/index.rst | 11 + .../issues.md} | 20 +- .../contribution_guide/pull_requests.md | 233 ++++++++++++++++++ docs/source/index.rst | 2 +- 4 files changed, 251 insertions(+), 15 deletions(-) create mode 100644 docs/source/contribution_guide/index.rst rename docs/source/{contribution_guide.md => contribution_guide/issues.md} (65%) create mode 100644 docs/source/contribution_guide/pull_requests.md diff --git a/docs/source/contribution_guide/index.rst b/docs/source/contribution_guide/index.rst new file mode 100644 index 000000000..36a7cf247 --- /dev/null +++ b/docs/source/contribution_guide/index.rst @@ -0,0 +1,11 @@ +Contribution Guide +================== + +Thank you for contributing to aiaccel! +This document introduces how to contribute. + +.. toctree:: + :maxdepth: 2 + + issues + pull_requests \ No newline at end of file diff --git a/docs/source/contribution_guide.md b/docs/source/contribution_guide/issues.md similarity index 65% rename from docs/source/contribution_guide.md rename to docs/source/contribution_guide/issues.md index 8d6d9b828..79b1e284d 100644 --- a/docs/source/contribution_guide.md +++ b/docs/source/contribution_guide/issues.md @@ -1,26 +1,18 @@ -# Contribution Guide - -Thank you for contributing to aiaccel! -This document introduces how to contribute. - -## Issues +# Issues When you find any problems or have requests for new features, please first check to ensure that there is no duplicate issues already posted. We usually use Japanese for internal development, but we are more than happy to communicate with you in English. ### Bug report A bug report should briefly summarize the following details: * What the bug is -* Steps to reproduce the the bug +* Steps to reproduce the bug * What you expected to happen * The execution environment ### Feature request +A feature request should briefly summarize the following details: -## Pull request - -### Documentation - -### Test - -### Coding style \ No newline at end of file +- If a bug is relevant, what it is +- What new features do you want to achieve +- Description of the implementation you consider diff --git a/docs/source/contribution_guide/pull_requests.md b/docs/source/contribution_guide/pull_requests.md new file mode 100644 index 000000000..17eb09790 --- /dev/null +++ b/docs/source/contribution_guide/pull_requests.md @@ -0,0 +1,233 @@ +# Pull Requests + +When you want to the modified code to be reflected in the repository, please execute pull request. + +### Procedures + +- Please fork aiaccel repository on GitHub. +- After forking, run `git clone` command for aiaccel repository. + +~~~bash +git clone https://github.com/[YOUR USERNAME]/aiaccel.git +~~~ + +### Development +- Update a local repository to the latest version. + +~~~bash +git checkout main +git pull upstream main +~~~ + +- Make a branch. + +~~~bash +git checkout -b feature/add-new-feature +~~~ + +- Commit on local by using `git add` and `git commit` command as you progress. + + - The commit message describes the motivation for the change, the nature of the bug, or details the enhancement. + - The message should be written in such a way that their contents can be understood without refering code. + + +### Submitting + +Before submit *Pull request*, confirm the following: +- Did you discuss it with other developer on issues in advance? +- Can it be distributed under the MIT licence? +- Is there appropriate [unit tests](#test)? +- Can the [unit tests](#test) be run on local? +- Does the public function have a docstring? +- Can the [documentation](#documentation-wip) be rendered correctly? +- Is the [coding style](#coding-style) appropriate? +- Is the commit message appropriate? +- For larger commit, please provide the example (docs/source/examples) and the description of module level. +- If you are adding complied codes, have you modified setup.py? + +After confirming above, do following: +- Push changes to the fork on GitHub. + +~~~bash +git push origin feature/add-new-feature +~~~ + +- Enter your GitHub username and password. +- Move to the GitHub web page and write the title and message, noting the following. + - Title + - Briefly describe the changes. + - Codes should be enclosed in backquotes. + - Do not end with a period. + - Descriptions + - Write the motivation. + - Write the changes. + - If the related issues can be closed, please close it with `Close #N`. + - If work-in-progress, write the remaining tasks. +- Submit the pull request. + +## Review processes + +- Other developers can contribute comments to improve implementations, documentations, and coding styles in the pull request. +- When updating codes in the pull request, please commit the changes in the local repository and push the changes to the fork only if they have been successfully tested in the local environment. +- If the pull request has been reviewed and approved by at least one member of the aiaccel development team, it will be merged into the main branch. + +# Documentation (WIP) + +## Docstrings + +- Write a basic description of the implemented functions, the types and meanings of parameters and return values, and examples of their usage. +- Write in accordance with the [Google Python Style Guide](https://google.github.io/styleguide/pyguide.html#38-comments-and-docstrings). +- See also Coding Conventions(#Coding style). + +## Documentation + +- Create source files for documentation in a directory under docs. +- The recommended document file format is markdown format. +- Create documentation for any major feature addtions. + +## Confirming rendering + +If you have added, changed, or modified documents, make sure that it renders correctly in the local environment. +Move to the aiaccel directory and execute the following command to generate an API reference. + +~~~bash +cd aiaccel +sphinx-apidoc -f -o docs/source/api_reference aiaccel +~~~ + +Move to aiaccel/docs and build html files to see how the document is rendered. + +~~~bash +cd docs +make html +~~~ + +The built HTML format files are generated under docs/build/html. +Execute the following command in aiaccel/docs to generate multilingual documents. + +~~~bash +make gettext +sphinx-intl update -p build/gettext -l en -l ja +~~~ + +# Test + +## Adding tests + +- aiaccel uses pytest for testing. +- Create a directory for unit test under tests directory. + - The directory structure under aiaccel/tests/unit corresponds to that under aiaccel/aiaccel, except for a few modeules such as config.py. For example, the test for aiaccel/aiaccel/optimizer/abstract_optimizer.py is aiaccel/tests/unit/optimzier_test/test_abstract_optimizer.py. +- If you have added a new feature or bug fix, please create codes for testing. + + +## Running tests (WIP) + +- Move to the aiaccel directory and execute the following command to run all codes for testing on the local environment. + +~~~bash +cd aiaccel +pytest +~~~ + +- Specify a file name as an argument to run only specific code. + +~~~bash +pytest tests/unit/optimizer_test/test_abstract_optimizer.py +~~~ + +- In addition, execute the following command to check coding styles. + +~~~bash +pycodestyle aiaccel examples +flake8 aiaccel examples +~~~ + + +## Coverages + +No strict criteria for code coverage have been set, but this value should be fully considered when designing test. Plase note the following cases. + +- Significantly lower overall score. +- Abnormally low coverage of a class or module. +- Test does not cover a specific branch of the if statement. + +### Measuerment coverages + +Run pytest with the option `--cov` to measure C0 coverage. + +~~~bash +pytest --cov=aiaccel +~~~ + +- Replace `aiaccel` with the appropriate path to measure only the coverage of a specific test code. +- Run pytest with the option `--cov` and `--cov-branch` to measure C1 coverage. + +~~~bash +pytest --cov=aiaccel --cov-branch +~~~ + +# Coding style + +## Basic rules + +- Write source codes for aiaccel in Python. +- Coding style should follow PEP8. + - Validate the coding style by using pycodestyle and flake8 in aiaccel. + - See also Docstrings below. +- Write type hints whenever possible, but there is no type hint validation in aiaccel. + - When using a built-in, e.g. `list` as a type hint, run future-import to support Python 3.8 in aiaccel. +- Use [`numpy.random.RandomState`](https://numpy.org/doc/1.16/reference/generated/numpy.random.RandomState.html) to generate a random value and maintain the compatibility with [Optuna](https://github.com/optuna/optuna) used by aiaccel. + +## Docstrings + +Basically, write docstrings in accordance with the [Google Python Style Guide](https://google.github.io/styleguide/pyguide.html#38-comments-and-docstrings). However, please note the following exceptions. + +- Docstrings for each module are not necessarily required. +- In `Args:` section, a parameter type is described in parentheses after a parameter name. +- Add `Example:` section as needed. +- Include the docstring of `__init__` method in a docstring of class. Do not write it under `__init__`. +- Use sphinx-style links to Python objects. +- Using VSCode as an editor, [autoDocstring](https://marketplace.visualstudio.com/items?itemName=njpwerner.autodocstring) is useful for generating docstrings. + +### Example + +```python +class ExampleClass: + """Summary of class. + + There can be additional description(s) of this class. + + Args: + param1 (type_of_param1): Description of `param1` which + is given when __init__ method is called. + param2 (type_of_param2): Description of `param2`. + + Attributions: + param1 (type_of_param1): Description of `param1`. + param2 (type_of_param2): Description of `param2`. + param3 (type_of_param3): Description of 'param3`. + """ + + def __init__(self, param1: type_of_param1, param2: type_of_param2): + self.param1 = param1 + self.param2 = param2 + self.param3 = generate_param3() + + def method(self, arg1: type_of_arg1) -> type_of_return: + """Recieves `type_of_arg1` object and returns return_of_method. + + Args: + arg1 (type_of_arg1): Description of `arg1`. + + Returns: + type_of_return: Description of return value. If this method + returns nothing, this section can be omitted. + + Raise: + TypeOfException: Description of Exception. + + """ + ... + return return_of_method + +``` \ No newline at end of file diff --git a/docs/source/index.rst b/docs/source/index.rst index 2605adefd..8f9409f3a 100644 --- a/docs/source/index.rst +++ b/docs/source/index.rst @@ -68,7 +68,7 @@ Contribution Guide .. toctree:: :maxdepth: 2 - contribution_guide.md + contribution_guide/index.rst Acknowledgments From 0cc4ca825baf50ca0a9bee32645f1d3344e1cec2 Mon Sep 17 00:00:00 2001 From: Yoshiaki Bando Date: Wed, 11 Dec 2024 00:52:22 +0900 Subject: [PATCH 06/18] Update aiaccel logo to a transparent one (#404) * Update logo * Update conf.py --- README.md | 2 +- docs/image/favicon.ico | Bin 146199 -> 117545 bytes docs/image/logo_aiaccel.png | Bin 188623 -> 54795 bytes docs/image/logo_aiaccel_padding.png | Bin 252249 -> 0 bytes docs/source/_static/custom_color.css | 17 ++++++++++++----- docs/source/conf.py | 8 +++----- 6 files changed, 16 insertions(+), 11 deletions(-) mode change 100644 => 100755 docs/image/favicon.ico mode change 100644 => 100755 docs/image/logo_aiaccel.png delete mode 100644 docs/image/logo_aiaccel_padding.png diff --git a/README.md b/README.md index 1646dbfca..1c542e022 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@
-# aiaccel: a library for accelerating research on ABCI +# Aiaccel: AIST Toolkit for accelerating machine learning research [![GitHub license](https://img.shields.io/github/license/aistairc/aiaccel.svg)](https://github.com/aistairc/aiaccel) [![Supported Python version](https://img.shields.io/badge/Python-3.8-blue)](https://github.com/aistairc/aiaccel) [![Documentation Status](https://readthedocs.org/projects/aiaccel/badge/?version=latest)](https://aiaccel.readthedocs.io/en/latest/) diff --git a/docs/image/favicon.ico b/docs/image/favicon.ico old mode 100644 new mode 100755 index 97a0289459fdac63239df202cad46cd5db9d777c..a61d61c16db7ce8cc325b7cfc725d0fb1b72013a GIT binary patch literal 117545 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

D8y3F7Qju^vy;)-bBu+Ib=X$r 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 literal 146199 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