From 1f582a3c51d8783e6e540d477cedc11fdf95200e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Tue, 6 Feb 2024 11:39:41 +0200 Subject: [PATCH 01/10] Adapted code to Asphalt 5 --- .pre-commit-config.yaml | 4 +-- pyproject.toml | 16 +++++---- .../py4j/{component.py => _component.py} | 8 ++--- src/asphalt/py4j/py.typed | 0 tests/conftest.py | 6 ---- tests/test_component.py | 33 +++++++++---------- 6 files changed, 31 insertions(+), 36 deletions(-) rename src/asphalt/py4j/{component.py => _component.py} (94%) create mode 100644 src/asphalt/py4j/py.typed delete mode 100644 tests/conftest.py diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index b79f534..68fadf6 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -26,8 +26,6 @@ repos: rev: v1.8.0 hooks: - id: mypy - args: ["--explicit-package-bases"] additional_dependencies: - - asphalt - - py4j +# - asphalt - pytest diff --git a/pyproject.toml b/pyproject.toml index d9f79cb..9e0db27 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -37,9 +37,9 @@ Homepage = "https://github.com/asphalt-framework/asphalt-py4j" [project.optional-dependencies] test = [ - "anyio >= 4.0", + "anyio[trio] >= 4.1", "coverage >= 7", - "pytest", + "pytest >= 7", ] doc = [ "Sphinx >= 7.0", @@ -48,13 +48,13 @@ doc = [ ] [project.entry-points."asphalt.components"] -py4j = "asphalt.py4j.component:Py4JComponent" +py4j = "asphalt.py4j._component:Py4JComponent" [tool.setuptools_scm] version_scheme = "post-release" local_scheme = "dirty-tag" -[tool.ruff] +[tool.ruff.lint] select = [ "ASYNC", # flake8-async "E", "F", "W", # default Flake8 @@ -66,11 +66,15 @@ select = [ "UP", # pyupgrade ] +[tool.ruff.lint.isort] +known-first-party = ["asphalt.py4j"] + [tool.mypy] python_version = "3.8" -strict = true +#strict = true ignore_missing_imports = true -mypy_path = ["src", "tests"] +explicit_package_bases = true +mypy_path = ["src", "tests", "examples"] [tool.coverage.run] source = ["asphalt.py4j"] diff --git a/src/asphalt/py4j/component.py b/src/asphalt/py4j/_component.py similarity index 94% rename from src/asphalt/py4j/component.py rename to src/asphalt/py4j/_component.py index 985041f..ff788a9 100644 --- a/src/asphalt/py4j/component.py +++ b/src/asphalt/py4j/_component.py @@ -7,7 +7,7 @@ from importlib import import_module from typing import Any, Iterable, cast -from asphalt.core import Component, Context, context_teardown +from asphalt.core import Component, add_resource, context_teardown from py4j.java_gateway import ( CallbackServerParameters, @@ -16,7 +16,7 @@ launch_gateway, ) -logger = logging.getLogger(__name__) +logger = logging.getLogger("asphalt.py4j") package_re = re.compile(r"\{(.+?)\}") @@ -87,7 +87,7 @@ def __init__( self.callback_server_params = callback_server @context_teardown - async def start(self, ctx: Context) -> AsyncGenerator[None, Exception | None]: + async def start(self) -> AsyncGenerator[None, Exception | None]: if self.launch_jvm: self.gateway_params.port = launch_gateway( classpath=self.classpath, javaopts=self.javaopts @@ -97,7 +97,7 @@ async def start(self, ctx: Context) -> AsyncGenerator[None, Exception | None]: gateway_parameters=self.gateway_params, callback_server_parameters=self.callback_server_params, ) - ctx.add_resource(gateway, self.resource_name) + await add_resource(gateway, self.resource_name) logger.info( "Configured Py4J gateway (%s; address=%s, port=%d)", self.resource_name, diff --git a/src/asphalt/py4j/py.typed b/src/asphalt/py4j/py.typed new file mode 100644 index 0000000..e69de29 diff --git a/tests/conftest.py b/tests/conftest.py deleted file mode 100644 index 5c53fe0..0000000 --- a/tests/conftest.py +++ /dev/null @@ -1,6 +0,0 @@ -import pytest - - -@pytest.fixture -def anyio_backend() -> str: - return "asyncio" diff --git a/tests/test_component.py b/tests/test_component.py index 0d4084f..4808be9 100644 --- a/tests/test_component.py +++ b/tests/test_component.py @@ -4,13 +4,14 @@ import os from typing import Any -import asphalt.py4j import pytest -from asphalt.core.context import Context -from asphalt.py4j.component import Py4JComponent +from asphalt.core import Context, require_resource from py4j.java_gateway import CallbackServerParameters, GatewayParameters, JavaGateway from pytest import LogCaptureFixture +import asphalt.py4j +from asphalt.py4j._component import Py4JComponent + @pytest.mark.anyio @pytest.mark.parametrize( @@ -24,14 +25,12 @@ async def test_default_gateway( kwargs: dict[str, Any], resource_name: str, caplog: LogCaptureFixture ) -> None: """Test that the default gateway is started and is available on the context.""" - caplog.set_level(logging.INFO, logger="asphalt.py4j.component") - async with Context() as context: - await Py4JComponent(**kwargs).start(context) - context.require_resource(JavaGateway, resource_name) - - records = [ - record for record in caplog.records if record.name == "asphalt.py4j.component" - ] + caplog.set_level(logging.INFO, logger="asphalt.py4j") + async with Context(): + await Py4JComponent(**kwargs).start() + require_resource(JavaGateway, resource_name) + + records = [record for record in caplog.records if record.name == "asphalt.py4j"] records.sort(key=lambda r: r.message) assert len(records) == 2 assert records[0].message.startswith( @@ -101,9 +100,9 @@ def call(self) -> int: class Java: implements = ["java.util.concurrent.Callable"] - async with Context() as context: - await Py4JComponent(callback_server=True).start(context) - gateway = context.require_resource(JavaGateway) + async with Context(): + await Py4JComponent(callback_server=True).start() + gateway = require_resource(JavaGateway) executor = gateway.jvm.java.util.concurrent.Executors.newFixedThreadPool(1) try: future = executor.submit(NumberCallable()) @@ -120,11 +119,11 @@ async def test_gateway_close() -> None: """ gateway = JavaGateway.launch_gateway() - async with Context() as context: + async with Context(): await Py4JComponent( gateway={"port": gateway.gateway_parameters.port}, launch_jvm=False - ).start(context) - gateway2 = context.require_resource(JavaGateway) + ).start() + gateway2 = require_resource(JavaGateway) gateway2.jvm.java.lang.System.setProperty("TEST_VALUE", "abc") assert gateway.jvm.java.lang.System.getProperty("TEST_VALUE") == "abc" From e03c23c9f14f6c29af441a196515515d42273b52 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Tue, 5 Mar 2024 18:09:12 +0200 Subject: [PATCH 02/10] Added some finishing touches/updates --- .github/workflows/test.yml | 2 +- .pre-commit-config.yaml | 2 +- docs/api.rst | 4 +++- docs/conf.py | 1 + examples/simple.py | 18 ++++++++++-------- pyproject.toml | 6 +++--- src/asphalt/py4j/__init__.py | 10 ++++++++++ src/asphalt/py4j/_component.py | 11 +++++------ 8 files changed, 34 insertions(+), 20 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 767c2c4..6f4b425 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -32,7 +32,7 @@ jobs: cache: pip cache-dependency-path: pyproject.toml - name: Install dependencies - run: pip install .[test] + run: pip install -e .[test] - name: Test with pytest run: coverage run -m pytest -v - name: Generate coverage report diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 68fadf6..0a5e6e6 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -27,5 +27,5 @@ repos: hooks: - id: mypy additional_dependencies: -# - asphalt + - asphalt@git+https://github.com/asphalt-framework/asphalt@5.0 - pytest diff --git a/docs/api.rst b/docs/api.rst index cf4d164..279f54c 100644 --- a/docs/api.rst +++ b/docs/api.rst @@ -1,7 +1,9 @@ API reference ============= +.. py:currentmodule:: asphalt.py4j + Component --------- -.. autoclass:: asphalt.py4j.component.Py4JComponent +.. autoclass:: Py4JComponent diff --git a/docs/conf.py b/docs/conf.py index 616bc8e..3a16e1b 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -24,6 +24,7 @@ exclude_patterns = ["_build"] pygments_style = "sphinx" +autodoc_default_options = {"members": True, "show-inheritance": True} highlight_language = "python3" todo_include_todos = False diff --git a/examples/simple.py b/examples/simple.py index 47e5f18..0131438 100644 --- a/examples/simple.py +++ b/examples/simple.py @@ -2,19 +2,18 @@ A simple example that reads its own source code using Java classes and then prints it on standard output. """ - -from asphalt.core import CLIApplicationComponent, Context, run_application +import anyio.to_thread +from asphalt.core import CLIApplicationComponent, require_resource, run_application from py4j.java_gateway import JavaGateway class ApplicationComponent(CLIApplicationComponent): - async def start(self, ctx: Context) -> None: + async def start(self) -> None: self.add_component("py4j") - await super().start(ctx) + await super().start() - async def run(self, ctx: Context) -> None: - javagw = ctx.require_resource(JavaGateway) - async with ctx.threadpool(): + async def run(self) -> None: + def read_file() -> None: f = javagw.jvm.java.io.File(__file__) buffer = javagw.new_array(javagw.jvm.char, f.length()) reader = javagw.jvm.java.io.FileReader(f) @@ -22,5 +21,8 @@ async def run(self, ctx: Context) -> None: reader.close() print(javagw.jvm.java.lang.String(buffer)) + javagw = require_resource(JavaGateway) + await anyio.to_thread.run_sync(read_file) + -run_application(ApplicationComponent()) +anyio.run(run_application, ApplicationComponent()) diff --git a/pyproject.toml b/pyproject.toml index 9e0db27..ff6e40c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -48,7 +48,7 @@ doc = [ ] [project.entry-points."asphalt.components"] -py4j = "asphalt.py4j._component:Py4JComponent" +py4j = "asphalt.py4j:Py4JComponent" [tool.setuptools_scm] version_scheme = "post-release" @@ -71,10 +71,10 @@ known-first-party = ["asphalt.py4j"] [tool.mypy] python_version = "3.8" -#strict = true +strict = true ignore_missing_imports = true explicit_package_bases = true -mypy_path = ["src", "tests", "examples"] +mypy_path = ["src"] [tool.coverage.run] source = ["asphalt.py4j"] diff --git a/src/asphalt/py4j/__init__.py b/src/asphalt/py4j/__init__.py index e69de29..9a2a6a2 100644 --- a/src/asphalt/py4j/__init__.py +++ b/src/asphalt/py4j/__init__.py @@ -0,0 +1,10 @@ +from typing import Any + +from ._component import Py4JComponent as Py4JComponent + +# Re-export imports, so they look like they live directly in this package +key: str +value: Any +for key, value in list(locals().items()): + if getattr(value, "__module__", "").startswith("asphalt.sqlalchemy."): + value.__module__ = __name__ diff --git a/src/asphalt/py4j/_component.py b/src/asphalt/py4j/_component.py index ff788a9..05bd65a 100644 --- a/src/asphalt/py4j/_component.py +++ b/src/asphalt/py4j/_component.py @@ -97,7 +97,11 @@ async def start(self) -> AsyncGenerator[None, Exception | None]: gateway_parameters=self.gateway_params, callback_server_parameters=self.callback_server_params, ) - await add_resource(gateway, self.resource_name) + add_resource( + gateway, + self.resource_name, + teardown_callback=gateway.shutdown if self.launch_jvm else gateway.close, + ) logger.info( "Configured Py4J gateway (%s; address=%s, port=%d)", self.resource_name, @@ -107,9 +111,4 @@ async def start(self) -> AsyncGenerator[None, Exception | None]: yield - if self.launch_jvm: - gateway.shutdown() - else: - gateway.close() - logger.info("Py4J gateway (%s) shut down", self.resource_name) From 7489bf62bc9dd0a278f0b79005263f955e0c4b3a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Tue, 5 Mar 2024 18:54:49 +0200 Subject: [PATCH 03/10] Generalized the re-export code --- src/asphalt/py4j/__init__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/asphalt/py4j/__init__.py b/src/asphalt/py4j/__init__.py index 9a2a6a2..526ed02 100644 --- a/src/asphalt/py4j/__init__.py +++ b/src/asphalt/py4j/__init__.py @@ -6,5 +6,5 @@ key: str value: Any for key, value in list(locals().items()): - if getattr(value, "__module__", "").startswith("asphalt.sqlalchemy."): + if getattr(value, "__module__", "").startswith(f"{__name__}."): value.__module__ = __name__ From 1aa4bffe1a177c78c5812ea4b82ec04ff99d02bd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Tue, 26 Mar 2024 17:40:24 +0200 Subject: [PATCH 04/10] Updated GitHub actions --- .github/workflows/publish.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index d0fb4c2..92bbd0d 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -23,7 +23,7 @@ jobs: - name: Create packages run: python -m build - name: Archive packages - uses: actions/upload-artifact@v3 + uses: actions/upload-artifact@v4 with: name: dist path: dist @@ -36,7 +36,7 @@ jobs: id-token: write steps: - name: Retrieve packages - uses: actions/download-artifact@v3 + uses: actions/download-artifact@v4 - name: Upload packages uses: pypa/gh-action-pypi-publish@release/v1 From 43a960de116cae587ffef7656b9d648799e3fbae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Fri, 19 Apr 2024 01:32:16 +0300 Subject: [PATCH 05/10] Updated use of run_application() in examples to match the latest changes --- examples/simple.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/examples/simple.py b/examples/simple.py index 0131438..6e89918 100644 --- a/examples/simple.py +++ b/examples/simple.py @@ -3,7 +3,7 @@ standard output. """ import anyio.to_thread -from asphalt.core import CLIApplicationComponent, require_resource, run_application +from asphalt.core import CLIApplicationComponent, get_resource_nowait, run_application from py4j.java_gateway import JavaGateway @@ -21,8 +21,8 @@ def read_file() -> None: reader.close() print(javagw.jvm.java.lang.String(buffer)) - javagw = require_resource(JavaGateway) + javagw = get_resource_nowait(JavaGateway) await anyio.to_thread.run_sync(read_file) -anyio.run(run_application, ApplicationComponent()) +run_application(ApplicationComponent()) From 741fa3ceb0e67e4160cffc29cc3c37850ef2bd98 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Thu, 13 Jun 2024 13:12:55 +0300 Subject: [PATCH 06/10] Updated code for Asphalt 5 --- .pre-commit-config.yaml | 6 +++--- examples/simple.py | 10 +++++----- pyproject.toml | 7 +++---- src/asphalt/py4j/_component.py | 2 +- tests/test_component.py | 29 ++++++++++++++--------------- 5 files changed, 26 insertions(+), 28 deletions(-) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 0a5e6e6..9ea4618 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -5,7 +5,7 @@ # * Run "pre-commit install". repos: - repo: https://github.com/pre-commit/pre-commit-hooks - rev: v4.5.0 + rev: v4.6.0 hooks: - id: check-toml - id: check-yaml @@ -16,14 +16,14 @@ repos: - id: trailing-whitespace - repo: https://github.com/astral-sh/ruff-pre-commit - rev: v0.2.0 + rev: v0.4.8 hooks: - id: ruff args: [--fix, --show-fixes] - id: ruff-format - repo: https://github.com/pre-commit/mirrors-mypy - rev: v1.8.0 + rev: v1.10.0 hooks: - id: mypy additional_dependencies: diff --git a/examples/simple.py b/examples/simple.py index 6e89918..3c1bd18 100644 --- a/examples/simple.py +++ b/examples/simple.py @@ -2,15 +2,15 @@ A simple example that reads its own source code using Java classes and then prints it on standard output. """ -import anyio.to_thread + +from anyio import to_thread from asphalt.core import CLIApplicationComponent, get_resource_nowait, run_application from py4j.java_gateway import JavaGateway class ApplicationComponent(CLIApplicationComponent): - async def start(self) -> None: + def __init__(self) -> None: self.add_component("py4j") - await super().start() async def run(self) -> None: def read_file() -> None: @@ -22,7 +22,7 @@ def read_file() -> None: print(javagw.jvm.java.lang.String(buffer)) javagw = get_resource_nowait(JavaGateway) - await anyio.to_thread.run_sync(read_file) + await to_thread.run_sync(read_file) -run_application(ApplicationComponent()) +run_application(ApplicationComponent) diff --git a/pyproject.toml b/pyproject.toml index ff6e40c..c3ae70f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -55,15 +55,15 @@ version_scheme = "post-release" local_scheme = "dirty-tag" [tool.ruff.lint] -select = [ +extend-select = [ "ASYNC", # flake8-async - "E", "F", "W", # default Flake8 "G", # flake8-logging-format "I", # isort "ISC", # flake8-implicit-str-concat "PGH", # pygrep-hooks "RUF100", # unused noqa (yesqa) "UP", # pyupgrade + "W", # pycodestyle warnings ] [tool.ruff.lint.isort] @@ -72,9 +72,8 @@ known-first-party = ["asphalt.py4j"] [tool.mypy] python_version = "3.8" strict = true -ignore_missing_imports = true explicit_package_bases = true -mypy_path = ["src"] +mypy_path = ["src", "tests", "examples"] [tool.coverage.run] source = ["asphalt.py4j"] diff --git a/src/asphalt/py4j/_component.py b/src/asphalt/py4j/_component.py index 05bd65a..87a9c34 100644 --- a/src/asphalt/py4j/_component.py +++ b/src/asphalt/py4j/_component.py @@ -87,7 +87,7 @@ def __init__( self.callback_server_params = callback_server @context_teardown - async def start(self) -> AsyncGenerator[None, Exception | None]: + async def start(self) -> AsyncGenerator[None, BaseException | None]: if self.launch_jvm: self.gateway_params.port = launch_gateway( classpath=self.classpath, javaopts=self.javaopts diff --git a/tests/test_component.py b/tests/test_component.py index 4808be9..a3de97c 100644 --- a/tests/test_component.py +++ b/tests/test_component.py @@ -5,12 +5,12 @@ from typing import Any import pytest -from asphalt.core import Context, require_resource +from asphalt.core import Context, get_resource_nowait, start_component from py4j.java_gateway import CallbackServerParameters, GatewayParameters, JavaGateway from pytest import LogCaptureFixture import asphalt.py4j -from asphalt.py4j._component import Py4JComponent +from asphalt.py4j import Py4JComponent @pytest.mark.anyio @@ -27,16 +27,14 @@ async def test_default_gateway( """Test that the default gateway is started and is available on the context.""" caplog.set_level(logging.INFO, logger="asphalt.py4j") async with Context(): - await Py4JComponent(**kwargs).start() - require_resource(JavaGateway, resource_name) + await start_component(Py4JComponent, kwargs) + get_resource_nowait(JavaGateway, resource_name) - records = [record for record in caplog.records if record.name == "asphalt.py4j"] - records.sort(key=lambda r: r.message) - assert len(records) == 2 - assert records[0].message.startswith( + assert len(caplog.messages) == 2 + assert caplog.messages[0].startswith( f"Configured Py4J gateway ({resource_name}; address=127.0.0.1, port=" ) - assert records[1].message == f"Py4J gateway ({resource_name}) shut down" + assert caplog.messages[1] == f"Py4J gateway ({resource_name}) shut down" def test_bad_classpath_entry() -> None: @@ -101,8 +99,8 @@ class Java: implements = ["java.util.concurrent.Callable"] async with Context(): - await Py4JComponent(callback_server=True).start() - gateway = require_resource(JavaGateway) + await start_component(Py4JComponent, {"callback_server": True}) + gateway = get_resource_nowait(JavaGateway) executor = gateway.jvm.java.util.concurrent.Executors.newFixedThreadPool(1) try: future = executor.submit(NumberCallable()) @@ -120,10 +118,11 @@ async def test_gateway_close() -> None: """ gateway = JavaGateway.launch_gateway() async with Context(): - await Py4JComponent( - gateway={"port": gateway.gateway_parameters.port}, launch_jvm=False - ).start() - gateway2 = require_resource(JavaGateway) + await start_component( + Py4JComponent, + {"gateway": {"port": gateway.gateway_parameters.port}, "launch_jvm": False}, + ) + gateway2 = get_resource_nowait(JavaGateway) gateway2.jvm.java.lang.System.setProperty("TEST_VALUE", "abc") assert gateway.jvm.java.lang.System.getProperty("TEST_VALUE") == "abc" From bb201a21e5c311735af2fd4f3585753463f4508e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Fri, 13 Dec 2024 12:13:39 +0200 Subject: [PATCH 07/10] Asphalt 5 update --- .github/workflows/test.yml | 14 ++++++++------ .readthedocs.yml | 2 +- docs/requirements.txt | 4 ---- pyproject.toml | 8 ++++---- 4 files changed, 13 insertions(+), 15 deletions(-) delete mode 100644 docs/requirements.txt diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 6f4b425..af7a43d 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -11,16 +11,16 @@ jobs: fail-fast: false matrix: os: [ubuntu-latest] - python-version: ["3.8", "3.9", "3.10", "3.11", "3.12", "pypy-3.10"] + python-version: ["3.9", "3.10", "3.11", "3.12", "3.13", "pypy-3.10"] include: - os: macos-latest - python-version: "3.8" + python-version: "3.9" - os: macos-latest - python-version: "3.12" + python-version: "3.13" - os: windows-latest - python-version: "3.8" + python-version: "3.9" - os: windows-latest - python-version: "3.12" + python-version: "3.13" runs-on: ${{ matrix.os }} steps: - uses: actions/checkout@v4 @@ -32,7 +32,9 @@ jobs: cache: pip cache-dependency-path: pyproject.toml - name: Install dependencies - run: pip install -e .[test] + run: | + pip install git+https://github.com/asphalt-framework/asphalt.git@5.0 + pip install -e .[test] - name: Test with pytest run: coverage run -m pytest -v - name: Generate coverage report diff --git a/.readthedocs.yml b/.readthedocs.yml index 026b967..ac1099a 100644 --- a/.readthedocs.yml +++ b/.readthedocs.yml @@ -3,7 +3,7 @@ version: 2 build: os: ubuntu-22.04 tools: - python: "3.8" + python: "3.9" sphinx: configuration: docs/conf.py diff --git a/docs/requirements.txt b/docs/requirements.txt deleted file mode 100644 index 3b58a95..0000000 --- a/docs/requirements.txt +++ /dev/null @@ -1,4 +0,0 @@ -Sphinx >= 1.5 -sphinx_rtd_theme -sphinx-autodoc-typehints >= 1.0.5 -sphinxcontrib-asyncio >= 0.2.0 diff --git a/pyproject.toml b/pyproject.toml index c3ae70f..ab62e1c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -19,13 +19,13 @@ classifiers = [ "Typing :: Typed", "Programming Language :: Python", "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", ] -requires-python = ">=3.8" +requires-python = ">=3.9" dependencies = [ "asphalt ~= 4.8", "py4j >= 0.10.9" @@ -70,7 +70,7 @@ extend-select = [ known-first-party = ["asphalt.py4j"] [tool.mypy] -python_version = "3.8" +python_version = "3.9" strict = true explicit_package_bases = true mypy_path = ["src", "tests", "examples"] @@ -86,7 +86,7 @@ show_missing = true [tool.tox] legacy_tox_ini = """ [tox] -envlist = py38, py39, py310, py311, pypy3 +envlist = py39, py310, py311, py312, py313, pypy3 skip_missing_interpreters = true minversion = 4.0 From 55a9af1e7146d451688aad4c1fc00efbd065d3c7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Fri, 13 Dec 2024 12:24:14 +0200 Subject: [PATCH 08/10] Added pygrep-hooks to pre-commit --- .pre-commit-config.yaml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 9ea4618..e83b686 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -29,3 +29,10 @@ repos: additional_dependencies: - asphalt@git+https://github.com/asphalt-framework/asphalt@5.0 - pytest + + - repo: https://github.com/pre-commit/pygrep-hooks + rev: v1.10.0 + hooks: + - id: rst-backticks + - id: rst-directive-colons + - id: rst-inline-touching-normal From 6f69a637e313cf2403bbbdcb2942c0c8443ba186 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Mon, 30 Dec 2024 18:20:13 +0200 Subject: [PATCH 09/10] Updated configs and code for Asphalt 5 --- .github/workflows/test.yml | 4 +--- .pre-commit-config.yaml | 6 +++--- docs/conf.py | 2 ++ docs/configuration.rst | 4 +--- docs/versionhistory.rst | 5 +++++ pyproject.toml | 28 +++++++++++++++------------- src/asphalt/py4j/_component.py | 23 ++++------------------- 7 files changed, 31 insertions(+), 41 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index af7a43d..22518c8 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -32,9 +32,7 @@ jobs: cache: pip cache-dependency-path: pyproject.toml - name: Install dependencies - run: | - pip install git+https://github.com/asphalt-framework/asphalt.git@5.0 - pip install -e .[test] + run: pip install -e .[test] - name: Test with pytest run: coverage run -m pytest -v - name: Generate coverage report diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index e83b686..f649616 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -5,7 +5,7 @@ # * Run "pre-commit install". repos: - repo: https://github.com/pre-commit/pre-commit-hooks - rev: v4.6.0 + rev: v5.0.0 hooks: - id: check-toml - id: check-yaml @@ -16,14 +16,14 @@ repos: - id: trailing-whitespace - repo: https://github.com/astral-sh/ruff-pre-commit - rev: v0.4.8 + rev: v0.8.4 hooks: - id: ruff args: [--fix, --show-fixes] - id: ruff-format - repo: https://github.com/pre-commit/mirrors-mypy - rev: v1.10.0 + rev: v1.14.0 hooks: - id: mypy additional_dependencies: diff --git a/docs/conf.py b/docs/conf.py index 3a16e1b..54d2559 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -7,6 +7,7 @@ "sphinx.ext.autodoc", "sphinx.ext.intersphinx", "sphinx_autodoc_typehints", + "sphinx_rtd_theme", ] templates_path = ["_templates"] @@ -25,6 +26,7 @@ exclude_patterns = ["_build"] pygments_style = "sphinx" autodoc_default_options = {"members": True, "show-inheritance": True} +autodoc_inherit_docstrings = False highlight_language = "python3" todo_include_todos = False diff --git a/docs/configuration.rst b/docs/configuration.rst index f69cd41..634cce5 100644 --- a/docs/configuration.rst +++ b/docs/configuration.rst @@ -52,10 +52,8 @@ of the component: components: py4j: - py4j-remote: - type: py4j + py4j/remote: launch_jvm: false - resource_name: remote gateway: host: 10.0.0.1 diff --git a/docs/versionhistory.rst b/docs/versionhistory.rst index 187e695..be788b7 100644 --- a/docs/versionhistory.rst +++ b/docs/versionhistory.rst @@ -3,6 +3,11 @@ Version history This library adheres to `Semantic Versioning 2.0 `_. +**UNRELEASED** + +- **BACKWARD INCOMPATIBLE** Bumped minimum Asphalt version to 5.0 +- Dropped support for Python 3.7 and 3.8 + **4.0.0** (2023-12-26) - **BACKWARD INCOMPATIBLE** Bumped minimum Asphalt version to 4.8 diff --git a/pyproject.toml b/pyproject.toml index ab62e1c..7277c39 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -27,7 +27,7 @@ classifiers = [ ] requires-python = ">=3.9" dependencies = [ - "asphalt ~= 4.8", + "asphalt @ git+https://github.com/asphalt-framework/asphalt", "py4j >= 0.10.9" ] dynamic = ["version"] @@ -61,13 +61,18 @@ extend-select = [ "I", # isort "ISC", # flake8-implicit-str-concat "PGH", # pygrep-hooks - "RUF100", # unused noqa (yesqa) + "RUF", # Ruff-specific rules "UP", # pyupgrade "W", # pycodestyle warnings ] [tool.ruff.lint.isort] known-first-party = ["asphalt.py4j"] +known-third-party = ["asphalt.core"] + +[tool.pytest.ini_options] +addopts = ["-rsfE", "--tb=short"] +testpaths = ["tests"] [tool.mypy] python_version = "3.9" @@ -84,17 +89,14 @@ branch = true show_missing = true [tool.tox] -legacy_tox_ini = """ -[tox] -envlist = py39, py310, py311, py312, py313, pypy3 +env_list = ["py39", "py310", "py311", "py312", "py313", "pypy3"] skip_missing_interpreters = true -minversion = 4.0 -[testenv] -extras = test -commands = python -m pytest {posargs} +[tool.tox.env_run_base] +commands = [["python", "-m", "pytest", { replace = "posargs", extend = true }]] +package = "editable" +extras = ["test"] -[testenv:docs] -extras = doc -commands = sphinx-build -W -n docs build/sphinx {posargs} -""" +[tool.tox.env.docs] +commands = [["sphinx-build", "-W", "-n", "docs", "build/sphinx", { replace = "posargs", extend = true }]] +extras = ["doc"] diff --git a/src/asphalt/py4j/_component.py b/src/asphalt/py4j/_component.py index 87a9c34..ded7d4d 100644 --- a/src/asphalt/py4j/_component.py +++ b/src/asphalt/py4j/_component.py @@ -3,11 +3,11 @@ import logging import os import re -from collections.abc import AsyncGenerator +from collections.abc import Iterable from importlib import import_module -from typing import Any, Iterable, cast +from typing import Any, cast -from asphalt.core import Component, add_resource, context_teardown +from asphalt.core import Component, add_resource from py4j.java_gateway import ( CallbackServerParameters, @@ -24,7 +24,6 @@ class Py4JComponent(Component): """ Creates a :class:`~py4j.java_gateway.JavaGateway` resource. - :param resource_name: name of the Java gateway resource to be published :param launch_jvm: ``True`` to spawn a Java Virtual Machine in a subprocess and connect to it, ``False`` to connect to an existing Py4J enabled JVM :param gateway: either a :class:`~py4j.java_gateway.GatewayParameters` object or @@ -38,14 +37,12 @@ class path def __init__( self, - resource_name: str = "default", launch_jvm: bool = True, gateway: GatewayParameters | dict[str, Any] | None = None, callback_server: CallbackServerParameters | dict[str, Any] | bool = False, javaopts: Iterable[str] = (), classpath: Iterable[str] = "", ): - self.resource_name = resource_name self.launch_jvm = launch_jvm classpath = ( classpath if isinstance(classpath, str) else os.pathsep.join(classpath) @@ -86,8 +83,7 @@ def __init__( else: self.callback_server_params = callback_server - @context_teardown - async def start(self) -> AsyncGenerator[None, BaseException | None]: + async def start(self) -> None: if self.launch_jvm: self.gateway_params.port = launch_gateway( classpath=self.classpath, javaopts=self.javaopts @@ -99,16 +95,5 @@ async def start(self) -> AsyncGenerator[None, BaseException | None]: ) add_resource( gateway, - self.resource_name, teardown_callback=gateway.shutdown if self.launch_jvm else gateway.close, ) - logger.info( - "Configured Py4J gateway (%s; address=%s, port=%d)", - self.resource_name, - self.gateway_params.address, - self.gateway_params.port, - ) - - yield - - logger.info("Py4J gateway (%s) shut down", self.resource_name) From 059a419e62b18951c4be0144d74234d6d838173c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alex=20Gr=C3=B6nholm?= Date: Mon, 30 Dec 2024 18:25:18 +0200 Subject: [PATCH 10/10] Fixed asphalt core URL in pre-commit config --- .pre-commit-config.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index f649616..7827a73 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -27,7 +27,7 @@ repos: hooks: - id: mypy additional_dependencies: - - asphalt@git+https://github.com/asphalt-framework/asphalt@5.0 + - asphalt@git+https://github.com/asphalt-framework/asphalt - pytest - repo: https://github.com/pre-commit/pygrep-hooks