Changelog

All notable changes to this project are documented.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning. Dates formatted as YYYY-MM-DD as per ISO standard.

v0.13.1 - 2026-06-12

Essential bug fixes for ruff format and ruff check --fix.

Added

  • Back tests for formatters.

Changed

  • Updated documentation to mention formatters.
  • Updated JOSS paper.

Fixed

Fixes that were preventing the return of formatted QMD files:

  • Add missing self. for python_blocks, required in format_qmd().
  • Amend error code catch in _format_temp_py() that was preventing return of ruff check --fix file.

v0.13.0 - 2026-06-12

This release adds support for basedpyright and alpha support for formatters ruff format and ruff check --fix. It also includes some major refactoring to improve codebase.

Added

  • Add basic support for formatters ruff format and ruff check --fix - both still in alpha, with known bugs and further testing required. Support for these required several codebase (#93).
  • @jaycrick add support for basedpyright static type checker (#175).
  • In docs, add explanation of how to best apply linting rules to only quarto files (#136).

Changed

  • Major refactoring to improve code clarity and organisation, following all the recent changes made (#171).
  • Add new help formatter so lintquarto --help returns simpler options.
  • Simplified CONTRIBUTING.md.

v0.12.0 - 2026-06-08

This release primarily addresses feedback from @sneakers-the-rat ’s PyOpenSci review - as well as the tree-sitter suggestion from @isabelizimm.

Added

  • Check linter availability first before all files, so can fail fast if not present (#133).
  • Ignore RUF100 (#120) and INP001 (#141) by default, fixed by @Bergam0t.
  • Add script to automatically generate CLI documentation (#130), with GitHub workflow checking README and docs are consistent, to help prevent this going out-of-date.
  • In documentation, add note about limitation of pycodestyle and # noqa, and possible workarounds using flake8 and ruff (#142).
  • Add lintquarto list command which will list the supported linters and whether they are available or not (#131).
  • Add custom-command option so users can pass their own tools (#159).
  • Add support for listing lintquarto settings in [tool.lintquarto] within pyproject.toml (#132).

Changed

  • Centred badges in README (#146) by @aselaws.
  • Moved functions out of __main__.py (#135) and refactored main() as it was too complex (#161).
  • Refactored converter from regex to tree-sitter-markdown (#106).
  • Spacing and line preservation rules refactored to constants at start of script (#162).
  • Removed uv.lock and pythonversion - now, actions install from pyproject.toml and CONTRIBUTING supports any environment manager rather than pushing uv.

Fixed

  • Prevent directories with .qmd suffix being collected (#139) fixed by @sneakers-the-rat.
  • Handle valueboxes (#134).
  • Ensure temporary files are cleaned up, using a contextmanager (#137) and handling exceptions (#140).
  • Replace all chunk options with placeholders, fixing a false positive E265 pycodestyle error (#138).

Removed

  • Removed support for Python 3.9. This was due to a refactor to using tree-sitter-markdown, which requires 3.10+.

v0.11.0 - 2026-05-22

This release primarily fixes incorrect linting of IPython cell magics and restores pyrefly regression tests across older versions and pyrefly 1.0.0+, alongside smaller updates to docs, non-executable linting guidance, and environment checks.

Added

  • Add non-executable linting instructions to README.md and “Getting started”.
  • Add tests for python cell magic.
  • Add test to check all required linters for testing are present in environment.

Changed

  • Updated conda _meta.yml instructions in CONTRIBUTING.md, now that Python 3.9+ is supported (instead of 3.7+).
  • Removed mention of only linting non-executable code from the JOSS paper.

Fixed

  • Fixed bug (linters running on cell magic) identified by @jaycrick.
  • Add pyrefly.toml with preset = "strict" to make the pyrefly regression test back-compatible between earlier pyrefly versions and pyrefly 1.0.0+.

v0.10.0 - 2026-05-06

This release primarily addresses feedback from @isabelizimm ’s PyOpenSci review.

Added

  • Add all-contributors to README.md.
  • Add instructions for installing development version of package to documentation.
  • Add page to documentation with related tools (panache and nbqa).
  • Add support for linting non-executable Python cells.

Changed

  • In documentation, clarified that ruff is only used as a linter (and not a formatter).
  • Moved test environment for CI/CD into pyproject.toml (instead of separate requirements file). GitHub action now runs with uv.
  • Expanded ruff ruleset to ALL (with a few exceptions), and then simplified linting so now only using ruff (and not also flake8, pylint, radon-cc, vulture, pydoclint and mypy) - then linted codebase.

Fixed

  • Fixed hyperlinks in CONTRIBUTING.md.

Removed

  • Removed support for Python 3.7 and 3.8. This was because I was facing tooling issues with 3.7 and 3.8, and then learnt about NEP 29 which advises on which Python versions to support.

v0.9.0 - 2026-03-02

Add support for quarto code annotations, switched to codecov for coverage badge, and refactored converter.

Added

  • Converter: Add support for quarto code annotations (e.g., # <1>), with tests checking this implementation.

Changed

  • Converter: Refactored to reduce complexity of _handle_python_chunk().
  • Paper: Corrections.

Fixed

  • Coverage: Switched to codecov for generation of coverage badge.

v0.8.0 - 2026-02-11

Fixed issues with evaluation of inactive Python cells, and fixed version checks in test logic. Also switched to uv for dependencies and build, add new tests, moved vulture in docs, and add JOSS paper.

Added

  • Paper for Journal of Open Source Software (JOSS).
    • New/Changed files for paper: inst/ and .github/workflows/draft-pdf.yml.
    • Described in CONTRIBUTING.md and README.md.
  • Tests: Tests for new logic that fetches and respects the overall YAML and chunk options for evaluation.
  • GitHub actions: Add new action which tests the build of the package, and will build and publish to PyPI when release is published.

Changed

  • Documentation: Move vulture in documentation from “linters” to “code analysis tools”.
  • Build: Switched to uv for dependency management and package build.
    • New/Changed files for uv: .python-version, pyproject.toml, uv.lock.
    • Updated GitHub actions for docs and linting to use uv.
    • Removed requirements-dev.txt and requirements-stable.yml.
    • Updated instructions in CONTRIBUTING.md.
  • GitHub actions: Now run on pull request to main too (but docs action skips publish if not a push to main).

Fixed

  • Converter: Fixed bug where code quality tools would run on inactive Python cells when overall YAML has set eval: false.
  • Tests: Corrected skip_if_linter_available() which checked for Python > 3.12, but would inclde 3.12.x - now set to >= 3.13.

v0.7.0 - 2025-12-05

Fixed converter and CLI behaviour so duplicate output filenames now use an _1 suffix, decorator-related E302 issues are suppressed, and paths containing commas correctly raise errors. These are supported by new tests. Other changes include a linting pre-commit hook and updates to documentation.

Added

  • Pre-commit: Add back in a linting pre-commit.
  • Tests:
    • Add test checking that a duplicate filename triggers pylint
    • Add test detecting E302 error for function with decorator (e.g., @runtime_checkable).
    • Add test checking error is raised if there are commas in paths.

Changed

  • CONTRIBUTING: Make conda update instructions clearer, removed emojis and explain pre-commit.
  • Documentation: Make command line interface usage / options clearer, correct exclude command, and explain limitation of config files.

Fixed

  • Converter:
    • Duplicate filenames now _1 instead of (1) (with tests changed accordingly).
    • Suppress E302 for decorators (@).
  • main: Check for commas in paths and raise error if found.

v0.6.0 - 2025-09-25

Updates fix multiple converter and process_qmd issues, including improved detection of Python chunks, handling of comments, Quarto include syntax, and line highlight annotations. Other changes to documentation, actions and tests.

Added

  • GitHub actions: Add linting action.
  • Tests: Add tests relevant to changes/fixes below.

Changed

  • Acknowledgements: Redid LLM acknowledgement so just one overarching statement in README, and add more specific details on how it was used, based on PyOpenSci discussions.
  • Converter: Quarto code chunks now use noqa messages (rather than changing “#|” to “# |”, as they did before).
  • CONTRIBUTING: Corrected instructions for conda update.
  • process_qmd: Refactored to reduce complexity and repetition.
  • README: Add more badges (build & quality status, stars/download metrics) and button linking to documentation.

Fixed

  • process_qmd: Replace ...py in output with just the filename, and not the full file path (as that is there already, depending on linter, so get duplicates).
  • Converter:
    • “First code line” now excludes comments.
    • Can now handle Quarto {{< include ... >}} syntax (comments the line, else linters break as not valid Python syntax).
    • Can now handle “#<<” code annotations from shafayetShafee’s line-highlight extension (removes them and any whitespace prior).
    • Corrected detection of python code chunk start (allowing spaces before {python} and allowing in-line chunk options e.g. {python, echo=…}).
  • GitHub actions: Linting action now fails even for warning messages (previously, just failed for errors but not warnings).

v0.5.0 - 2025-08-18

Package now supports pydoclint, adds conda-related tooling and optional dev dependencies. Code now uses type hints, and have add some version-specific test and installation skips.

Added

  • pydoclint: Add support for a new linter: pydoclint.
  • Environment: Add grayskull, types-toml, and made a [dev] optional dependencies section in pyproject.toml. Add exclusions for particular python versions.

Changed

  • Type hints: Add type hints to package, and then use pydoclint and mypy when linting docs and package.
  • CONTRIBUTING: Improvements include table of contents and instructions for conda upload.
  • Documentation:
    • Add conda badge and PyPI downloads badges.
    • Add explanation for mypy output containing files outside specified path.
    • Mentioned “code analysis tools” (rather than referring to radon as a linter).
  • Test: Utility function for skipping tests when unavailable on certain python versions.

v0.4.0 - 2025-08-14

Extended support for radon, incorporating commands for maintainability index, Halstead metrics, and raw code metrics. Also some additional tests and documentation improvements, and a few small fixes.

Added

  • Radon: Extended support beyond radon cc - now also supports radon mi, radon hal and radon raw - which required addition of preserve_line_count in QmdToPyConverter.
  • Tests:
    • Add back testing for every linter (test_back.py).
    • Add test using check-dependencies which tests for missing or undeclared dependencies.
    • Add new tests related to radon changes (test_preserve_line_count_false_removes_non_code(), test_radon_hal_preserve_line_effect()).
  • Build: Add toml as required dependency

Changed

  • Radon: Command for radon cc is now radon-cc (was radon before).
  • Documentation:
    • docs.yaml now uses Python 3.12 (as one of the linters is unsupported in 3.13).
    • Improved readability of CONTRIBUTING.md.
    • Correct statement about only specifying one linter per command in README.md.
    • Add back in bold and gap for PyPI button.

Removed

  • Tests: Removed some redundant check_available tests (which were actually already covered by check_supported).

Fixed

  • File type: Fixed replacement of .py with .qmd in the output for some linters.
  • Tests: Include error in checkd output and remove line numbers for pytype. Add skip for pytype back-test for unsupported python versions.
  • lint_package.sh: Only run pylint on files that exist in tests/ to prevent false error about tests/__init__.py.

v0.3.0 - 2025-07-07

Major updates include support for multiple linters and file/directory exclusion, expanded testing, several fixes (e.g. false positive linter warnings, deletion of .py files, coverage badge), and the removal of pylama.

Added

  • Exclude: Add an -e / --exclude flag to exclude files/directories, with examples in documentation.
  • Multiple linters: Add option to run multiple linters using -l / --linters.
  • Tests: Expanded to provide a comprehensive set of unit tests for the args, converter, linelength and linters modules, as well as integration and functional tests for the __main__ module.
  • Test CI: GitHub actions workflow now runs tests on multiple Python versions (3.7-3.13).

Changed

  • Converter: Changed conversion of quarto to python file from a function (_qmd_lines_to_py_lines) to a class (QmdToPyConverter).
  • Command to run lintquarto: To run multiple linters, now required to use -l / --linters for linters and -p / --paths for files and directories.

Removed

  • Pre-commit: Removed, as it was not functioning as intended and a manual workflow is now preferred.
  • Pylama: Removed, since its supported linters are now integrated directly, and the others were either redundant or deprecated (#25).
  • Behind the scenes: removed as now more complex and decided better to just look at the code rahter than page in docs, more standard, and up to date, etc.

Fixed

  • README: Display of coverage badge.
  • Chunk options: Amends Quarto code chunk options from #| ... to # | ... to avoid linting errors.
  • E305: Linters like flake8 will warn “Expected 2 blank lines after end of function or class (E305)” at the start of a quarto code cell, but this will never be true, so for those linters, noqa: E305 is always appended.
  • E302: For functions/classes defined at the start of a quarto code cell, linters like flake8 will also warn “Expected 2 blank lines, found 0 (E302)”. This will also not be true, so in those cases, noqa: E302 is appended.
  • E501: When appending noqa: E302,E305 the line length can then become too long - “Line too long (82 > 79 characters) (E501)”. Hence, this warning is disabled in these cases (where the line length was fine before, but not after adding the noqa comment).
  • Deletion of .py file: When creating the temporary python file, the converter would replace any of the same name in the directory. If not keeping, it would then delete it. This issue has been fixed, by appending the duplicate temporary filename (e.g. file (1).py).
  • C0114: pylint will warn “missing-module-docstring / C0114” but this will never be relevant for a quarto file so has been disabled.
  • Errors in convert_qmd_to_py: For FileNotFoundError and PermissionError, corrected to also return None (as already done for Exception).
  • Coverage badge: Coverage badge is now pushed to the repository when generated in the tests GitHub action.

v0.2.0 - 2025-06-27

Major updates include expanded linter support, new Quarto documentation, and new CI/CD workflows.

Added

  • Linter support: Added support for new Python linters: pyflakes, ruff, pylama, vulture, pycodestyle, pyright, pyrefly and pytype.
  • Documentation:
    • Introduced Quarto documentation site with getting started, API reference, user guide and detailed linter pages.
    • Add the downloadthis extension to allow download buttons in .qmd files.
    • Add a Makefile for building and previewing the documentation.
  • CI/CD: Added GitHub actions to build documentation and run tests.
  • Linting the package: Added scripts and a pre-commit hook to lint the package code and documentation.
  • Environment: Created a stable version of the environment with pinned versions using Conda.

Changed

  • Refactoring: Refactored and simplified main code and converter logic, and linted the package.
  • README: Updated with new buttons and shield badges.
  • CONTRIBUTING: Add instructions on releases, bug reports, dependency versions, testing, and linting.
  • Environment: Add jupyter, genbadge, pre-commit, pytest-cov and quartodoc to the environment.

Fixed

  • README: Corrected links (PyPI, Zenodo, external images).

v0.1.0 - 2025-06-24

🌱 First release.

Added

  • Lint Quarto markdown (.qmd) files using pylint, flake8, or mypy.