diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index f841d99..fec8d94 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -13,11 +13,18 @@ jobs: if: "!contains(github.event.pull_request.labels.*.name, 'docs-only')" runs-on: ${{ matrix.os }} strategy: + fail-fast: false matrix: - os: [ubuntu-latest, macos-latest, windows-latest] - python: ['3.9', '3.10', '3.11'] + os: [ubuntu-latest] + python: ["3.9", "3.12"] + include: + - os: macos-latest + python: "3.12" + - os: windows-latest + python: "3.12" steps: + - uses: actions/checkout@v4 - uses: compas-dev/compas-actions.build@v4 with: python: ${{ matrix.python }} diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml index 219f923..e3a9abd 100644 --- a/.github/workflows/docs.yml +++ b/.github/workflows/docs.yml @@ -14,6 +14,8 @@ jobs: docs: runs-on: ubuntu-latest steps: - - uses: compas-dev/compas-actions.docs@v4 + - uses: compas-dev/compas-actions.docs@v5 with: github_token: ${{ secrets.GITHUB_TOKEN }} + generator: mkdocs + extras: dev,mkdocs \ No newline at end of file diff --git a/.github/workflows/pr-checks.yml b/.github/workflows/pr-checks.yml index fa70e31..4702d8b 100644 --- a/.github/workflows/pr-checks.yml +++ b/.github/workflows/pr-checks.yml @@ -11,7 +11,7 @@ jobs: name: Check Actions runs-on: ubuntu-latest steps: - - uses: actions/checkout@v1 + - uses: actions/checkout@v4 - name: Changelog check uses: Zomzog/changelog-checker@v1.2.0 with: diff --git a/CHANGELOG.md b/CHANGELOG.md index d713049..ee3960e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,6 +9,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added +* Added support for `Mkdocs` documentation generation, using `mkdocs.docs` task. (`Mkdocs` is an optional dependency at the moment, but may become a required dependency in the future). + ### Changed ### Removed diff --git a/LICENSE b/LICENSE index ac4d88e..a344364 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ MIT License -ETH Zurich +Copyright (c) 2026 COMPAS Association Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/docs/_images/PLACEHOLDER b/docs/_images/PLACEHOLDER deleted file mode 100644 index 48f73eb..0000000 --- a/docs/_images/PLACEHOLDER +++ /dev/null @@ -1 +0,0 @@ -# container for images to be included in the docs diff --git a/docs/_logo/compas_logo_white_transparent.png b/docs/_logo/compas_logo_white_transparent.png new file mode 100644 index 0000000..5dd158c Binary files /dev/null and b/docs/_logo/compas_logo_white_transparent.png differ diff --git a/docs/_logo/favicon.ico b/docs/_logo/favicon.ico new file mode 100644 index 0000000..381bd94 Binary files /dev/null and b/docs/_logo/favicon.ico differ diff --git a/docs/_static/PLACEHOLDER b/docs/_static/PLACEHOLDER deleted file mode 100644 index f611256..0000000 --- a/docs/_static/PLACEHOLDER +++ /dev/null @@ -1 +0,0 @@ -# container for static files, e.g. logo, banner images, javascript, stylesheets, ... diff --git a/docs/api.rst b/docs/api.rst deleted file mode 100644 index 360bea0..0000000 --- a/docs/api.rst +++ /dev/null @@ -1,12 +0,0 @@ -******************************************************************************** -API Reference -******************************************************************************** - -.. toctree:: - :maxdepth: 1 - - api/compas_invocations2.build - api/compas_invocations2.console - api/compas_invocations2.docs - api/compas_invocations2.style - api/compas_invocations2.tests diff --git a/docs/api/build.md b/docs/api/build.md new file mode 100644 index 0000000..9506db0 --- /dev/null +++ b/docs/api/build.md @@ -0,0 +1,3 @@ +# Build Tasks + +::: compas_invocations2.build diff --git a/docs/api/console.md b/docs/api/console.md new file mode 100644 index 0000000..31def5f --- /dev/null +++ b/docs/api/console.md @@ -0,0 +1,3 @@ +# Console Tasks + +::: compas_invocations2.console diff --git a/docs/api/docs.md b/docs/api/docs.md new file mode 100644 index 0000000..7074b0a --- /dev/null +++ b/docs/api/docs.md @@ -0,0 +1,3 @@ +# Documentation Tasks + +::: compas_invocations2.docs diff --git a/docs/api/style.md b/docs/api/style.md new file mode 100644 index 0000000..0ebb07d --- /dev/null +++ b/docs/api/style.md @@ -0,0 +1,3 @@ +# Style Tasks + +::: compas_invocations2.style diff --git a/docs/api/tests.md b/docs/api/tests.md new file mode 100644 index 0000000..7ed4d43 --- /dev/null +++ b/docs/api/tests.md @@ -0,0 +1,3 @@ +# Test Tasks + +::: compas_invocations2.tests diff --git a/docs/assets/stylesheets/custom.css b/docs/assets/stylesheets/custom.css new file mode 100644 index 0000000..a6f31ae --- /dev/null +++ b/docs/assets/stylesheets/custom.css @@ -0,0 +1,5 @@ +:root > * { + --md-primary-fg-color: #0092d2; + --md-primary-fg-color--light: #0092d2; + --md-primary-fg-color--dark: #0092d2; +} \ No newline at end of file diff --git a/docs/conf.py b/docs/conf.py deleted file mode 100644 index ef7168e..0000000 --- a/docs/conf.py +++ /dev/null @@ -1,154 +0,0 @@ -# flake8: noqa -# -*- coding: utf-8 -*- - -from sphinx.writers import html, html5 -import sphinx_compas2_theme - -# -- General configuration ------------------------------------------------ - -project = "COMPAS Invocations 2" -copyright = "COMPAS Association" -package = "compas_invocations2" -organization = "compas-dev" - -master_doc = "index" -source_suffix = {".rst": "restructuredtext", ".md": "markdown"} -templates_path = sphinx_compas2_theme.get_autosummary_templates_path() -exclude_patterns = sphinx_compas2_theme.default_exclude_patterns -add_module_names = True -language = "en" - -latest_version = sphinx_compas2_theme.get_latest_version() - -if latest_version == "Unreleased": - release = "Unreleased" - version = "latest" -else: - release = latest_version - version = ".".join(release.split(".")[0:2]) # type: ignore - -# -- Extension configuration ------------------------------------------------ - -extensions = sphinx_compas2_theme.default_extensions -extensions.remove("sphinx.ext.linkcode") - -# numpydoc options - -numpydoc_show_class_members = False -numpydoc_class_members_toctree = False -numpydoc_attributes_as_param_list = True - -# bibtex options - -# autodoc options - -autodoc_type_aliases = {} - -autodoc_typehints = "description" -autodoc_typehints_format = "short" -autodoc_typehints_description_target = "documented" - -autodoc_mock_imports = sphinx_compas2_theme.default_mock_imports - -autodoc_default_options = { - "undoc-members": True, - "show-inheritance": True, -} - -autodoc_member_order = "groupwise" - -autoclass_content = "class" - -# autosummary options - -autosummary_generate = True -autosummary_mock_imports = sphinx_compas2_theme.default_mock_imports - -# graph options - -# plot options - -# intersphinx options - -intersphinx_mapping = { - "python": ("https://docs.python.org/", None), - "compas": ("https://compas.dev/compas/latest/", None), -} - -# linkcode - -linkcode_resolve = sphinx_compas2_theme.get_linkcode_resolve(organization, package) - -# extlinks - -extlinks = {} - -# from pytorch - -sphinx_compas2_theme.replace(html.HTMLTranslator) -sphinx_compas2_theme.replace(html5.HTML5Translator) - -# -- Options for HTML output ---------------------------------------------- - -html_theme = "sidebaronly" -html_title = project - -favicons = [ - { - "rel": "icon", - "href": "compas.ico", - } -] - -html_theme_options = { - "icon_links": [ - { - "name": "GitHub", - "url": f"https://github.com/{organization}/{package}", - "icon": "fa-brands fa-github", - "type": "fontawesome", - }, - { - "name": "Discourse", - "url": "http://forum.compas-framework.org/", - "icon": "fa-brands fa-discourse", - "type": "fontawesome", - }, - { - "name": "PyPI", - "url": f"https://pypi.org/project/{package}/", - "icon": "fa-brands fa-python", - "type": "fontawesome", - }, - ], - "switcher": { - "json_url": f"https://raw.githubusercontent.com/{organization}/{package}/gh-pages/versions.json", - "version_match": version, - }, - "check_switcher": False, - "logo": { - "image_light": "_static/compas_icon_white.png", - "image_dark": "_static/compas_icon_white.png", - "text": project, - }, - "navigation_depth": 3, -} - - -html_context = { - "github_url": "https://github.com", - "github_user": organization, - "github_repo": package, - "github_version": "main", - "doc_path": "docs", -} - -html_static_path = sphinx_compas2_theme.get_html_static_path() + ["_static"] -html_css_files = [] -html_extra_path = [] -html_last_updated_fmt = "" -html_copy_source = False -html_show_sourcelink = True -html_permalinks = False -html_permalinks_icon = "" -html_compact_lists = True \ No newline at end of file diff --git a/docs/examples/PLACEHOLDER b/docs/examples/PLACEHOLDER deleted file mode 100644 index e69de29..0000000 diff --git a/docs/index.md b/docs/index.md new file mode 100644 index 0000000..0e163ed --- /dev/null +++ b/docs/index.md @@ -0,0 +1,10 @@ +# COMPAS Invocations 2 + +A collection of reusable [`pyinvoke`](https://pyinvoke.org/) tasks for COMPAS packages. + +## Features + +- **Project Management**: Tasks for releasing, cleaning, and managing changelogs. +- **Documentation**: Tasks for building Sphinx and MkDocs documentation. +- **Code Style**: Tasks for linting (ruff) and formatting (black/isort). +- **Testing**: Tasks for running pytest and doctests. diff --git a/docs/index.rst b/docs/index.rst deleted file mode 100644 index 27fd830..0000000 --- a/docs/index.rst +++ /dev/null @@ -1,31 +0,0 @@ -******************************************************************************** -compas_invocations2 -******************************************************************************** - -.. rst-class:: lead - -A collection of reusable pyinvoke tasks - -.. .. figure:: /_images/ - :figclass: figure - :class: figure-img img-fluid - - -Table of Contents -================= - -.. toctree:: - :maxdepth: 3 - :titlesonly: - - Introduction - installation - api - license - - -Indices and tables -================== - -* :ref:`genindex` -* :ref:`modindex` diff --git a/docs/installation.md b/docs/installation.md new file mode 100644 index 0000000..5a6dcbd --- /dev/null +++ b/docs/installation.md @@ -0,0 +1,7 @@ +# Installation + +Install `compas_invocations2` using `pip` from the Python Package Index. + +```bash +pip install compas_invocations2 +``` diff --git a/docs/installation.rst b/docs/installation.rst deleted file mode 100644 index b12de57..0000000 --- a/docs/installation.rst +++ /dev/null @@ -1,9 +0,0 @@ -******************************************************************************** -Installation -******************************************************************************** - -Install ``compas_invocations2`` using ``pip`` from the Python Package Index. - -.. code-block:: bash - - pip install compas_invocations2 diff --git a/docs/license.md b/docs/license.md new file mode 100644 index 0000000..0e8c6fc --- /dev/null +++ b/docs/license.md @@ -0,0 +1,3 @@ +# License + +--8<-- "LICENSE" diff --git a/docs/license.rst b/docs/license.rst deleted file mode 100644 index e6a80ce..0000000 --- a/docs/license.rst +++ /dev/null @@ -1,5 +0,0 @@ -******************************************************************************** -License -******************************************************************************** - -.. literalinclude:: ../LICENSE diff --git a/mkdocs.yml b/mkdocs.yml new file mode 100644 index 0000000..0949943 --- /dev/null +++ b/mkdocs.yml @@ -0,0 +1,150 @@ +site_name: COMPAS Invocations 2 +site_url: https://compas-dev.github.io/compas_invocations2 +repo_url: https://github.com/compas-dev/compas_invocations2 +repo_name: compas-dev/compas_invocations2 +edit_uri: blob/main/docs/ + +copyright: Copyright © 2026, COMPAS Association + +extra: + homepage: https://compas-dev.github.io/compas_invocations2 + version: + provider: mike + +theme: + name: material + palette: + # Palette toggle for light mode + - scheme: default + primary: indigo + accent: indigo + toggle: + icon: material/brightness-7 + name: Switch to dark mode + + # Palette toggle for dark mode + - scheme: slate + primary: indigo + accent: indigo + toggle: + icon: material/brightness-4 + name: Switch to light mode + font: + text: Roboto + code: Roboto Mono + logo: _logo/compas_logo_white_transparent.png + favicon: _logo/favicon.ico + features: + - content.code.copy + - content.footnote.tooltips + - navigation.expand + - navigation.footer + - navigation.indexes + - navigation.sections + - navigation.top + - search.highlight + - search.suggest + - toc.follow + +extra_css: + - assets/stylesheets/custom.css + +markdown_extensions: + - abbr + - attr_list + - admonition + - callouts: + strip_period: no + - footnotes + - md_in_html + - pymdownx.blocks.caption + - pymdownx.caret + - pymdownx.emoji: + emoji_index: !!python/name:material.extensions.emoji.twemoji + emoji_generator: !!python/name:material.extensions.emoji.to_svg + - pymdownx.keys + - pymdownx.mark + - pymdownx.tasklist: + custom_checkbox: true + - pymdownx.tilde + - pymdownx.highlight: + anchor_linenums: true + line_spans: __span + pygments_lang_class: true + - pymdownx.inlinehilite + - pymdownx.snippets: + check_paths: true + - toc: + permalink: "¤" + - pymdownx.superfences: + # make exceptions to highlighting of code: + custom_fences: + - name: mermaid + class: mermaid + format: !!python/name:mermaid2.fence_mermaid_custom + +plugins: + - search + - mermaid2 + - mkdocstrings: + default_handler: python + handlers: + python: + paths: [src] # search packages in the src folder + inventories: + - https://docs.python.org/3/objects.inv + - https://compas.dev/compas/latest/objects.inv + options: + allow_inspection: true + backlinks: tree + docstring_options: + ignore_init_summary: true + trim_doctest_flags: true + docstring_style: numpy + docstring_section_style: list + filters: public + group_by_category: true + heading_level: 2 + inheritance_diagram_direction: TD + inherited_members: false + line_length: 88 + merge_init_into_class: true + modernize_annotations: true + parameter_headings: false + preload_modules: [mkdocstrings, compas] + relative_crossrefs: true + scoped_crossrefs: true + separate_signature: true + show_bases: false + show_category_heading: true + show_docstring_attributes: true + show_docstring_functions: true + show_docstring_modules: false + show_if_no_docstring: false + show_inheritance_diagram: false + show_root_heading: true + show_root_full_path: true + show_signature: true + show_signature_annotations: true + show_signature_type_parameters: true + show_source: false + show_submodules: false + show_symbol_type_heading: true + show_symbol_type_toc: true + signature_crossrefs: true + summary: + modules: false + type_parameter_headings: true + unwrap_annotated: true + + +nav: + - Home: index.md + - Installation: installation.md + - API Reference: + - Build Tasks: api/build.md + - Console Tasks: api/console.md + - Documentation Tasks: api/docs.md + - Style Tasks: api/style.md + - Test Tasks: api/tests.md + - License: license.md diff --git a/pyproject.toml b/pyproject.toml index 7dc7745..3322e2d 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,5 +1,5 @@ [build-system] -requires = ["setuptools>=66.0"] +requires = ["setuptools>=68.0"] build-backend = "setuptools.build_meta" # ============================================================================ @@ -12,6 +12,7 @@ description = "A collection of reusable pyinvoke tasks." keywords = [] authors = [ { name = "Li Chen", email = "li.chen@arch.ethz.ch" }, + { name = "Gonzalo Casas", email = "casas@arch.ethz.ch" }, ] license = { file = "LICENSE" } readme = "README.md" @@ -25,6 +26,7 @@ classifiers = [ "Programming Language :: Python :: 3.9", "Programming Language :: Python :: 3.10", "Programming Language :: Python :: 3.11", + "Programming Language :: Python :: 3.12", ] [project.urls] @@ -45,7 +47,7 @@ zip-safe = false [tool.setuptools.dynamic] version = { attr = "compas_invocations2.__version__" } dependencies = { file = "requirements.txt" } -optional-dependencies = { dev = { file = "requirements-dev.txt" } } +optional-dependencies = { dev = { file = "requirements-dev.txt" }, mkdocs = { file = "requirements-mkdocs.txt" } } [tool.setuptools.packages.find] where = ["src"] @@ -105,7 +107,6 @@ select = ["E", "F", "I"] [tool.ruff.lint.per-file-ignores] "__init__.py" = ["I001"] "tests/*" = ["I001"] -"tasks.py" = ["I001"] [tool.ruff.lint.isort] force-single-line = true diff --git a/requirements-mkdocs.txt b/requirements-mkdocs.txt new file mode 100644 index 0000000..42585b8 --- /dev/null +++ b/requirements-mkdocs.txt @@ -0,0 +1,16 @@ +markdown-callouts >=0.4 +markdown-exec >=1.8 +mike +mkdocs >=1.6 +mkdocs-autorefs >=1.4 +mkdocs-coverage >=1.0 +mkdocs-git-revision-date-localized-plugin >=1.2 +mkdocs-llmstxt >=0.2 +mkdocs-material >=9.5 +mkdocs-minify-plugin >=0.8 +mkdocs-redirects >=1.2 +mkdocs-section-index >=0.3 +mkdocs-mermaid2-plugin +mkdocstrings[python] +pydantic >=2.10 +tomli >=2.0; python_version < '3.11' diff --git a/src/compas_invocations2/__init__.py b/src/compas_invocations2/__init__.py index 4776fa1..5f2af4d 100644 --- a/src/compas_invocations2/__init__.py +++ b/src/compas_invocations2/__init__.py @@ -1,5 +1,5 @@ __author__ = ["Li Chen"] -__copyright__ = "ETH Zurich" +__copyright__ = "COMPAS Association" __license__ = "MIT License" __email__ = "li.chen@arch.ethz.ch" __version__ = "0.7.0" diff --git a/src/compas_invocations2/console.py b/src/compas_invocations2/console.py index 63ee96a..d41e88f 100644 --- a/src/compas_invocations2/console.py +++ b/src/compas_invocations2/console.py @@ -1,21 +1,3 @@ -""" -******************************************************************************** -console -******************************************************************************** - -Text console UI helpers and patterns, e.g. ‘Y/n’ prompts and the like. - -.. currentmodule:: compas_invocations2.console - -.. autosummary:: - :toctree: generated/ - :nosignatures: - - confirm - chdir - -""" - import contextlib import os import sys diff --git a/src/compas_invocations2/mkdocs.py b/src/compas_invocations2/mkdocs.py new file mode 100644 index 0000000..b379ec8 --- /dev/null +++ b/src/compas_invocations2/mkdocs.py @@ -0,0 +1,18 @@ +import invoke + +from compas_invocations2.console import chdir + + +@invoke.task( + help={ + "clean": "True to clean the site directory before building, otherwise False.", + "verbose": "True to nicely format the output, otherwise False.", + } +) +def docs(ctx, clean=False, verbose=False): + """Builds the HTML documentation based on mkdocs.""" + clean_flag = "--clean" if clean else "" + verbose_flag = "--verbose" if verbose else "" + + with chdir(ctx.base_folder): + ctx.run("mkdocs build {} {} -d dist/docs".format(clean_flag, verbose_flag)) diff --git a/tasks.py b/tasks.py index cd33979..34b1031 100644 --- a/tasks.py +++ b/tasks.py @@ -1,21 +1,19 @@ -from __future__ import print_function - import os -from invoke import Collection +from invoke.collection import Collection from compas_invocations2 import build from compas_invocations2 import docs +from compas_invocations2 import mkdocs from compas_invocations2 import style from compas_invocations2 import tests ns = Collection( docs.help, + mkdocs.docs, style.check, style.lint, style.format, - docs.docs, - docs.linkcheck, tests.test, tests.testdocs, tests.testcodeblocks,