diff --git a/README.md b/README.md index c296eab..1757678 100644 --- a/README.md +++ b/README.md @@ -3,302 +3,17 @@ [![PyPI - Version](https://img.shields.io/pypi/v/antares-study-version.svg)](https://pypi.org/project/antares-study-version) [![PyPI - Python Version](https://img.shields.io/pypi/pyversions/antares-study-version.svg)](https://pypi.org/project/antares-study-version) ------ - -**Table of Contents** - -- [Overview](#overview) -- [Installation](#installation) -- [Usage](#usage) - - [StudyVersion](#studyversion) - - [SolverVersion](#solverversion) - - [Pydantic model](#pydantic-model) -- [Development](#development) - - [Development tasks](#development-tasks) - - [Building the package](#building-the-package) -- [License](#license) -- [Changelog](CHANGELOG.md) - -## Overview +![antares-study-version-title](docs/assets/antares-study-version-title.jpeg) The `antares-study-version` package defines `StudyVersion` and `SolverVersion` classes to manage version numbers. -It can be used to manage the version of a study, but also the version -of [Antares Solver](https://github.com/AntaresSimulatorTeam/Antares_Simulator). -It supports the [semver](https://semver.org/) format ("major.minor.patch") and the integer format -(major×100 + minor×10 + patch), which is specific to Antares. - -This module harmonizes the management of versions in Antares: - -- at the level of Antares studies (configuration files, database, etc.) -- at the level of Antares applications, in particular [AntaREST](https://github.com/AntaresSimulatorTeam/AntaREST/). - -In the data of a study and in the programs, we encounter several version formats: - -- dotted string (ex. `"8.7"` or `"8.7.2"`), -- compact string (ex. `"870"`), -- integer (ex. `870`). -- tuples or lists (ex. `(8, 7)` or `[8, 7, 2]`). -- dictionaries (ex. `{"major": 8, "minor": 7, "patch": 2}`). - -For instance, since -[version 9.0](https://antares-simulator.readthedocs.io/en/latest/reference-guide/13-file-format/#v900) -of Antares Solver, versions are stored as dotted strings; -the compact format is now obsolete (backward compatibility is ensured for versions prior to 9.0); - -For instance, the `study.antares` configuration file now uses the "X.Y" format for the study version instead -of the "XYZ" format. - -```ini -[antares] -version = 9.1 -caption = My Study -created = 1618413128 -lastsave = 1625583204 -author = John DOE -``` - -This module allows to convert these formats to each other, and to compare versions. - -## Installation - -```console -pip install antares-study-version -``` - -## Usage - -This package provides a `StudyVersion` class to manage study version numbers, -and a `SolverVersion` class to manage Antares Solver version numbers. - -The difference between `StudyVersion` and `SolverVersion` is that Solver versions are generally on 3 digits -(with the `major`, `minor` and `patch` components), while study versions are on 2 digits -(with the `major` and `minor` components only), and the `patch` component is not used (always 0). - -### StudyVersion - -Using the `antares-study-version` module is straightforward: - -```python -from antares.study.version import StudyVersion - -version = StudyVersion(8, 7, 2) # patch component is not used -print(version) # 8.7 -``` - -You can also create a version object from a dotted string: - -```python -from antares.study.version import StudyVersion - -version = StudyVersion.parse("8.7") -print(version) # 8.7 -``` - -You can create a version object from a compact string: - -```python -from antares.study.version import StudyVersion - -version = StudyVersion.parse("870") -print(version) # 8.7 -``` - -You can create a version object from an integer: - -```python -from antares.study.version import StudyVersion - -version = StudyVersion.parse(870) -print(version) # 8.7 -``` - -You can compare versions: - -```python -from antares.study.version import StudyVersion - -version1 = StudyVersion(8, 6) -version2 = StudyVersion(8, 7) -print(version1 < version2) # True -``` - -You can convert a version to string using format specifiers: - -```python -from antares.study.version import StudyVersion - -version = StudyVersion(8, 7) -print(f"{version}") # 8.7 -print(f"{version:02d}") # 08.07 -print(f"{version:03d}") # 08.07.00 -print(f"{version:ddd}") # 870 -``` - -You can convert a version to an integer: - -```python -from antares.study.version import StudyVersion - -version = StudyVersion(8, 7) -print(int(version)) # 870 -``` - -### SolverVersion - -Of course, the same operations can be done with `SolverVersion` objects, but with 3 digits: - -```python -from antares.study.version import SolverVersion - -version = SolverVersion(8, 7, 2) -print(version) # 8.7.2 -``` - -Objects of the `StudyVersion` and `SolverVersion` classes can be compared to each other: - -```python -from antares.study.version import StudyVersion, SolverVersion - -study_version = StudyVersion(8, 7) -solver_version = SolverVersion(8, 7, 2) -print(study_version <= solver_version) # True -``` - -### Pydantic model -You can even use the `StudyVersion` or `SolverVersion` classes in a Pydantic model: - -```python -import datetime -import typing as t -import uuid - -from pydantic import BaseModel, Field, validator - -from antares.study.version import StudyVersion - - -class StudyDTO(BaseModel): - id: uuid.UUID = Field(default_factory=lambda: uuid.uuid4()) - name: str - version: StudyVersion - created: datetime.datetime = Field(default_factory=lambda: datetime.datetime.now(tz=datetime.timezone.utc)) - - @validator("version", pre=True) - def _validate_version(cls, v: t.Any) -> StudyVersion: - return StudyVersion.parse(v) - - -study = StudyDTO(name="foo", version=StudyVersion(4, 5)) -obj = study.json() -print(obj) -# { -# "created": "2024-12-31T12:30:00+00:00", -# "id": "4930a577-63d2-4ea9-b0b9-581110d97475", -# "name": "foo", -# "version": {"major": 4, "minor": 5, "patch": 0} -# } -``` - -## Development - -This projet uses [Hach](https://hatch.pypa.io/latest/) to manage the development environment. - -### Project setup - -➢ To install the [development environment](https://hatch.pypa.io/latest/environment/), run: - -```shell -hatch env create -``` - -> See [hatch env create](https://hatch.pypa.io/latest/cli/reference/#hatch-env-create) documentation - -This command will create a virtual environment and install the development dependencies. - -> NOTE: `hatch` creates a virtual environment in the `~/.local/share/hatch/env/virtual/antares-study-version` directory. - -➢ To activate the virtual environment, run: - -```shell -hatch shell -``` - -> See [hatch shell](https://hatch.pypa.io/latest/cli/reference/#hatch-shell) documentation - -This command will spawn a new shell with the virtual environment activated. Use Ctrl+D to exit the shell. - -> NOTE: this command will display the full path to the virtual environment. -> You can use it to configure PyCharm or Visual Studio Code to use this virtual environment. - -### Development tasks - -➢ To format and lint the source code with [ruff](https://docs.astral.sh/ruff/), run: - -```shell -hatch fmt -``` - -> See [hatch fmt](https://hatch.pypa.io/latest/cli/reference/#hatch-fmt) documentation - -➢ To run the tests on the current Python version, run: - -```shell -hatch run test -``` - -> See [hatch run](https://hatch.pypa.io/latest/cli/reference/#hatch-run) documentation - -➢ To run the tests on Python 3.12, for example, run: - -```shell -hatch run all.py3.12:test -``` - -➢ To generate the test coverage report, run: - -```shell -hatch run cov -``` - -This command will run the unit tests and generate a coverage report in the `htmlcov` directory. - -➢ To check the typing with [mypy](http://mypy-lang.org/), run: - -```shell -hatch run types:check -``` - -➢ To check the typing on unit tests, run: - -```shell -hatch run types:check-tests -``` - -### Building the package - -➢ To build the package, run: - -```shell -hatch build -``` - -This command will create a `dist` directory with the built package. - -➢ To build the package and upload it to [PyPI](https://pypi.org/), run: - -```shell -hatch publish -``` - -➢ To clean the project, run: - -```shell -hatch clean -``` - -This command will remove the `dist` directory. +----- -## License +**Table of Contents** -`antares-study-version` is distributed under the terms of the [MIT](https://spdx.org/licenses/MIT.html) license. +- [overview.md](docs/overview.md) +- [installation.md](docs/installation.md) +- [usage.md](docs/usage.md) +- [development.md](docs/development.md) +- [Changelog](docs/CHANGELOG.md) +- [LICENSE.md](LICENSE.md) diff --git a/CHANGELOG.md b/docs/CHANGELOG.md similarity index 70% rename from CHANGELOG.md rename to docs/CHANGELOG.md index 004c84f..6d667be 100644 --- a/CHANGELOG.md +++ b/docs/CHANGELOG.md @@ -15,17 +15,17 @@ v0.1.1 (2024-04-10) ### Docs -* [README.md](README.md): update doc, fix typo, add a link to the change log +* `README.md`: update doc, fix typo, add a link to the change log ### Build * create [CHANGELOG.md](CHANGELOG.md) and update the release date -* add [update_version.py](scripts/update_version.py) script to create or update the changelog +* add `scripts/update_version.py` script to create or update the changelog ### CI * add missing dependency [pytest-freezer](https://pypi.org/project/pytest-freezer/) required for type checking -* create the [GitHub workflows](.github/workflows/python-package.yml) for code style and typing check +* create the `.github/workflows/python-package.yml` GitHub workflow for code style and typing check v0.1.0 (2024-03-20) ------------------- diff --git a/docs/assets/antares-study-version-1024.jpeg b/docs/assets/antares-study-version-1024.jpeg new file mode 100644 index 0000000..589197d Binary files /dev/null and b/docs/assets/antares-study-version-1024.jpeg differ diff --git a/docs/assets/antares-study-version-200.jpeg b/docs/assets/antares-study-version-200.jpeg new file mode 100644 index 0000000..fe9b179 Binary files /dev/null and b/docs/assets/antares-study-version-200.jpeg differ diff --git a/docs/assets/antares-study-version-icon.png b/docs/assets/antares-study-version-icon.png new file mode 100644 index 0000000..597698e Binary files /dev/null and b/docs/assets/antares-study-version-icon.png differ diff --git a/docs/assets/antares-study-version-logo.png b/docs/assets/antares-study-version-logo.png new file mode 100644 index 0000000..1bd0941 Binary files /dev/null and b/docs/assets/antares-study-version-logo.png differ diff --git a/docs/assets/antares-study-version-title.jpeg b/docs/assets/antares-study-version-title.jpeg new file mode 100644 index 0000000..20a5776 Binary files /dev/null and b/docs/assets/antares-study-version-title.jpeg differ diff --git a/docs/development.md b/docs/development.md new file mode 100644 index 0000000..dc1c614 --- /dev/null +++ b/docs/development.md @@ -0,0 +1,123 @@ +# Development + +This projet uses [Hach](https://hatch.pypa.io/latest/) to manage the development environment. + +## Project setup + +➢ To install the [development environment](https://hatch.pypa.io/latest/environment/), run: + +```shell +hatch env create +``` + +> See [hatch env create](https://hatch.pypa.io/latest/cli/reference/#hatch-env-create) documentation + +This command will create a virtual environment and install the development dependencies. + +> NOTE: `hatch` creates a virtual environment in the `~/.local/share/hatch/env/virtual/antares-study-version` directory. + +➢ To activate the virtual environment, run: + +```shell +hatch shell +``` + +> See [hatch shell](https://hatch.pypa.io/latest/cli/reference/#hatch-shell) documentation + +This command will spawn a new shell with the virtual environment activated. Use Ctrl+D to exit the shell. + +> NOTE: this command will display the full path to the virtual environment. +> You can use it to configure PyCharm or Visual Studio Code to use this virtual environment. + +## Development tasks + +➢ To format and lint the source code with [ruff](https://docs.astral.sh/ruff/), run: + +```shell +hatch fmt +``` + +> See [hatch fmt](https://hatch.pypa.io/latest/cli/reference/#hatch-fmt) documentation + +➢ To run the tests on the current Python version, run: + +```shell +hatch run test +``` + +> See [hatch run](https://hatch.pypa.io/latest/cli/reference/#hatch-run) documentation + +➢ To run the tests on Python 3.12, for example, run: + +```shell +hatch run all.py3.12:test +``` + +➢ To generate the test coverage report, run: + +```shell +hatch run cov +``` + +This command will run the unit tests and generate a coverage report in the `htmlcov` directory. + +➢ To check the typing with [mypy](http://mypy-lang.org/), run: + +```shell +hatch run types:check +``` + +➢ To check the typing on unit tests, run: + +```shell +hatch run types:check-tests +``` + +## Generating the documentation + +➢ To prepare the documentation environment, run: + +```shell +hatch env create docs +``` + +➢ To generate the documentation with [mkdocs](https://www.mkdocs.org/), run: + +```shell +hatch run docs:build +``` + +This command will generate the documentation in the `site` directory. + +➢ To serve the documentation locally, run: + +```shell +hatch run docs:serve +``` + +This command will start a local web server to serve the documentation +at [http://127.0.0.1:8000/](http://127.0.0.1:8000/). + +## Building the package + +➢ To build the package, run: + +```shell +hatch build +``` + +This command will create a `dist` directory with the built package. + +➢ To build the package and upload it to [PyPI](https://pypi.org/), run: + +```shell +hatch publish +``` + +➢ To clean the project, run: + +```shell +hatch clean +``` + +This command will remove the `dist` directory. diff --git a/docs/index.md b/docs/index.md new file mode 100644 index 0000000..74118af --- /dev/null +++ b/docs/index.md @@ -0,0 +1,18 @@ +# Antares Study Version + +[![PyPI - Version](https://img.shields.io/pypi/v/antares-study-version.svg)](https://pypi.org/project/antares-study-version) +[![PyPI - Python Version](https://img.shields.io/pypi/pyversions/antares-study-version.svg)](https://pypi.org/project/antares-study-version) + +Welcome to the `antares-study-version` documentation! + +![antares-study-version-title](assets/antares-study-version-title.jpeg) + +The `antares-study-version` package defines `StudyVersion` and `SolverVersion` classes to manage version numbers. + +**Table of Contents** + +- [overview.md](overview.md) +- [installation.md](installation.md) +- [usage.md](usage.md) +- [development.md](development.md) +- [Changelog](CHANGELOG.md) diff --git a/docs/installation.md b/docs/installation.md new file mode 100644 index 0000000..29c45c7 --- /dev/null +++ b/docs/installation.md @@ -0,0 +1,5 @@ +# Installation + +```console +pip install antares-study-version +``` diff --git a/docs/overview.md b/docs/overview.md new file mode 100644 index 0000000..a41aa3a --- /dev/null +++ b/docs/overview.md @@ -0,0 +1,39 @@ +# Overview + +The `antares-study-version` package defines `StudyVersion` and `SolverVersion` classes to manage version numbers. +It can be used to manage the version of a study, but also the version +of [Antares Solver](https://github.com/AntaresSimulatorTeam/Antares_Simulator). +It supports the [semver](https://semver.org/) format ("major.minor.patch") and the integer format +(major×100 + minor×10 + patch), which is specific to Antares. + +This module harmonizes the management of versions in Antares: + +- at the level of Antares studies (configuration files, database, etc.) +- at the level of Antares applications, in particular [AntaREST](https://github.com/AntaresSimulatorTeam/AntaREST/). + +In the data of a study and in the programs, we encounter several version formats: + +- dotted string (ex. `"8.7"` or `"8.7.2"`), +- compact string (ex. `"870"`), +- integer (ex. `870`). +- tuples or lists (ex. `(8, 7)` or `[8, 7, 2]`). +- dictionaries (ex. `{"major": 8, "minor": 7, "patch": 2}`). + +For instance, since +[version 9.0](https://antares-simulator.readthedocs.io/en/latest/reference-guide/13-file-format/#v900) +of Antares Solver, versions are stored as dotted strings; +the compact format is now obsolete (backward compatibility is ensured for versions prior to 9.0); + +For instance, the `study.antares` configuration file now uses the "X.Y" format for the study version instead +of the "XYZ" format. + +```ini +[antares] +version = 9.1 +caption = My Study +created = 1618413128 +lastsave = 1625583204 +author = John DOE +``` + +This module allows to convert these formats to each other, and to compare versions. diff --git a/docs/stylesheets/extra.css b/docs/stylesheets/extra.css new file mode 100644 index 0000000..f778681 --- /dev/null +++ b/docs/stylesheets/extra.css @@ -0,0 +1,11 @@ +[data-md-color-scheme="antares"] { + --md-primary-fg-color: #002a5e; + --md-primary-fg-color--light: #00a3ca; + --md-primary-fg-color--dark: #112446; + --md-typeset-a-color: #00a3ca; /* text link color*/ + --md-accent-fg-color: #ff9800; /* link color on hover*/ +} +[data-md-color-scheme="slate"] { + --md-hue: 213; /* [0, 360] */ + --md-accent-fg-color: #ff9800; +} diff --git a/docs/usage.md b/docs/usage.md new file mode 100644 index 0000000..f67de1b --- /dev/null +++ b/docs/usage.md @@ -0,0 +1,134 @@ +# Usage + +This package provides a `StudyVersion` class to manage study version numbers, +and a `SolverVersion` class to manage Antares Solver version numbers. + +The difference between `StudyVersion` and `SolverVersion` is that Solver versions are generally on 3 digits +(with the `major`, `minor` and `patch` components), while study versions are on 2 digits +(with the `major` and `minor` components only), and the `patch` component is not used (always 0). + +## StudyVersion + +Using the `antares-study-version` module is straightforward: + +```python +from antares.study.version import StudyVersion + +version = StudyVersion(8, 7, 2) # patch component is not used +print(version) # 8.7 +``` + +You can also create a version object from a dotted string: + +```python +from antares.study.version import StudyVersion + +version = StudyVersion.parse("8.7") +print(version) # 8.7 +``` + +You can create a version object from a compact string: + +```python +from antares.study.version import StudyVersion + +version = StudyVersion.parse("870") +print(version) # 8.7 +``` + +You can create a version object from an integer: + +```python +from antares.study.version import StudyVersion + +version = StudyVersion.parse(870) +print(version) # 8.7 +``` + +You can compare versions: + +```python +from antares.study.version import StudyVersion + +version1 = StudyVersion(8, 6) +version2 = StudyVersion(8, 7) +print(version1 < version2) # True +``` + +You can convert a version to string using format specifiers: + +```python +from antares.study.version import StudyVersion + +version = StudyVersion(8, 7) +print(f"{version}") # 8.7 +print(f"{version:02d}") # 08.07 +print(f"{version:03d}") # 08.07.00 +print(f"{version:ddd}") # 870 +``` + +You can convert a version to an integer: + +```python +from antares.study.version import StudyVersion + +version = StudyVersion(8, 7) +print(int(version)) # 870 +``` + +## SolverVersion + +Of course, the same operations can be done with `SolverVersion` objects, but with 3 digits: + +```python +from antares.study.version import SolverVersion + +version = SolverVersion(8, 7, 2) +print(version) # 8.7.2 +``` + +Objects of the `StudyVersion` and `SolverVersion` classes can be compared to each other: + +```python +from antares.study.version import StudyVersion, SolverVersion + +study_version = StudyVersion(8, 7) +solver_version = SolverVersion(8, 7, 2) +print(study_version <= solver_version) # True +``` + +## Pydantic model + +You can even use the `StudyVersion` or `SolverVersion` classes in a Pydantic model: + +```python +import datetime +import typing as t +import uuid + +from pydantic import BaseModel, Field, validator + +from antares.study.version import StudyVersion + + +class StudyDTO(BaseModel): + id: uuid.UUID = Field(default_factory=lambda: uuid.uuid4()) + name: str + version: StudyVersion + created: datetime.datetime = Field(default_factory=lambda: datetime.datetime.now(tz=datetime.timezone.utc)) + + @validator("version", pre=True) + def _validate_version(cls, v: t.Any) -> StudyVersion: + return StudyVersion.parse(v) + + +study = StudyDTO(name="foo", version=StudyVersion(4, 5)) +obj = study.json() +print(obj) +# { +# "created": "2024-12-31T12:30:00+00:00", +# "id": "4930a577-63d2-4ea9-b0b9-581110d97475", +# "name": "foo", +# "version": {"major": 4, "minor": 5, "patch": 0} +# } +``` diff --git a/mkdocs.yml b/mkdocs.yml new file mode 100644 index 0000000..d3ec07c --- /dev/null +++ b/mkdocs.yml @@ -0,0 +1,67 @@ +docs_dir: docs +site_name: Antares Study Version Documentation +repo_url: https://github.com/AntaresSimulatorTeam/antares-study-version +edit_uri: edit/doc/docs/ + +theme: + name: mkdocs # material + logo: assets/antares-study-version-logo.png + favicon: assets/antares-study-version-icon.png + prev_next_buttons_location: none + features: + - navigation.instant + - navigation.top + - navigation.expand + # - navigation.sections + # - header.autohide + # - toc.separate + palette: + - media: "(prefers-color-scheme: light)" + scheme: antares + toggle: + icon: material/toggle-switch-off-outline + name: Switch to dark mode + - media: "(prefers-color-scheme: dark)" + scheme: slate + toggle: + icon: material/toggle-switch + name: Switch to light mode + +nav: + - 'Index': 'index.md' + - 'Overview': 'overview.md' + - 'Installation': 'installation.md' + - 'Usage': 'usage.md' + - 'Development': 'development.md' + - 'Antares ecosystem': 'https://antares-doc.readthedocs.io' + - 'Changelog': 'CHANGELOG.md' + +extra: + generator: false + version: + provider: mike +plugins: + - search + +extra_css: + - stylesheets/extra.css + +extra_javascript: + - https://code.jquery.com/jquery-3.6.0.min.js + - https://polyfill.io/v3/polyfill.min.js?features=es6 + - https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js?config=TeX-AMS-MML_HTMLorMML + +#markdown_extensions: +# - attr_list +# - toc: +# permalink: true +# toc_depth: 3 +# - pymdownx.emoji: +# emoji_index: !!python/name:material.extensions.emoji.twemoji +# emoji_generator: !!python/name:material.extensions.emoji.to_svg +# - admonition +# - pymdownx.details +# - pymdownx.superfences +# - pymdownx.tabbed + +copyright: Copyright © 2007 - 2024 RTE diff --git a/pyproject.toml b/pyproject.toml index 40d6226..cc37691 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -74,6 +74,18 @@ dependencies = [ check = "mypy --namespace-packages --package antares.study.version --install-types --non-interactive" check-tests = "mypy --install-types --non-interactive {args:tests}" +[tool.hatch.envs.docs] +detached = true +dependencies = [ + "mkdocs", +] + +[tool.hatch.envs.docs.scripts] +build = "mkdocs build -f mkdocs.yml {args}" +serve = "mkdocs serve -f mkdocs.yml {args}" +gh-deploy = "mkdocs gh-deploy -f mkdocs.yml {args}" + + [tool.mypy] mypy_path = 'src, tests' diff --git a/scripts/update_version.py b/scripts/update_version.py index 6a909db..1d2e580 100755 --- a/scripts/update_version.py +++ b/scripts/update_version.py @@ -22,7 +22,7 @@ # ============================================================== ABOUT_FILE = "src/antares/study/version/__about__.py" -CHANGELOG_FILE = "CHANGELOG.md" +CHANGELOG_FILE = "docs/CHANGELOG.md" FILES_TO_PATCH = [ ( ABOUT_FILE,