From 2f6f4082676052c199a5e10f8aaaf943ce3ed7bf Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Fri, 24 Nov 2023 06:53:06 -0800 Subject: [PATCH 01/15] Switch from setup.py to pyproject.toml, update unit tests, update github workflows. --- .github/workflows/publish.yaml | 44 +++-------- .github/workflows/tests.yaml | 46 ++---------- README.md | 27 ++++--- install.txt | 1 - npm-deps.txt | 2 - pyproject.toml | 74 +++++++++++++++++++ requirements.txt | 1 - setup.py | 52 ------------- .../__init__.py | 0 .../plugins/__init__.py | 0 .../plugins/discovery/__init__.py | 0 .../plugins/discovery/dockerfile.py} | 0 .../plugins/tool/__init__.py | 0 .../plugins/tool/dockerfile_lint.py} | 0 .../plugins/tool/dockerfilelint.py} | 0 .../plugins/tool/hadolint.py} | 0 .../statick_tool/rsc}/.dockerfilelintrc | 0 {rsc => src/statick_tool/rsc}/.hadolint.yaml | 0 .../rsc}/dockerfile-lint-profile.yaml | 0 .../rsc}/dockerfilelint-profile.yaml | 0 .../statick_tool/rsc}/hadolint-profile.yaml | 0 .../statick_tool/rsc}/tooling-config.yaml | 0 .../statick_tool/rsc}/tooling-profile.yaml | 0 .../dockerfile_discovery_plugin.yapsy-plugin | 3 - .../dockerfile_lint_tool_plugin.yapsy-plugin | 3 - .../dockerfilelint_tool_plugin.yapsy-plugin | 3 - .../tool/hadolint_tool_plugin.yapsy-plugin | 3 - .../test_dockerfile_discovery_plugin.py | 40 ++++------ .../test_dockerfile_lint_tool_plugin.py | 48 +++++------- .../test_dockerfilelint_tool_plugin.py | 50 +++++-------- .../test_hadolint_tool_plugin.py | 51 +++++-------- tox.ini | 42 ++--------- 32 files changed, 180 insertions(+), 310 deletions(-) delete mode 100644 install.txt delete mode 100644 npm-deps.txt create mode 100644 pyproject.toml delete mode 100644 requirements.txt delete mode 100644 setup.py rename src/{statick_tooling => statick_tool}/__init__.py (100%) rename src/{statick_tooling => statick_tool}/plugins/__init__.py (100%) rename src/{statick_tooling => statick_tool}/plugins/discovery/__init__.py (100%) rename src/{statick_tooling/plugins/discovery/dockerfile_discovery_plugin.py => statick_tool/plugins/discovery/dockerfile.py} (100%) rename src/{statick_tooling => statick_tool}/plugins/tool/__init__.py (100%) rename src/{statick_tooling/plugins/tool/dockerfile_lint_tool_plugin.py => statick_tool/plugins/tool/dockerfile_lint.py} (100%) rename src/{statick_tooling/plugins/tool/dockerfilelint_tool_plugin.py => statick_tool/plugins/tool/dockerfilelint.py} (100%) rename src/{statick_tooling/plugins/tool/hadolint_tool_plugin.py => statick_tool/plugins/tool/hadolint.py} (100%) rename {rsc => src/statick_tool/rsc}/.dockerfilelintrc (100%) rename {rsc => src/statick_tool/rsc}/.hadolint.yaml (100%) rename {rsc => src/statick_tool/rsc}/dockerfile-lint-profile.yaml (100%) rename {rsc => src/statick_tool/rsc}/dockerfilelint-profile.yaml (100%) rename {rsc => src/statick_tool/rsc}/hadolint-profile.yaml (100%) rename {rsc => src/statick_tool/rsc}/tooling-config.yaml (100%) rename {rsc => src/statick_tool/rsc}/tooling-profile.yaml (100%) delete mode 100644 src/statick_tooling/plugins/discovery/dockerfile_discovery_plugin.yapsy-plugin delete mode 100644 src/statick_tooling/plugins/tool/dockerfile_lint_tool_plugin.yapsy-plugin delete mode 100644 src/statick_tooling/plugins/tool/dockerfilelint_tool_plugin.yapsy-plugin delete mode 100644 src/statick_tooling/plugins/tool/hadolint_tool_plugin.yapsy-plugin diff --git a/.github/workflows/publish.yaml b/.github/workflows/publish.yaml index 7c25cf3..a347bd1 100644 --- a/.github/workflows/publish.yaml +++ b/.github/workflows/publish.yaml @@ -10,6 +10,11 @@ jobs: build-n-publish: name: Build and publish Python 🐍 distributions 📦 to PyPI and TestPyPI runs-on: ubuntu-latest + environment: + name: pypi + url: https://pypi.org/p/statick-tooling + permissions: + id-token: write steps: - uses: actions/checkout@v3 @@ -18,47 +23,16 @@ jobs: uses: actions/setup-python@v4 with: python-version: '3.11' - - - uses: actions/cache@v3 - if: startsWith(runner.os, 'Linux') - with: - path: ~/.cache/pip - key: ${{ runner.os }}-pip-${{ hashFiles('**/requirements.txt') }} - restore-keys: | - ${{ runner.os }}-pip- - - - uses: actions/cache@v3 - if: startsWith(runner.os, 'macOS') - with: - path: ~/Library/Caches/pip - key: ${{ runner.os }}-pip-${{ hashFiles('**/requirements.txt') }} - restore-keys: | - ${{ runner.os }}-pip- - - - uses: actions/cache@v3 - if: startsWith(runner.os, 'Windows') - with: - path: ~\AppData\Local\pip\Cache - key: ${{ runner.os }}-pip-${{ hashFiles('**/requirements.txt') }} - restore-keys: | - ${{ runner.os }}-pip- + cache: 'pip' - name: Install tools run: | - python -m pip install --upgrade setuptools - python -m pip install --upgrade wheel + pip install .[dist] - name: Build a binary wheel and a source tarball run: | - python setup.py sdist bdist_wheel - - - name: Publish distribution 📦 to Test PyPI - uses: pypa/gh-action-pypi-publish@release/v1 - with: - password: ${{ secrets.PYPI_TEST_TOKEN }} - repository_url: https://test.pypi.org/legacy/ + pip install -q build + python -m build - name: Publish distribution 📦 to PyPI uses: pypa/gh-action-pypi-publish@release/v1 - with: - password: ${{ secrets.PYPI_TOKEN }} diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index e28f2c0..12f8dc6 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -8,7 +8,6 @@ on: # NOLINT - cron: '0 10 * * MON' workflow_dispatch: - jobs: build: @@ -16,7 +15,7 @@ jobs: strategy: matrix: os: [macos-latest, ubuntu-20.04, ubuntu-22.04, windows-latest] - python-version: ['3.8', '3.9', '3.10', '3.11'] + python-version: ['3.8', '3.9', '3.10', '3.11', '3.12'] steps: - uses: actions/checkout@v3 @@ -25,51 +24,20 @@ jobs: uses: actions/setup-python@v4 with: python-version: ${{ matrix.python-version }} + cache: 'pip' - uses: actions/setup-node@v3 with: node-version: '16' - - uses: actions/cache@v3 - if: startsWith(runner.os, 'Linux') - with: - path: ~/.cache/pip - key: ${{ runner.os }}-pip-${{ hashFiles('**/requirements.txt') }} - restore-keys: | - ${{ runner.os }}-pip- - - - uses: actions/cache@v3 - if: startsWith(runner.os, 'macOS') - with: - path: ~/Library/Caches/pip - key: ${{ runner.os }}-pip-${{ hashFiles('**/requirements.txt') }} - restore-keys: | - ${{ runner.os }}-pip- - - - uses: actions/cache@v3 - if: startsWith(runner.os, 'Windows') - with: - path: ~\AppData\Local\pip\Cache - key: ${{ runner.os }}-pip-${{ hashFiles('**/requirements.txt') }} - restore-keys: | - ${{ runner.os }}-pip- - - name: Install dependencies run: | - python -m pip install --upgrade pip - python -m pip install --upgrade setuptools - python -m pip install --upgrade wheel - python -m pip install --upgrade coverage - python -m pip install --upgrade mypy - python -m pip install --upgrade statick - python -m pip install --upgrade statick-md - python -m pip install --upgrade tox - python -m pip install --upgrade tox-gh-actions - python -m pip install --upgrade virtualenv - python -m pip install -r requirements.txt + pip install --upgrade pip + pip install . + pip install .[test] + pip install .[docs] - # Have to install newer version from non-apt source due to SSL library compatibility issues. - - name: Install Node and node-based tools (Linux) + - name: Install Node-based tools (Linux) if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' run: | npm install -g markdownlint-cli diff --git a/README.md b/README.md index 51836ac..b0eba43 100644 --- a/README.md +++ b/README.md @@ -17,21 +17,26 @@ Custom exceptions can be applied the same way they are with [Statick exceptions] ## Table of Contents -* [Installation](#installation) -* [Usage](#usage) -* [Existing Plugins](#existing-plugins) - * [Discovery Plugins](#discovery-plugins) - * [Tool Plugins](#tool-plugins) -* [Contributing](#contributing) - * [Mypy](#mypy) - * [Formatting](#formatting) +- [Statick Tooling Plugins](#statick-tooling-plugins) + - [Table of Contents](#table-of-contents) + - [Installation](#installation) + - [Usage](#usage) + - [Pip Install](#pip-install) + - [Pip Install and Custom Configuration](#pip-install-and-custom-configuration) + - [Source Install and Custom Configuration](#source-install-and-custom-configuration) + - [Existing Plugins](#existing-plugins) + - [Discovery Plugins](#discovery-plugins) + - [Tool Plugins](#tool-plugins) + - [Contributing](#contributing) + - [Mypy](#mypy) + - [Formatting](#formatting) ## Installation The recommended method to install these Statick plugins is via pip: ```shell -python3 -m pip install statick-tooling +pip install statick-tooling ``` You can also clone the repository and use it locally. @@ -41,8 +46,8 @@ You can also clone the repository and use it locally. Make sure you install all the dependencies from apt/npm: ```shell -cat install.txt | xargs sudo apt-get install -y -cat npm-deps.txt | xargs sudo npm install -g +sudo apt-get install -y npm +sudo npm install -g dockerfilelint dockerfile_lint ``` ### Pip Install diff --git a/install.txt b/install.txt deleted file mode 100644 index b235581..0000000 --- a/install.txt +++ /dev/null @@ -1 +0,0 @@ -npm diff --git a/npm-deps.txt b/npm-deps.txt deleted file mode 100644 index e00b8f8..0000000 --- a/npm-deps.txt +++ /dev/null @@ -1,2 +0,0 @@ -dockerfilelint -dockerfile_lint diff --git a/pyproject.toml b/pyproject.toml new file mode 100644 index 0000000..36deb23 --- /dev/null +++ b/pyproject.toml @@ -0,0 +1,74 @@ +[build-system] +requires = ["setuptools"] +build-backend = "setuptools.build_meta" + +[project] +name = "statick-tooling" +authors = [{name = "NIWC Pacific"}] +description="Statick analysis plugins for Tooling files." +version = "0.1.1" +readme = "README.md" +requires-python = ">=3.8" +license = {text = "CC0-1.0"} +classifiers = [ + "License :: CC0 1.0 Universal (CC0 1.0) Public Domain Dedication", + "Programming Language :: Python :: 3", + "Programming Language :: Python :: 3.8", + "Programming Language :: Python :: 3.9", + "Programming Language :: Python :: 3.10", + "Programming Language :: Python :: 3.11", + "Programming Language :: Python :: 3.12", + "Topic :: Software Development :: Quality Assurance", + "Topic :: Software Development :: Testing", + "Typing :: Typed", +] + +dependencies = [ + "importlib_metadata", + "statick", + "types-docutils", +] + +[tool.setuptools.package-data] +statick_tool = [ + "rsc/*", + "rsc/.*", +] + +[project.entry-points."statick_tool.plugins.discovery"] +dockerfile = "statick_tool.plugins.discovery.dockerfile:DockerfileDiscoveryPlugin" + +[project.entry-points."statick_tool.plugins.tool"] +dockerfile-lint = "statick_tool.plugins.tool.dockerfile_lint:DockerfileULintToolPlugin" +dockerfilelint = "statick_tool.plugins.tool.dockerfilelint:DockerfileLintToolPlugin" +hadolint = "statick_tool.plugins.tool.hadolint:HadolintToolPlugin" + +[project.urls] +"Homepage" = "https://github.com/tdenewiler/statick-tooling" +"Bug Tracker" = "https://github.com/tdenewiler/statick-tooling/issues" + +[project.optional-dependencies] +test = [ + "coverage", + "flake8-pep3101", + "flake8<5", # Pin until https://github.com/tholo/pytest-flake8/issues/87 is fixed. + "mock", + "mypy", + "pycodestyle<2.9.0", # Pin until https://github.com/tholo/pytest-flake8/issues/87 is fixed. + "pydocstyle", + "pytest", + "pytest-cov", + "setuptools", + "statick", + "statick-md", + "tox", + "tox-gh-actions", +] +docs = [ + "sphinx==1.7.9", + "yaml-1.3", +] +dist = [ + "setuptools", + "wheel", +] diff --git a/requirements.txt b/requirements.txt deleted file mode 100644 index 15f3587..0000000 --- a/requirements.txt +++ /dev/null @@ -1 +0,0 @@ -statick diff --git a/setup.py b/setup.py deleted file mode 100644 index 6b87a9c..0000000 --- a/setup.py +++ /dev/null @@ -1,52 +0,0 @@ -"""Setup.""" - - -from setuptools import setup - -with open("README.md", encoding="utf8") as f: - long_description = f.read() # pylint: disable=invalid-name - -TEST_DEPS = [ - "mock", - "pytest", -] - -EXTRAS = { - "test": TEST_DEPS, -} - -setup( - author="NIWC Pacific", - name="statick-tooling", - description="Statick analysis plugins for Tooling files.", - version="0.1.1", - packages=[ - "statick_tool", - "statick_tool.plugins.discovery", - "statick_tool.plugins.tool", - ], - package_dir={ - "statick_tool": ".", - "statick_tool.plugins.discovery": "src/statick_tooling/plugins/discovery", - "statick_tool.plugins.tool": "src/statick_tooling/plugins/tool", - }, - package_data={ - "statick_tool": ["rsc/.*", "rsc/*"], - "statick_tool.plugins.discovery": ["*.yapsy-plugin"], - "statick_tool.plugins.tool": ["*.yapsy-plugin"], - }, - long_description=long_description, - long_description_content_type="text/markdown", - install_requires=["statick"], - tests_require=TEST_DEPS, - extras_require=EXTRAS, - url="https://github.com/sscpac/statick-tooling", - classifiers=[ - "License :: CC0 1.0 Universal (CC0 1.0) Public Domain Dedication", - "Programming Language :: Python :: 3.8", - "Programming Language :: Python :: 3.9", - "Programming Language :: Python :: 3.10", - "Programming Language :: Python :: 3.11", - "Topic :: Software Development :: Testing", - ], -) diff --git a/src/statick_tooling/__init__.py b/src/statick_tool/__init__.py similarity index 100% rename from src/statick_tooling/__init__.py rename to src/statick_tool/__init__.py diff --git a/src/statick_tooling/plugins/__init__.py b/src/statick_tool/plugins/__init__.py similarity index 100% rename from src/statick_tooling/plugins/__init__.py rename to src/statick_tool/plugins/__init__.py diff --git a/src/statick_tooling/plugins/discovery/__init__.py b/src/statick_tool/plugins/discovery/__init__.py similarity index 100% rename from src/statick_tooling/plugins/discovery/__init__.py rename to src/statick_tool/plugins/discovery/__init__.py diff --git a/src/statick_tooling/plugins/discovery/dockerfile_discovery_plugin.py b/src/statick_tool/plugins/discovery/dockerfile.py similarity index 100% rename from src/statick_tooling/plugins/discovery/dockerfile_discovery_plugin.py rename to src/statick_tool/plugins/discovery/dockerfile.py diff --git a/src/statick_tooling/plugins/tool/__init__.py b/src/statick_tool/plugins/tool/__init__.py similarity index 100% rename from src/statick_tooling/plugins/tool/__init__.py rename to src/statick_tool/plugins/tool/__init__.py diff --git a/src/statick_tooling/plugins/tool/dockerfile_lint_tool_plugin.py b/src/statick_tool/plugins/tool/dockerfile_lint.py similarity index 100% rename from src/statick_tooling/plugins/tool/dockerfile_lint_tool_plugin.py rename to src/statick_tool/plugins/tool/dockerfile_lint.py diff --git a/src/statick_tooling/plugins/tool/dockerfilelint_tool_plugin.py b/src/statick_tool/plugins/tool/dockerfilelint.py similarity index 100% rename from src/statick_tooling/plugins/tool/dockerfilelint_tool_plugin.py rename to src/statick_tool/plugins/tool/dockerfilelint.py diff --git a/src/statick_tooling/plugins/tool/hadolint_tool_plugin.py b/src/statick_tool/plugins/tool/hadolint.py similarity index 100% rename from src/statick_tooling/plugins/tool/hadolint_tool_plugin.py rename to src/statick_tool/plugins/tool/hadolint.py diff --git a/rsc/.dockerfilelintrc b/src/statick_tool/rsc/.dockerfilelintrc similarity index 100% rename from rsc/.dockerfilelintrc rename to src/statick_tool/rsc/.dockerfilelintrc diff --git a/rsc/.hadolint.yaml b/src/statick_tool/rsc/.hadolint.yaml similarity index 100% rename from rsc/.hadolint.yaml rename to src/statick_tool/rsc/.hadolint.yaml diff --git a/rsc/dockerfile-lint-profile.yaml b/src/statick_tool/rsc/dockerfile-lint-profile.yaml similarity index 100% rename from rsc/dockerfile-lint-profile.yaml rename to src/statick_tool/rsc/dockerfile-lint-profile.yaml diff --git a/rsc/dockerfilelint-profile.yaml b/src/statick_tool/rsc/dockerfilelint-profile.yaml similarity index 100% rename from rsc/dockerfilelint-profile.yaml rename to src/statick_tool/rsc/dockerfilelint-profile.yaml diff --git a/rsc/hadolint-profile.yaml b/src/statick_tool/rsc/hadolint-profile.yaml similarity index 100% rename from rsc/hadolint-profile.yaml rename to src/statick_tool/rsc/hadolint-profile.yaml diff --git a/rsc/tooling-config.yaml b/src/statick_tool/rsc/tooling-config.yaml similarity index 100% rename from rsc/tooling-config.yaml rename to src/statick_tool/rsc/tooling-config.yaml diff --git a/rsc/tooling-profile.yaml b/src/statick_tool/rsc/tooling-profile.yaml similarity index 100% rename from rsc/tooling-profile.yaml rename to src/statick_tool/rsc/tooling-profile.yaml diff --git a/src/statick_tooling/plugins/discovery/dockerfile_discovery_plugin.yapsy-plugin b/src/statick_tooling/plugins/discovery/dockerfile_discovery_plugin.yapsy-plugin deleted file mode 100644 index 9d594fa..0000000 --- a/src/statick_tooling/plugins/discovery/dockerfile_discovery_plugin.yapsy-plugin +++ /dev/null @@ -1,3 +0,0 @@ -[Core] -Name = Dockerfile Discovery Plugin -Module = dockerfile_discovery_plugin diff --git a/src/statick_tooling/plugins/tool/dockerfile_lint_tool_plugin.yapsy-plugin b/src/statick_tooling/plugins/tool/dockerfile_lint_tool_plugin.yapsy-plugin deleted file mode 100644 index 914206a..0000000 --- a/src/statick_tooling/plugins/tool/dockerfile_lint_tool_plugin.yapsy-plugin +++ /dev/null @@ -1,3 +0,0 @@ -[Core] -Name = Dockerfile Lint Tool Plugin -Module = dockerfile_lint_tool_plugin diff --git a/src/statick_tooling/plugins/tool/dockerfilelint_tool_plugin.yapsy-plugin b/src/statick_tooling/plugins/tool/dockerfilelint_tool_plugin.yapsy-plugin deleted file mode 100644 index 69936eb..0000000 --- a/src/statick_tooling/plugins/tool/dockerfilelint_tool_plugin.yapsy-plugin +++ /dev/null @@ -1,3 +0,0 @@ -[Core] -Name = DockerfileLint Tool Plugin -Module = dockerfilelint_tool_plugin diff --git a/src/statick_tooling/plugins/tool/hadolint_tool_plugin.yapsy-plugin b/src/statick_tooling/plugins/tool/hadolint_tool_plugin.yapsy-plugin deleted file mode 100644 index a4e5db1..0000000 --- a/src/statick_tooling/plugins/tool/hadolint_tool_plugin.yapsy-plugin +++ /dev/null @@ -1,3 +0,0 @@ -[Core] -Name = Hadolint Tool Plugin -Module = hadolint_tool_plugin diff --git a/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py b/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py index a2555c5..ef23a2e 100644 --- a/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py +++ b/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py @@ -1,40 +1,26 @@ """Unit tests for the dockerfile discovery plugin.""" import os +import sys -from yapsy.PluginManager import PluginManager - -import statick_tool -from statick_tool.discovery_plugin import DiscoveryPlugin from statick_tool.exceptions import Exceptions from statick_tool.package import Package -from statick_tool.plugins.discovery.dockerfile_discovery_plugin import ( - DockerfileDiscoveryPlugin, -) +from statick_tool.plugins.discovery.dockerfile import DockerfileDiscoveryPlugin + +if sys.version_info < (3, 10): + from importlib_metadata import entry_points +else: + from importlib.metadata import entry_points def test_dockerfile_plugin_found(): """Test that the plugin manager finds the dockerfile discovery plugin.""" - manager = PluginManager() - # Get the path to statick_tool/__init__.py, get the directory part, and - # add 'plugins' to that to get the standard plugins dir - manager.setPluginPlaces( - [os.path.join(os.path.dirname(statick_tool.__file__), "plugins")] - ) - manager.setCategoriesFilter( - { - "Discovery": DiscoveryPlugin, - } - ) - manager.collectPlugins() - # Verify that a plugin's get_name() function returns "dockerfile" - assert any( - plugin_info.plugin_object.get_name() == "dockerfile" - for plugin_info in manager.getPluginsOfCategory("Discovery") - ) - # While we're at it, verify that a plugin is named dockerfile Discovery Plugin + discovery_plugins = {} + plugins = entry_points(group="statick_tool.plugins.discovery") + for plugin_type in plugins: + plugin = plugin_type.load() + discovery_plugins[plugin_type.name] = plugin() assert any( - plugin_info.name == "Dockerfile Discovery Plugin" - for plugin_info in manager.getPluginsOfCategory("Discovery") + plugin.get_name() == "dockerfile" for _, plugin in list(discovery_plugins.items()) ) diff --git a/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py b/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py index e6c3830..e3f9a06 100644 --- a/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py +++ b/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py @@ -1,22 +1,22 @@ """Unit tests for the dockerfilelint plugin.""" - import argparse -import os -import subprocess - import mock +import os import pytest -from yapsy.PluginManager import PluginManager +import subprocess +import sys import statick_tool from statick_tool.config import Config from statick_tool.package import Package from statick_tool.plugin_context import PluginContext -from statick_tool.plugins.tool.dockerfile_lint_tool_plugin import ( - DockerfileULintToolPlugin, -) +from statick_tool.plugins.tool.dockerfile_lint import DockerfileULintToolPlugin from statick_tool.resources import Resources -from statick_tool.tool_plugin import ToolPlugin + +if sys.version_info < (3, 10): + from importlib_metadata import entry_points +else: + from importlib.metadata import entry_points def setup_dockerfilelint_tool_plugin(): @@ -45,27 +45,13 @@ def setup_dockerfilelint_tool_plugin(): def test_dockerfilelint_tool_plugin_found(): """Test that the plugin manager can find the dockerfilelint plugin.""" - manager = PluginManager() - # Get the path to statick_tool/__init__.py, get the directory part, and - # add 'plugins' to that to get the standard plugins dir - manager.setPluginPlaces( - [os.path.join(os.path.dirname(statick_tool.__file__), "plugins")] - ) - manager.setCategoriesFilter( - { - "Tool": ToolPlugin, - } - ) - manager.collectPlugins() - # Verify that a plugin's get_name() function returns "dockerfilelint" - assert any( - plugin_info.plugin_object.get_name() == "dockerfile-lint" - for plugin_info in manager.getPluginsOfCategory("Tool") - ) - # While we're at it, verify that a plugin is named dockerfilelint Tool Plugin + tool_plugins = {} + plugins = entry_points(group="statick_tool.plugins.tool") + for plugin_type in plugins: + plugin = plugin_type.load() + tool_plugins[plugin_type.name] = plugin() assert any( - plugin_info.name == "Dockerfile Lint Tool Plugin" - for plugin_info in manager.getPluginsOfCategory("Tool") + plugin.get_name() == "dockerfile-lint" for _, plugin in list(tool_plugins.items()) ) @@ -132,7 +118,7 @@ def test_dockerfilelint_tool_plugin_parse_invalid(): @mock.patch( - "statick_tool.plugins.tool.dockerfilelint_tool_plugin.subprocess.check_output" + "statick_tool.plugins.tool.dockerfilelint.subprocess.check_output" ) def test_dockerfilelint_tool_plugin_scan_calledprocesserror( mock_subprocess_check_output, @@ -169,7 +155,7 @@ def test_dockerfilelint_tool_plugin_scan_calledprocesserror( @mock.patch( - "statick_tool.plugins.tool.dockerfilelint_tool_plugin.subprocess.check_output" + "statick_tool.plugins.tool.dockerfilelint.subprocess.check_output" ) def test_dockerfilelint_tool_plugin_scan_oserror(mock_subprocess_check_output): """ diff --git a/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py b/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py index e4846d0..687b47d 100644 --- a/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py +++ b/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py @@ -1,22 +1,22 @@ """Unit tests for the dockerfilelint plugin.""" - import argparse -import os -import subprocess - import mock +import os import pytest -from yapsy.PluginManager import PluginManager +import subprocess +import sys import statick_tool from statick_tool.config import Config from statick_tool.package import Package from statick_tool.plugin_context import PluginContext -from statick_tool.plugins.tool.dockerfilelint_tool_plugin import ( - DockerfileLintToolPlugin, -) +from statick_tool.plugins.tool.dockerfilelint import DockerfileLintToolPlugin from statick_tool.resources import Resources -from statick_tool.tool_plugin import ToolPlugin + +if sys.version_info < (3, 10): + from importlib_metadata import entry_points +else: + from importlib.metadata import entry_points def setup_dockerfilelint_tool_plugin(package="valid_package"): @@ -45,27 +45,13 @@ def setup_dockerfilelint_tool_plugin(package="valid_package"): def test_dockerfilelint_tool_plugin_found(): """Test that the plugin manager can find the dockerfilelint plugin.""" - manager = PluginManager() - # Get the path to statick_tool/__init__.py, get the directory part, and - # add 'plugins' to that to get the standard plugins dir - manager.setPluginPlaces( - [os.path.join(os.path.dirname(statick_tool.__file__), "plugins")] - ) - manager.setCategoriesFilter( - { - "Tool": ToolPlugin, - } - ) - manager.collectPlugins() - # Verify that a plugin's get_name() function returns "dockerfilelint" - assert any( - plugin_info.plugin_object.get_name() == "dockerfilelint" - for plugin_info in manager.getPluginsOfCategory("Tool") - ) - # While we're at it, verify that a plugin is named dockerfilelint Tool Plugin + tool_plugins = {} + plugins = entry_points(group="statick_tool.plugins.tool") + for plugin_type in plugins: + plugin = plugin_type.load() + tool_plugins[plugin_type.name] = plugin() assert any( - plugin_info.name == "DockerfileLint Tool Plugin" - for plugin_info in manager.getPluginsOfCategory("Tool") + plugin.get_name() == "dockerfilelint" for _, plugin in list(tool_plugins.items()) ) @@ -155,7 +141,7 @@ def test_dockerfilelint_tool_plugin_scan_invalid_rc_file(): # at Array.forEach () # at Object. (/usr/local/lib/node_modules/dockerfilelint/bin/dockerfilelint:65:8) # at Module._compile (internal/modules/cjs/loader.js:1063:30) - assert len(issues) == 14 + assert len(issues) == 15 assert issues[2].filename == "EXCEPTION" assert issues[2].line_number == "0" assert issues[2].tool == "dockerfilelint" @@ -165,7 +151,7 @@ def test_dockerfilelint_tool_plugin_scan_invalid_rc_file(): @mock.patch( - "statick_tool.plugins.tool.dockerfilelint_tool_plugin.subprocess.check_output" + "statick_tool.plugins.tool.dockerfilelint.subprocess.check_output" ) def test_dockerfilelint_tool_plugin_scan_calledprocesserror( mock_subprocess_check_output, @@ -202,7 +188,7 @@ def test_dockerfilelint_tool_plugin_scan_calledprocesserror( @mock.patch( - "statick_tool.plugins.tool.dockerfilelint_tool_plugin.subprocess.check_output" + "statick_tool.plugins.tool.dockerfilelint.subprocess.check_output" ) def test_dockerfilelint_tool_plugin_scan_oserror(mock_subprocess_check_output): """ diff --git a/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py b/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py index bfad3d0..8b9583b 100644 --- a/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py +++ b/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py @@ -1,22 +1,23 @@ """Unit tests for the hadolint plugin.""" - import argparse import json +import mock import os +import pytest import subprocess import sys -import mock -import pytest -from yapsy.PluginManager import PluginManager - import statick_tool from statick_tool.config import Config from statick_tool.package import Package from statick_tool.plugin_context import PluginContext -from statick_tool.plugins.tool.hadolint_tool_plugin import HadolintToolPlugin +from statick_tool.plugins.tool.hadolint import HadolintToolPlugin from statick_tool.resources import Resources -from statick_tool.tool_plugin import ToolPlugin + +if sys.version_info < (3, 10): + from importlib_metadata import entry_points +else: + from importlib.metadata import entry_points def setup_hadolint_tool_plugin( @@ -56,27 +57,13 @@ def setup_hadolint_tool_plugin( def test_hadolint_tool_plugin_found(): """Test that the plugin manager can find the hadolint plugin.""" - manager = PluginManager() - # Get the path to statick_tool/__init__.py, get the directory part, and - # add 'plugins' to that to get the standard plugins dir - manager.setPluginPlaces( - [os.path.join(os.path.dirname(statick_tool.__file__), "plugins")] - ) - manager.setCategoriesFilter( - { - "Tool": ToolPlugin, - } - ) - manager.collectPlugins() - # Verify that a plugin's get_name() function returns "hadolint" - assert any( - plugin_info.plugin_object.get_name() == "hadolint" - for plugin_info in manager.getPluginsOfCategory("Tool") - ) - # While we're at it, verify that a plugin is named hadolint Tool Plugin + tool_plugins = {} + plugins = entry_points(group="statick_tool.plugins.tool") + for plugin_type in plugins: + plugin = plugin_type.load() + tool_plugins[plugin_type.name] = plugin() assert any( - plugin_info.name == "Hadolint Tool Plugin" - for plugin_info in manager.getPluginsOfCategory("Tool") + plugin.get_name() == "hadolint" for _, plugin in list(tool_plugins.items()) ) @@ -228,7 +215,7 @@ def test_hadolint_tool_plugin_scan_docker_duplicate_format(): assert len(issues) == 4 -@mock.patch("statick_tool.plugins.tool.hadolint_tool_plugin.json.loads") +@mock.patch("statick_tool.plugins.tool.hadolint.json.loads") def test_hadolint_tool_plugin_scan_jsondecodeerror( mock_json_loads_jsondecodeerror, ): @@ -264,7 +251,7 @@ def test_hadolint_tool_plugin_scan_different_binary(): assert issues is None -@mock.patch("statick_tool.plugins.tool.hadolint_tool_plugin.subprocess.check_output") +@mock.patch("statick_tool.plugins.tool.hadolint.subprocess.check_output") def test_hadolint_tool_plugin_scan_calledprocesserror( mock_subprocess_check_output, ): @@ -293,7 +280,7 @@ def test_hadolint_tool_plugin_scan_calledprocesserror( assert not issues -@mock.patch("statick_tool.plugins.tool.hadolint_tool_plugin.subprocess.check_output") +@mock.patch("statick_tool.plugins.tool.hadolint.subprocess.check_output") def test_hadolint_tool_plugin_scan_oserror(mock_subprocess_check_output): """ Test what happens when an OSError is raised (usually means hadolint doesn't exist). @@ -312,7 +299,7 @@ def test_hadolint_tool_plugin_scan_oserror(mock_subprocess_check_output): assert issues is None -@mock.patch("statick_tool.plugins.tool.hadolint_tool_plugin.subprocess.check_output") +@mock.patch("statick_tool.plugins.tool.hadolint.subprocess.check_output") def test_hadolint_tool_plugin_scan_calledprocesserror_with_docker( mock_subprocess_check_output, ): @@ -342,7 +329,7 @@ def test_hadolint_tool_plugin_scan_calledprocesserror_with_docker( assert not issues -@mock.patch("statick_tool.plugins.tool.hadolint_tool_plugin.subprocess.check_output") +@mock.patch("statick_tool.plugins.tool.hadolint.subprocess.check_output") def test_hadolint_tool_plugin_scan_oserror_with_docker(mock_subprocess_check_output): """ Test what happens when an OSError is raised by scan_docker. diff --git a/tox.ini b/tox.ini index 7c099ff..f99fc5f 100644 --- a/tox.ini +++ b/tox.ini @@ -1,26 +1,9 @@ [tox] -envlist = py38, py39, py310, py311 +envlist = py38, py39, py310, py311, py312 skip_missing_interpreters = true [pytest] -flake8-max-line-length = 9000 -norecursedirs = .tox - -# To work with black some items must be ignored. -# https://github.com/psf/black#how-black-wraps-lines -[flake8] -exclude = .tox -ignore = E203, E231, W503 - -# To work with black a specific configuration is required. -# https://github.com/psf/black#how-black-wraps-lines -[isort] -known_first_party = statick_tool -multi_line_output = 3 -include_trailing_comma = True -force_grid_wrap = 0 -use_parentheses = True -line_length = 88 +norecursedirs = .tox build [gh-actions] python = @@ -28,31 +11,20 @@ python = 3.9: py39 3.10: py310 3.11: py311 + 3.12: py312 [testenv] changedir = {toxinidir}/output-{envname} passenv = CI setenv = PY_IGNORE_IMPORTMISMATCH = 1 deps = - codecov - flake8<5 # Pin until https://github.com/tholo/pytest-flake8/issues/87 is fixed. - flake8-pep3101 - pycodestyle<2.9.0 # Pin until https://github.com/tholo/pytest-flake8/issues/87 is fixed. - pydocstyle - pytest - pytest-cov - pytest-flake8 - pytest-isort .[test] commands = - pydocstyle ../src/ - pycodestyle --ignore=E203,E501,W503 ../src/ - pytest -rs --flake8 --isort \ - --cov=statick_tool.plugins.discovery.dockerfile_discovery_plugin \ - --cov=statick_tool.plugins.tool.dockerfilelint_tool_plugin \ - --cov=statick_tool.plugins.tool.dockerfile_lint_tool_plugin \ - --cov=statick_tool.plugins.tool.hadolint_tool_plugin \ + pytest \ + --cov={toxinidir}/src/statick_tool \ --cov-report term-missing \ --doctest-modules \ + --junit-xml=statick-{envname}-junit.xml \ + --junit-prefix={envname} \ {toxinidir} {posargs} coverage xml From af78da9167644effe4f9c461eac8c415b9e9b17d Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Fri, 24 Nov 2023 06:55:25 -0800 Subject: [PATCH 02/15] Update URLs. --- pyproject.toml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index 36deb23..c9833a4 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -44,8 +44,8 @@ dockerfilelint = "statick_tool.plugins.tool.dockerfilelint:DockerfileLintToolPlu hadolint = "statick_tool.plugins.tool.hadolint:HadolintToolPlugin" [project.urls] -"Homepage" = "https://github.com/tdenewiler/statick-tooling" -"Bug Tracker" = "https://github.com/tdenewiler/statick-tooling/issues" +"Homepage" = "https://github.com/sscpac/statick-tooling" +"Bug Tracker" = "https://github.com/sscpac/statick-tooling/issues" [project.optional-dependencies] test = [ From 15c895171109967628efb3d8f4254fb182384505 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Sat, 25 Nov 2023 18:53:20 -0800 Subject: [PATCH 03/15] Dependency cleanup. --- .github/workflows/publish.yaml | 4 ---- pyproject.toml | 15 ++++----------- tox.ini | 2 -- 3 files changed, 4 insertions(+), 17 deletions(-) diff --git a/.github/workflows/publish.yaml b/.github/workflows/publish.yaml index a347bd1..19e9421 100644 --- a/.github/workflows/publish.yaml +++ b/.github/workflows/publish.yaml @@ -25,10 +25,6 @@ jobs: python-version: '3.11' cache: 'pip' - - name: Install tools - run: | - pip install .[dist] - - name: Build a binary wheel and a source tarball run: | pip install -q build diff --git a/pyproject.toml b/pyproject.toml index c9833a4..325069b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,5 +1,5 @@ [build-system] -requires = ["setuptools"] +requires = ["setuptools", "wheel"] build-backend = "setuptools.build_meta" [project] @@ -50,15 +50,9 @@ hadolint = "statick_tool.plugins.tool.hadolint:HadolintToolPlugin" [project.optional-dependencies] test = [ "coverage", - "flake8-pep3101", - "flake8<5", # Pin until https://github.com/tholo/pytest-flake8/issues/87 is fixed. "mock", - "mypy", - "pycodestyle<2.9.0", # Pin until https://github.com/tholo/pytest-flake8/issues/87 is fixed. - "pydocstyle", "pytest", "pytest-cov", - "setuptools", "statick", "statick-md", "tox", @@ -68,7 +62,6 @@ docs = [ "sphinx==1.7.9", "yaml-1.3", ] -dist = [ - "setuptools", - "wheel", -] + +[tool.isort] +profile = "black" diff --git a/tox.ini b/tox.ini index f99fc5f..f21c33c 100644 --- a/tox.ini +++ b/tox.ini @@ -15,8 +15,6 @@ python = [testenv] changedir = {toxinidir}/output-{envname} -passenv = CI -setenv = PY_IGNORE_IMPORTMISMATCH = 1 deps = .[test] commands = From 3c82eb160240df8a674ee05cace817bcffc38edc Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Tue, 10 Sep 2024 06:15:55 -0700 Subject: [PATCH 04/15] Update GitHub action versions. Use stdlib-plugins branch for statick dependency. Remove all __init__.py files as they collide with main statick files. --- .github/workflows/tests.yaml | 6 +++--- pyproject.toml | 5 ++--- src/statick_tool/__init__.py | 1 - src/statick_tool/plugins/__init__.py | 1 - src/statick_tool/plugins/discovery/__init__.py | 1 - src/statick_tool/plugins/tool/__init__.py | 1 - 6 files changed, 5 insertions(+), 10 deletions(-) delete mode 100644 src/statick_tool/__init__.py delete mode 100644 src/statick_tool/plugins/__init__.py delete mode 100644 src/statick_tool/plugins/discovery/__init__.py delete mode 100644 src/statick_tool/plugins/tool/__init__.py diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index 12f8dc6..8c403d3 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -18,15 +18,15 @@ jobs: python-version: ['3.8', '3.9', '3.10', '3.11', '3.12'] steps: - - uses: actions/checkout@v3 + - uses: actions/checkout@v4 - name: Set up Python ${{ matrix.python-version }} - uses: actions/setup-python@v4 + uses: actions/setup-python@v5 with: python-version: ${{ matrix.python-version }} cache: 'pip' - - uses: actions/setup-node@v3 + - uses: actions/setup-node@v4 with: node-version: '16' diff --git a/pyproject.toml b/pyproject.toml index 325069b..abb885a 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -25,7 +25,7 @@ classifiers = [ dependencies = [ "importlib_metadata", - "statick", + "statick@git+https://github.com/tdenewiler/statick@stdlib-plugins", "types-docutils", ] @@ -53,8 +53,7 @@ test = [ "mock", "pytest", "pytest-cov", - "statick", - "statick-md", + "statick-md@git+https://github.com/tdenewiler/statick-md@stdlib-plugins", "tox", "tox-gh-actions", ] diff --git a/src/statick_tool/__init__.py b/src/statick_tool/__init__.py deleted file mode 100644 index 5da5b0e..0000000 --- a/src/statick_tool/__init__.py +++ /dev/null @@ -1 +0,0 @@ -"""Statick tool.""" diff --git a/src/statick_tool/plugins/__init__.py b/src/statick_tool/plugins/__init__.py deleted file mode 100644 index 9e74282..0000000 --- a/src/statick_tool/plugins/__init__.py +++ /dev/null @@ -1 +0,0 @@ -"""Markdown plugins for Statick.""" diff --git a/src/statick_tool/plugins/discovery/__init__.py b/src/statick_tool/plugins/discovery/__init__.py deleted file mode 100644 index 878179b..0000000 --- a/src/statick_tool/plugins/discovery/__init__.py +++ /dev/null @@ -1 +0,0 @@ -"""Md file discovery plugins.""" diff --git a/src/statick_tool/plugins/tool/__init__.py b/src/statick_tool/plugins/tool/__init__.py deleted file mode 100644 index ef93d6a..0000000 --- a/src/statick_tool/plugins/tool/__init__.py +++ /dev/null @@ -1 +0,0 @@ -"""Md tool plugins.""" From a4f1bedcc36fdc6b739d855861b3b9632b843a85 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Mon, 14 Oct 2024 20:46:16 -0700 Subject: [PATCH 05/15] Drop Python 3.8, add Python 3.13. --- .github/workflows/tests.yaml | 12 ++++++------ pyproject.toml | 2 +- tox.ini | 3 ++- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index 8c403d3..0b180b2 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -14,8 +14,8 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: [macos-latest, ubuntu-20.04, ubuntu-22.04, windows-latest] - python-version: ['3.8', '3.9', '3.10', '3.11', '3.12'] + os: [macos-latest, ubuntu-22.04, ubuntu-24.04, windows-latest] + python-version: ['3.9', '3.10', '3.11', '3.12', '3.13'] steps: - uses: actions/checkout@v4 @@ -38,7 +38,7 @@ jobs: pip install .[docs] - name: Install Node-based tools (Linux) - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' + if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | npm install -g markdownlint-cli npm install -g dockerfilelint @@ -53,7 +53,7 @@ jobs: echo "$GITHUB_WORKSPACE/hadolint-bin" >> $GITHUB_PATH - name: Install Hadolint docker image (Linux) - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' + if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | docker pull hadolint/hadolint:latest @@ -71,12 +71,12 @@ jobs: fail_ci_if_error: false - name: Statick Documentation - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' + if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | statick . --check --user-paths . --profile documentation.yaml - name: Self check - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' + if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | mkdir statick-output statick . --output-directory statick-output --check --profile self_check.yaml diff --git a/pyproject.toml b/pyproject.toml index abb885a..69200f1 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -13,11 +13,11 @@ license = {text = "CC0-1.0"} classifiers = [ "License :: CC0 1.0 Universal (CC0 1.0) Public Domain Dedication", "Programming Language :: Python :: 3", - "Programming Language :: Python :: 3.8", "Programming Language :: Python :: 3.9", "Programming Language :: Python :: 3.10", "Programming Language :: Python :: 3.11", "Programming Language :: Python :: 3.12", + "Programming Language :: Python :: 3.13", "Topic :: Software Development :: Quality Assurance", "Topic :: Software Development :: Testing", "Typing :: Typed", diff --git a/tox.ini b/tox.ini index f21c33c..6b7d8fe 100644 --- a/tox.ini +++ b/tox.ini @@ -1,5 +1,5 @@ [tox] -envlist = py38, py39, py310, py311, py312 +envlist = py39, py310, py311, py312, py313 skip_missing_interpreters = true [pytest] @@ -12,6 +12,7 @@ python = 3.10: py310 3.11: py311 3.12: py312 + 3.13: py313 [testenv] changedir = {toxinidir}/output-{envname} From 6e5eeb70e1e78f87a065dc7bcdb69d8891e711d5 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Mon, 14 Oct 2024 21:11:11 -0700 Subject: [PATCH 06/15] Add ubuntu-20.04. --- .github/workflows/tests.yaml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index 0b180b2..10566e8 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -14,7 +14,7 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: [macos-latest, ubuntu-22.04, ubuntu-24.04, windows-latest] + os: [macos-latest, ubuntu-20.04, ubuntu-22.04, ubuntu-24.04, windows-latest] python-version: ['3.9', '3.10', '3.11', '3.12', '3.13'] steps: @@ -38,7 +38,7 @@ jobs: pip install .[docs] - name: Install Node-based tools (Linux) - if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | npm install -g markdownlint-cli npm install -g dockerfilelint @@ -53,7 +53,7 @@ jobs: echo "$GITHUB_WORKSPACE/hadolint-bin" >> $GITHUB_PATH - name: Install Hadolint docker image (Linux) - if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | docker pull hadolint/hadolint:latest @@ -71,12 +71,12 @@ jobs: fail_ci_if_error: false - name: Statick Documentation - if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | statick . --check --user-paths . --profile documentation.yaml - name: Self check - if: matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' run: | mkdir statick-output statick . --output-directory statick-output --check --profile self_check.yaml From 0e74b721f4d0c6c036acdbbd00563163f6ae83cc Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Thu, 2 Jan 2025 18:39:54 -0800 Subject: [PATCH 07/15] Run isort on test files. --- .../test_dockerfile_discovery_plugin.py | 1 + .../test_dockerfile_lint_tool_plugin.py | 9 +++++---- .../test_dockerfilelint_tool_plugin.py | 9 +++++---- .../hadolint_tool_plugin/test_hadolint_tool_plugin.py | 9 +++++---- 4 files changed, 16 insertions(+), 12 deletions(-) diff --git a/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py b/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py index ef23a2e..70b1684 100644 --- a/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py +++ b/tests/discovery/dockerfile_discovery_plugin/test_dockerfile_discovery_plugin.py @@ -4,6 +4,7 @@ from statick_tool.exceptions import Exceptions from statick_tool.package import Package + from statick_tool.plugins.discovery.dockerfile import DockerfileDiscoveryPlugin if sys.version_info < (3, 10): diff --git a/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py b/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py index e3f9a06..ae1d06d 100644 --- a/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py +++ b/tests/tool/dockerfile_lint_tool_plugin/test_dockerfile_lint_tool_plugin.py @@ -1,18 +1,19 @@ """Unit tests for the dockerfilelint plugin.""" import argparse -import mock import os -import pytest import subprocess import sys -import statick_tool +import mock +import pytest from statick_tool.config import Config from statick_tool.package import Package from statick_tool.plugin_context import PluginContext -from statick_tool.plugins.tool.dockerfile_lint import DockerfileULintToolPlugin from statick_tool.resources import Resources +import statick_tool +from statick_tool.plugins.tool.dockerfile_lint import DockerfileULintToolPlugin + if sys.version_info < (3, 10): from importlib_metadata import entry_points else: diff --git a/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py b/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py index 687b47d..8bc5e85 100644 --- a/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py +++ b/tests/tool/dockerfilelint_tool_plugin/test_dockerfilelint_tool_plugin.py @@ -1,18 +1,19 @@ """Unit tests for the dockerfilelint plugin.""" import argparse -import mock import os -import pytest import subprocess import sys -import statick_tool +import mock +import pytest from statick_tool.config import Config from statick_tool.package import Package from statick_tool.plugin_context import PluginContext -from statick_tool.plugins.tool.dockerfilelint import DockerfileLintToolPlugin from statick_tool.resources import Resources +import statick_tool +from statick_tool.plugins.tool.dockerfilelint import DockerfileLintToolPlugin + if sys.version_info < (3, 10): from importlib_metadata import entry_points else: diff --git a/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py b/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py index 8b9583b..aa5d3e1 100644 --- a/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py +++ b/tests/tool/hadolint_tool_plugin/test_hadolint_tool_plugin.py @@ -1,19 +1,20 @@ """Unit tests for the hadolint plugin.""" import argparse import json -import mock import os -import pytest import subprocess import sys -import statick_tool +import mock +import pytest from statick_tool.config import Config from statick_tool.package import Package from statick_tool.plugin_context import PluginContext -from statick_tool.plugins.tool.hadolint import HadolintToolPlugin from statick_tool.resources import Resources +import statick_tool +from statick_tool.plugins.tool.hadolint import HadolintToolPlugin + if sys.version_info < (3, 10): from importlib_metadata import entry_points else: From e3173854c15d95189c7477245cb030ab2a67f737 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Fri, 3 Jan 2025 12:24:35 -0800 Subject: [PATCH 08/15] Simplify pip install command. --- .github/workflows/tests.yaml | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index 077b210..7fa3baf 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -33,9 +33,7 @@ jobs: - name: Install dependencies run: | pip install --upgrade pip - pip install . - pip install .[test] - pip install .[docs] + pip install .[docs,test] - name: Install Node-based tools (Linux) if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' From fefed51b58a842c33be4f591aa9e0f5d7dd1c6e9 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Fri, 3 Jan 2025 18:33:01 -0800 Subject: [PATCH 09/15] Update usage instructions in readme. --- README.md | 24 +++++++++++++++++++++--- 1 file changed, 21 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index b0eba43..a1d207d 100644 --- a/README.md +++ b/README.md @@ -43,11 +43,29 @@ You can also clone the repository and use it locally. ## Usage -Make sure you install all the dependencies from apt/npm: +Make sure you install all the dependencies from apt/npm. +See for Node/npm installation instructions. + +Configure npm to allow a non-root user to install packages. + +```shell +npm config set prefix '~/.local/' +``` + +Make sure `~/.local/bin` exists. +Check your `PATH` with `echo $PATH`. +If `~/.local/bin` is not listed then add it to your `PATH`. + +```shell +mkdir -p ~/.local/bin +echo 'export PATH="$HOME/.local/bin/:$PATH"' >> ~/.bashrc +``` + +Install npm packages. ```shell -sudo apt-get install -y npm -sudo npm install -g dockerfilelint dockerfile_lint +npm install -g dockerfilelint +npm install -g dockerfile_lint ``` ### Pip Install From 5ae3896b3600e8d133598ffae76314964f9e27b7 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Fri, 3 Jan 2025 18:58:58 -0800 Subject: [PATCH 10/15] Fix dockerfile_lint unit tests when tool output includes non-json lines (for warnings). --- src/statick_tool/plugins/tool/dockerfile_lint.py | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/src/statick_tool/plugins/tool/dockerfile_lint.py b/src/statick_tool/plugins/tool/dockerfile_lint.py index 272b0d6..cb8923f 100644 --- a/src/statick_tool/plugins/tool/dockerfile_lint.py +++ b/src/statick_tool/plugins/tool/dockerfile_lint.py @@ -79,14 +79,22 @@ def add_filename(cls, output: str, src: str) -> str: """Add the filename to the json output. This is because dockerfile-lint does not include the filename in the output. + + Some warnings and errors are included in the tool output, but they are not in + json format. Those lines start with a "(". Any line that does not start with a + "(" is considered to be a line of output. """ + updated_output = "" + for line in output.splitlines(): + if not line.startswith("("): + updated_output = updated_output + line + "\n" try: - json_dict = json.loads(output) + json_dict = json.loads(updated_output) json_dict["filename"] = src return json.dumps(json_dict) except ValueError as ex: logging.warning("ValueError: %s", ex) - return output + return updated_output def parse_output( self, total_output: List[str], package: Optional[Package] = None From 8110a29418c29cdec6328752707236e7ea9a59b4 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Fri, 3 Jan 2025 19:13:57 -0800 Subject: [PATCH 11/15] Bump node version to 20 in CI. --- .github/workflows/tests.yaml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index 7fa3baf..b1578ce 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -28,7 +28,8 @@ jobs: - uses: actions/setup-node@v4 with: - node-version: '16' + node-version: '20' + cache: 'npm' - name: Install dependencies run: | From e1aaacedd180bd06175f59cd4a5484315de89aaf Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Fri, 3 Jan 2025 19:15:36 -0800 Subject: [PATCH 12/15] Remove npm cache. --- .github/workflows/tests.yaml | 1 - 1 file changed, 1 deletion(-) diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index b1578ce..01170fb 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -29,7 +29,6 @@ jobs: - uses: actions/setup-node@v4 with: node-version: '20' - cache: 'npm' - name: Install dependencies run: | From b5ac510be7dd7fc5babcfe2dc9b65046bd5ce432 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Mon, 6 Jan 2025 08:54:27 -0800 Subject: [PATCH 13/15] Use runner.os to simplify Linux-specific action steps. --- .github/workflows/tests.yaml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index 01170fb..0a7544f 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -36,7 +36,7 @@ jobs: pip install .[docs,test] - name: Install Node-based tools (Linux) - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: runner.os == 'Linux' run: | npm install -g markdownlint-cli npm install -g dockerfilelint @@ -44,7 +44,7 @@ jobs: # Do not install on macos until there is a hadolint release for macos (Darwin on arm64 architecture). - name: Install Hadolint binary (github) - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'windows-latest' + if: runner.os == 'Linux' || runner.os == 'Windows' run: | mkdir -p $HOME/.local/bin echo "$HOME/.local/bin" >> $GITHUB_PATH @@ -53,7 +53,7 @@ jobs: mv hadolint $HOME/.local/bin/ - name: Install Hadolint docker image (Linux) - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: runner.os == 'Linux' run: | docker pull hadolint/hadolint:latest @@ -71,12 +71,12 @@ jobs: fail_ci_if_error: false - name: Statick Documentation - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: runner.os == 'Linux' run: | statick . --check --user-paths . --profile documentation.yaml - name: Self check - if: matrix.os == 'ubuntu-20.04' || matrix.os == 'ubuntu-22.04' || matrix.os == 'ubuntu-24.04' + if: runner.os == 'Linux' run: | mkdir statick-output statick . --output-directory statick-output --check --profile self_check.yaml From c604758fc528baedd20f4ffaed56e048d83be321 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Thu, 9 Jan 2025 07:23:47 -0800 Subject: [PATCH 14/15] Update changelog. --- CHANGELOG.md | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 04a1f7d..9eadd7d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,25 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) ## Unreleased +### Added + +- Support for Python 3.12 and 3.13. +- Use of `pyproject.toml` instead of `setup.py` and `requirements.txt`. +- Supports new plugin discovery mechanism for the main Statick tool. + - Switched from yapsy to setuptools for plugin mechanism. (sscpac/statick#508) + +### Changed + +- Disabled code coverage requirements in CI for now. + - Unable to get line coverage working with new plugin mechanism. + Unit tests still work to find problems. +- Updated README to use more modern approach to installing Python and NPM packages. +- Rename plugin modules so they are shorter and less redundant. + +### Removed + +- No longer support Python 3.8. + ## v0.2.0 - 2025-01-03 ### Added From d480834607f2e4d74dc82681959db7de40389a79 Mon Sep 17 00:00:00 2001 From: Thomas Denewiler Date: Mon, 20 Jan 2025 13:17:44 -0800 Subject: [PATCH 15/15] Use latest statick release as dependency. --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index d3dfeee..5b10447 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -25,7 +25,7 @@ classifiers = [ dependencies = [ "importlib_metadata", - "statick@git+https://github.com/tdenewiler/statick@stdlib-plugins", + "statick", "types-docutils", ]