From f77f4c7ad389b3c611c8d3ee6b7ddab8e891a998 Mon Sep 17 00:00:00 2001 From: Aldo Date: Mon, 2 Sep 2024 14:53:28 +0200 Subject: [PATCH] test: fix linting and tests - update nbmake to 1.5.4 - add needed fixtures for tests - fix mypy and other linting checks - remove safety checks (not open source anymore) - remove checks that are incompatible for different OS --- .github/workflows/lint.yml | 2 +- .github/workflows/test.yml | 3 +++ black_it/calibrator.py | 8 +++++--- black_it/loss_functions/gsl_div.py | 2 +- black_it/loss_functions/likelihood.py | 12 ++++++++---- black_it/plot/plot_results.py | 4 +++- black_it/samplers/xgboost.py | 6 +++--- black_it/search_space.py | 2 +- examples/models/simple_models.py | 2 +- examples/models/sir/simlib.py | 4 ++-- tests/fixtures/data/test_sir_w_breaks_python.npy | Bin 0 -> 2528 bytes tests/test_examples/test_main.py | 1 - tests/test_samplers/test_xgboost.py | 7 ++++--- tox.ini | 6 +++--- 14 files changed, 35 insertions(+), 24 deletions(-) create mode 100644 tests/fixtures/data/test_sir_w_breaks_python.npy diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index b688405e..6264bf4b 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -36,4 +36,4 @@ jobs: run: tox -e check-copyright - name: Misc checks run: | - tox -e bandit,safety + tox -e bandit diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 6087e1b7..fd33e843 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -46,6 +46,9 @@ jobs: # https://stackoverflow.com/questions/73029883/could-not-find-hdf5-installation-for-pytables-on-m1-mac echo "HDF5_DIR=/opt/homebrew/opt/hdf5" >> $GITHUB_ENV echo "BLOSC_DIR=/opt/homebrew/opt/c-blosc" >> $GITHUB_ENV + # - if: ${{ matrix.python-version == '3.12' }} + # name: Install setuptools + # run: pip install setuptools - if: ${{ (matrix.os == 'ubuntu-latest') || (matrix.os == 'macos-latest') }} name: Unit tests and coverage (ubuntu-latest, macos-latest) run: | diff --git a/black_it/calibrator.py b/black_it/calibrator.py index 579a1648..419bd4a5 100644 --- a/black_it/calibrator.py +++ b/black_it/calibrator.py @@ -128,9 +128,11 @@ def __init__( # noqa: PLR0913 # initialize arrays self.params_samp = np.zeros((0, self.param_grid.dims)) self.losses_samp = np.zeros(0) - self.batch_num_samp = np.zeros(0, dtype=int) - self.method_samp = np.zeros(0, dtype=int) - self.series_samp = np.zeros((0, self.ensemble_size, self.N, self.D)) + self.batch_num_samp: NDArray[np.int64] = np.zeros(0, dtype=int) + self.method_samp: NDArray[np.int64] = np.zeros(0, dtype=int) + self.series_samp: NDArray[np.float64] = np.zeros( + (0, self.ensemble_size, self.N, self.D), + ) # initialize variables before calibration self.n_sampled_params = 0 diff --git a/black_it/loss_functions/gsl_div.py b/black_it/loss_functions/gsl_div.py index f70696bc..28af0cbc 100644 --- a/black_it/loss_functions/gsl_div.py +++ b/black_it/loss_functions/gsl_div.py @@ -270,7 +270,7 @@ def get_words(time_series: NDArray[np.float64], length: int) -> NDArray: "the chosen word length is too high", exception_class=ValueError, ) - tsw = np.zeros(shape=(tswlen,), dtype=np.int32) + tsw: NDArray[np.float64] = np.zeros(shape=(tswlen,), dtype=np.int32) for i in range(length): k = 10 ** (length - i - 1) diff --git a/black_it/loss_functions/likelihood.py b/black_it/loss_functions/likelihood.py index 39243941..bef9f3bf 100644 --- a/black_it/loss_functions/likelihood.py +++ b/black_it/loss_functions/likelihood.py @@ -18,7 +18,7 @@ from __future__ import annotations import warnings -from typing import TYPE_CHECKING, Callable +from typing import TYPE_CHECKING, Callable, cast import numpy as np @@ -82,9 +82,13 @@ def compute_loss( Returns: The loss value. """ - r = sim_data_ensemble.shape[0] # number of repetitions - s = sim_data_ensemble.shape[1] # simulation length - d = sim_data_ensemble.shape[2] # number of dimensions + sim_data_ensemble_shape: tuple[int, int, int] = cast( + tuple[int, int, int], + sim_data_ensemble.shape, + ) + r = sim_data_ensemble_shape[0] # number of repetitions + s = sim_data_ensemble_shape[1] # simulation length + d = sim_data_ensemble_shape[2] # time series dimension if self.coordinate_weights is not None: warnings.warn( # noqa: B028 diff --git a/black_it/plot/plot_results.py b/black_it/plot/plot_results.py index b4576d25..ed42c167 100644 --- a/black_it/plot/plot_results.py +++ b/black_it/plot/plot_results.py @@ -33,6 +33,8 @@ import os from collections.abc import Collection + from numpy.typing import NDArray + def _get_samplers_id_table(saving_folder: str | os.PathLike) -> dict[str, int]: """Get the id table of the samplers from the checkpoint. @@ -299,7 +301,7 @@ def plot_sampling_interact(saving_folder: str | os.PathLike) -> None: data_frame = pd.read_csv(calibration_results_file) max_bn = int(max(data_frame["batch_num_samp"])) - all_bns = np.arange(max_bn + 1, dtype=int) + all_bns: NDArray[np.int64] = np.arange(max_bn + 1, dtype=int) indices_bns = np.array_split(all_bns, min(max_bn, 3)) dict_bns = {} diff --git a/black_it/samplers/xgboost.py b/black_it/samplers/xgboost.py index 275cea5b..da9b6d07 100644 --- a/black_it/samplers/xgboost.py +++ b/black_it/samplers/xgboost.py @@ -28,9 +28,9 @@ if TYPE_CHECKING: from numpy.typing import NDArray -MAX_FLOAT32 = np.finfo(np.float32).max -MIN_FLOAT32 = np.finfo(np.float32).min -EPS_FLOAT32 = np.finfo(np.float32).eps +MAX_FLOAT32: float = cast(float, np.finfo(np.float32).max) +MIN_FLOAT32: float = cast(float, np.finfo(np.float32).min) +EPS_FLOAT32: float = cast(float, np.finfo(np.float32).eps) class XGBoostSampler(MLSurrogateSampler): diff --git a/black_it/search_space.py b/black_it/search_space.py index 41a55e1c..2e03e1bd 100644 --- a/black_it/search_space.py +++ b/black_it/search_space.py @@ -72,7 +72,7 @@ def __init__( self._param_grid: list[NDArray[np.float64]] = [] self._space_size = 1 for i in range(self.dims): - new_col = np.arange( + new_col: NDArray[np.float64] = np.arange( parameters_bounds[0][i], parameters_bounds[1][i] + 0.0000001, parameters_precision[i], diff --git a/examples/models/simple_models.py b/examples/models/simple_models.py index 9ee8ef6e..010b30f1 100644 --- a/examples/models/simple_models.py +++ b/examples/models/simple_models.py @@ -31,7 +31,7 @@ from typing import TYPE_CHECKING import numpy as np -from scipy.stats import alpha, bernoulli +from scipy.stats import alpha, bernoulli # type: ignore[import-untyped] if TYPE_CHECKING: from collections.abc import Sequence diff --git a/examples/models/sir/simlib.py b/examples/models/sir/simlib.py index 656f6014..8dd1265e 100644 --- a/examples/models/sir/simlib.py +++ b/examples/models/sir/simlib.py @@ -62,7 +62,7 @@ def parse_simulator_output(stdout: str) -> list[dict[str, int]]: def _build_simulator_cmdline( docker_image_name: str, - sim_params: dict[str, str], + sim_params: dict[str, float], ) -> list[str]: """Convert a configuration object in a list of command line parameters. @@ -107,7 +107,7 @@ def _build_simulator_cmdline( def execute_simulator( path_to_simulator: str, - sim_params: dict[str, str], + sim_params: dict[str, float], ) -> list[dict[str, int]]: """Execute the simulator with the given parameters, and return a structured output. diff --git a/tests/fixtures/data/test_sir_w_breaks_python.npy b/tests/fixtures/data/test_sir_w_breaks_python.npy new file mode 100644 index 0000000000000000000000000000000000000000..5825c50b3d91dda1c471078362d77927e30b0f1f GIT binary patch literal 2528 zcmeIxNoW%R6b9hei)iqWn>lzGBs3L*Of5=~Y6m205xa<$Sc07{iEWWKrged$4243F z3UN7j5IP`u@Y2DG;zdXF;EE$C6@(HMt%%FG)#AzIf8$}^AXM?#cX|9@ejdprIo;H@ zqh(JO9iov~PiCk)AKReB>a&ShT#01|^TYYhfsVm^Pp0BqI`Yi)0Qu8niHxAN=UCbFZixIg*9*VpSy$j)}x z=i0<`WOekj-w#eBTjTtG$s4We345RS`8>CmKZZNi->^LCNzPRyb{g(?01* zxE}D$d|$eu!CmRJ5w7;i`|IFVz}Lb{0k7rz0guC#K6$?et_8dr-V*RATo3q4croA+ yxVc~tqi+ZLOX1FfozO1@`hRk_fy(0s`hV+{E9L2z&zX7A7oUUo1bF?&-^nlYK|k66 literal 0 HcmV?d00001 diff --git a/tests/test_examples/test_main.py b/tests/test_examples/test_main.py index 9cbb41e2..2a49b675 100644 --- a/tests/test_examples/test_main.py +++ b/tests/test_examples/test_main.py @@ -40,5 +40,4 @@ class TestMainExample(BaseMainExampleTestClass): "METHOD: BestBatchSampler", *[f"BATCH NUMBER: {i}" for i in range(1, nb_batches + 1)], TRUE_PARAMETERS_STR, - BEST_PARAMETERS_STR, ) diff --git a/tests/test_samplers/test_xgboost.py b/tests/test_samplers/test_xgboost.py index 23a36369..590f5527 100644 --- a/tests/test_samplers/test_xgboost.py +++ b/tests/test_samplers/test_xgboost.py @@ -15,6 +15,7 @@ # along with this program. If not, see . """This module contains tests for the xgboost sampler.""" import sys +from typing import cast import numpy as np @@ -34,9 +35,9 @@ else: expected_params = np.array([[0.24, 0.26], [0.37, 0.21], [0.43, 0.14], [0.11, 0.04]]) -MAX_FLOAT32 = np.finfo(np.float32).max -MIN_FLOAT32 = np.finfo(np.float32).min -EPS_FLOAT32 = np.finfo(np.float32).eps +MAX_FLOAT32: float = cast(float, np.finfo(np.float32).max) +MIN_FLOAT32: float = cast(float, np.finfo(np.float32).min) +EPS_FLOAT32: float = cast(float, np.finfo(np.float32).eps) def test_xgboost_2d() -> None: diff --git a/tox.ini b/tox.ini index 0aa6108d..dbf82800 100644 --- a/tox.ini +++ b/tox.ini @@ -36,9 +36,9 @@ commands = # test environment for notebooks [testenv:py{39,310,311,312}-nb] deps = - pytest==7.4.2 - mesa==2.1.1 - nbmake==1.4.3 + pytest==7.4.2 # current latest: 8.3.2 + mesa==2.1.1 # current latest: 2.3.3 + nbmake==1.5.4 commands = pytest examples/tests_on_toy_model.ipynb --nbmake --nbmake-timeout=300 [testenv:mypy]