diff --git a/.github/workflows/default-tests.yml b/.github/workflows/default-tests.yml index a2c143ee..68b90948 100644 --- a/.github/workflows/default-tests.yml +++ b/.github/workflows/default-tests.yml @@ -9,7 +9,7 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - python-version: ["3.7", "3.8", "3.9", "3.10", "3.11"] + python-version: ["3.8", "3.9", "3.10", "3.11", "3.12"] os: [windows-latest, ubuntu-latest, macos-latest] fail-fast: false @@ -22,7 +22,7 @@ jobs: environment-name: TEST init-shell: bash create-args: >- - python=${{ matrix.python-version } pip + python=${{ matrix.python-version }} pip --file requirements.txt --file test_requirements.txt --channel conda-forge diff --git a/compliance_checker/cf/util.py b/compliance_checker/cf/util.py index 64a21c1a..6f100653 100644 --- a/compliance_checker/cf/util.py +++ b/compliance_checker/cf/util.py @@ -1,4 +1,3 @@ -import importlib.resources import itertools import os import sys @@ -6,6 +5,7 @@ import requests from cf_units import Unit +from importlib_resources import files from lxml import etree from netCDF4 import Dataset @@ -284,10 +284,7 @@ def download_cf_standard_name_table(version, location=None): if ( location is None ): # This case occurs when updating the packaged version from command line - location = ( - importlib.resources.files("compliance_checker") - / "data/cf-standard-name-table.xml" - ) + location = files("compliance_checker") / "data/cf-standard-name-table.xml" if version == "latest": url = "http://cfconventions.org/Data/cf-standard-names/current/src/cf-standard-name-table.xml" diff --git a/compliance_checker/cfutil.py b/compliance_checker/cfutil.py index 22195a22..245c6fd3 100644 --- a/compliance_checker/cfutil.py +++ b/compliance_checker/cfutil.py @@ -3,13 +3,13 @@ compliance_checker/cfutil.py """ import csv -import importlib.resources import re import warnings from collections import defaultdict from functools import lru_cache, partial from cf_units import Unit +from importlib_resources import files _UNITLESS_DB = None _SEA_NAMES = None @@ -128,7 +128,7 @@ def get_sea_names(): if _SEA_NAMES is None: buf = {} with open( - importlib.resources.files("compliance_checker") / "data/seanames.csv", + files("compliance_checker") / "data/seanames.csv", ) as f: reader = csv.reader(f) for code, sea_name in reader: diff --git a/compliance_checker/tests/conftest.py b/compliance_checker/tests/conftest.py index f4002bc5..2c662c16 100644 --- a/compliance_checker/tests/conftest.py +++ b/compliance_checker/tests/conftest.py @@ -1,9 +1,9 @@ -import importlib.resources import os import subprocess from itertools import chain import pytest +from importlib_resources import files from netCDF4 import Dataset from compliance_checker.cf import util @@ -26,9 +26,7 @@ def static_files(cdl_stem): Returns the Path to a valid nc dataset\n replaces the old STATIC_FILES dict """ - datadir = ( - importlib.resources.files("compliance_checker").joinpath("tests/data").resolve() - ) + datadir = files("compliance_checker").joinpath("tests/data").resolve() assert datadir.exists(), f"{datadir} not found" cdl_paths = glob_down(datadir, f"{cdl_stem}.cdl", 3) diff --git a/compliance_checker/tests/resources.py b/compliance_checker/tests/resources.py index 67786179..7bbca9d6 100644 --- a/compliance_checker/tests/resources.py +++ b/compliance_checker/tests/resources.py @@ -1,12 +1,13 @@ -import importlib.resources import subprocess +from importlib_resources import files + def get_filename(path): """ Returns the path to a valid dataset """ - filename = importlib.resources.files("compliance_checker") / path + filename = files("compliance_checker") / path nc_path = filename.with_suffix(".nc") if not nc_path.exists(): generate_dataset(filename, nc_path) diff --git a/compliance_checker/tests/test_suite.py b/compliance_checker/tests/test_suite.py index 0bbbc44d..8c8987df 100644 --- a/compliance_checker/tests/test_suite.py +++ b/compliance_checker/tests/test_suite.py @@ -1,30 +1,23 @@ -import importlib.resources import os import unittest from pathlib import Path import numpy as np +from importlib_resources import files from compliance_checker.acdd import ACDDBaseCheck from compliance_checker.base import BaseCheck, GenericFile, Result from compliance_checker.suite import CheckSuite static_files = { - "2dim": importlib.resources.files("compliance_checker") / "tests/data/2dim-grid.nc", - "bad_region": importlib.resources.files("compliance_checker") - / "tests/data/bad_region.nc", - "bad_data_type": importlib.resources.files("compliance_checker") - / "tests/data/bad_data_type.nc", - "test_cdl": importlib.resources.files("compliance_checker") - / "tests/data/test_cdl.cdl", - "test_cdl_nc": importlib.resources.files("compliance_checker") - / "tests/data/test_cdl_nc_file.nc", - "empty": importlib.resources.files("compliance_checker") - / "tests/data/non-comp/empty.file", - "ru07": importlib.resources.files("compliance_checker") - / "tests/data/ru07-20130824T170228_rt0.nc", - "netCDF4": importlib.resources.files("compliance_checker") - / "tests/data/test_cdl_nc4_file.cdl", + "2dim": files("compliance_checker") / "tests/data/2dim-grid.nc", + "bad_region": files("compliance_checker") / "tests/data/bad_region.nc", + "bad_data_type": files("compliance_checker") / "tests/data/bad_data_type.nc", + "test_cdl": files("compliance_checker") / "tests/data/test_cdl.cdl", + "test_cdl_nc": files("compliance_checker") / "tests/data/test_cdl_nc_file.nc", + "empty": files("compliance_checker") / "tests/data/non-comp/empty.file", + "ru07": files("compliance_checker") / "tests/data/ru07-20130824T170228_rt0.nc", + "netCDF4": files("compliance_checker") / "tests/data/test_cdl_nc4_file.cdl", } diff --git a/pyproject.toml b/pyproject.toml index be14e45f..a78aad24 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -6,6 +6,81 @@ requires = [ "wheel", ] +[project] +name = "compliance-checker" +description = "Checks Datasets and SOS endpoints for standards compliance" +readme = "README.md" +license = {text = "Apache-2.0"} +maintainers = [ + {name = "Dave Foster", email = "dave@axiomdatascience.com"}, + {name = "Benjamin Adams"}, + {name = "Luke Campbell"}, + {name = "Filipe Fernandes"}, +] +requires-python = ">=3.8" +classifiers=[ + "Development Status :: 5 - Production/Stable", + "Intended Audience :: Developers", + "Intended Audience :: Science/Research", + "License :: OSI Approved :: Apache Software License", + "Operating System :: MacOS :: MacOS X", + "Operating System :: Microsoft :: Windows", + "Operating System :: POSIX :: Linux", + "Programming Language :: Python", + "Programming Language :: Python :: 3 :: Only", + "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 :: Scientific/Engineering", +] +dynamic = [ + "dependencies", + "version", +] +[project.urls] +documentation = "https://ioos.github.io/compliance-checker" +homepage = "https://compliance.ioos.us/index.html" +repository = "https://github.com/ioos/compliance-checker" +[project.scripts] +compliance-checker = "cchecker:main" +[project.entry-points."compliance_checker.suites"] +"acdd-1.1" = "compliance_checker.acdd:ACDD1_1Check" +"acdd-1.3" = "compliance_checker.acdd:ACDD1_3Check" +"cf-1.6" = "compliance_checker.cf.cf:CF1_6Check" +"cf-1.7" = "compliance_checker.cf.cf:CF1_7Check" +"cf-1.8" = "compliance_checker.cf.cf:CF1_8Check" +"ioos-0.1" = "compliance_checker.ioos:IOOS0_1Check" +"ioos-1.1" = "compliance_checker.ioos:IOOS1_1Check" +"ioos-1.2" = "compliance_checker.ioos:IOOS1_2Check" +"ioos_sos" = "compliance_checker.ioos:IOOSBaseSOSCheck" + +[tool.setuptools] +packages = ["compliance_checker"] +license-files = ["LICENSE"] +zip-safe = false +include-package-data = true +script-files = ["cchecker.py"] + +[tool.setuptools.package-data] +compliance_checker = [ + "data/*.xml", + "tests/data/*.nc", + "tests/data/*.cdl", + "tests/data/non-comp/*.cdl", + "data/templates/*.j2", +] + +[tool.setuptools.dynamic] +dependencies = {file = ["requirements.txt"]} +readme = {file = "README.md", content-type = "text/markdown"} + +[tool.setuptools_scm] +write_to = "compliance_checker/_version.py" +write_to_template = "__version__ = '{version}'" +tag_regex = "^(?Pv)?(?P[^\\+]+)(?P.*)?$" + [tool.ruff] lint.select = [ "A", # flake8-builtins @@ -41,3 +116,8 @@ markers = [ "integration: marks integration tests (deselect with '-m \"not integration\"')", "slowtest: marks slow tests (deselect with '-m \"not slowtest\"')" ] +filterwarnings = [ + "error:::compliance-checker.*", + "ignore::UserWarning", + "ignore::RuntimeWarning", +] diff --git a/requirements.txt b/requirements.txt index 5c04ef39..6277c633 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,5 +1,6 @@ cf-units>=2 cftime>=1.1.0 +importlib-resources # drop this when dropping Python 3.8 isodate>=0.6.1 jinja2>=2.7.3 lxml>=3.2.1 diff --git a/setup.py b/setup.py deleted file mode 100644 index e26a432b..00000000 --- a/setup.py +++ /dev/null @@ -1,81 +0,0 @@ -from setuptools import find_packages, setup - - -def readme(): - with open("README.md", encoding="utf-8") as f: - return f.read() - - -def pip_requirements(fname="requirements.txt"): - reqs = [] - with open(fname) as f: - for line in f: - line = line.strip() - if not line or line.startswith("#"): - continue - reqs.append(line) - - return reqs - - -setup( - name="compliance-checker", - description="Checks Datasets and SOS endpoints for standards compliance", - long_description=readme(), - long_description_content_type="text/markdown", - license="Apache License 2.0", - author="Dave Foster", - author_email="dave@axiomdatascience.com", - url="https://github.com/ioos/compliance-checker", - packages=find_packages(), - install_requires=pip_requirements(), - python_requires="~=3.7", - tests_require=["pytest"], - classifiers=[ - "Development Status :: 5 - Production/Stable", - "Intended Audience :: Developers", - "Intended Audience :: Science/Research", - "License :: OSI Approved :: Apache Software License", - "Operating System :: POSIX :: Linux", - "Operating System :: MacOS :: MacOS X", - "Operating System :: Microsoft :: Windows", - "Programming Language :: Python", - "Topic :: Scientific/Engineering", - ], - include_package_data=True, - scripts=["cchecker.py"], - # Note: Do not use colons in the entry-point keys. Python 3 reserves - # portions of the key after a colon for special use. - # Note: The entry point names are not used at all. All methods in the - # compliance checker use class attributes to determine the checker's name - # and version. But, an entry point must be defined for each plugin to be - # loaded. - entry_points={ - "console_scripts": ["compliance-checker = cchecker:main"], - "compliance_checker.suites": [ - "cf-1.6 = compliance_checker.cf.cf:CF1_6Check", - "cf-1.7 = compliance_checker.cf.cf:CF1_7Check", - "cf-1.8 = compliance_checker.cf.cf:CF1_8Check", - "acdd-1.1 = compliance_checker.acdd:ACDD1_1Check", - "acdd-1.3 = compliance_checker.acdd:ACDD1_3Check", - "ioos_sos = compliance_checker.ioos:IOOSBaseSOSCheck", - "ioos-0.1 = compliance_checker.ioos:IOOS0_1Check", - "ioos-1.1 = compliance_checker.ioos:IOOS1_1Check", - "ioos-1.2 = compliance_checker.ioos:IOOS1_2Check", - ], - }, - package_data={ - "compliance_checker": [ - "data/*.xml", - "tests/data/*.nc", - "tests/data/*.cdl", - "tests/data/non-comp/*.cdl", - "data/templates/*.j2", - ], - }, - use_scm_version={ - "write_to": "compliance_checker/_version.py", - "write_to_template": '__version__ = "{version}"', - "tag_regex": r"^(?Pv)?(?P[^\+]+)(?P.*)?$", - }, -)