From c461e155e90be68e1b4341978991fbb44cc7226f Mon Sep 17 00:00:00 2001 From: Alexander Goscinski Date: Mon, 13 Apr 2026 12:19:02 +0200 Subject: [PATCH 1/3] Fix broken imports and deprecated API usage that caused CI failures Restore missing imports (AttributesFrozendict, type_check, kiwipy, typing members) in ports.py and workchains.py, remove unused imports (abc, six), re-add required __all__ in ports.py, and replace deprecated inspect.getargspec with getfullargspec in lang.py and workchains.py. --- src/plumpy/lang.py | 4 ++-- src/plumpy/ports.py | 5 +++-- src/plumpy/workchains.py | 20 ++++++++++++++++++-- 3 files changed, 23 insertions(+), 6 deletions(-) diff --git a/src/plumpy/lang.py b/src/plumpy/lang.py index 4efd5827..450927d6 100644 --- a/src/plumpy/lang.py +++ b/src/plumpy/lang.py @@ -13,7 +13,7 @@ def wrap(func: Callable[..., Any]) -> Callable[..., Any]: if isinstance(func, property): raise RuntimeError('Protected must go after @property decorator') - args = inspect.getargspec(func)[0] + args = inspect.getfullargspec(func)[0] if len(args) == 0: raise RuntimeError('Can only use the protected decorator on member functions') @@ -45,7 +45,7 @@ def wrap(func: Callable[..., Any]) -> Callable[..., Any]: if isinstance(func, property): raise RuntimeError('Override must go after @property decorator') - args = inspect.getargspec(func)[0] + args = inspect.getfullargspec(func)[0] if len(args) == 0: raise RuntimeError('Can only use the override decorator on member functions') diff --git a/src/plumpy/ports.py b/src/plumpy/ports.py index 7d782a46..25a05a5a 100644 --- a/src/plumpy/ports.py +++ b/src/plumpy/ports.py @@ -1,6 +1,5 @@ # -*- coding: utf-8 -*- """Module for process ports""" -import abc import collections import copy import inspect @@ -9,7 +8,9 @@ import warnings from typing import Any, Callable, Dict, Iterator, List, Mapping, MutableMapping, Optional, Sequence, Type, Union, cast -from plumpy.utils import is_mutable_property +from plumpy.utils import AttributesFrozendict, is_mutable_property, type_check + +__all__ = ['UNSPECIFIED', 'InputPort', 'OutputPort', 'Port', 'PortNamespace', 'PortValidationError'] _LOGGER = logging.getLogger(__name__) UNSPECIFIED = () diff --git a/src/plumpy/workchains.py b/src/plumpy/workchains.py index b97facd4..b48b1c6b 100644 --- a/src/plumpy/workchains.py +++ b/src/plumpy/workchains.py @@ -7,7 +7,23 @@ import inspect import logging import re -import six +from typing import ( + Any, + Callable, + Dict, + Hashable, + List, + Mapping, + MutableSequence, + Optional, + Sequence, + Tuple, + Type, + Union, + cast, +) + +import kiwipy from . import lang, mixins, persistence, process_states, processes from .utils import PID_TYPE, SAVED_STATE_TYPE @@ -248,7 +264,7 @@ def __str__(self) -> str: class _FunctionCall(_Instruction): def __init__(self, func: WC_COMMAND_TYPE) -> None: try: - args = inspect.getargspec(func)[0] + args = inspect.getfullargspec(func)[0] except TypeError: raise TypeError(f'func is not a function, got {type(func)}') if len(args) != 1: From 7d3a49e95c468357c95aea7aad59009f08b0ff52 Mon Sep 17 00:00:00 2001 From: Alexander Goscinski Date: Mon, 13 Apr 2026 12:45:05 +0200 Subject: [PATCH 2/3] Fix pre-commit failures: ruff format, ruff lint, and mypy - Apply ruff format fixes in state_machine.py and ports.py (string concat, assert style) - Add __hash__ to __NULL class to fix PLW1641 and remove stale noqa: N801 - Ignore N801 and PLC0415 rules in ruff config (internal sentinel class, intentional lazy imports) - Fix mypy attr-defined error by using types.MethodType instead of __get__ in utils.py --- pyproject.toml | 4 +++- src/plumpy/base/state_machine.py | 2 +- src/plumpy/lang.py | 5 ++++- src/plumpy/ports.py | 7 ++++--- src/plumpy/utils.py | 2 +- 5 files changed, 13 insertions(+), 7 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index 21d506f1..4b4c1a41 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -94,7 +94,9 @@ ignore = [ 'PLR0915', # Too many statements 'PLR2004', # Magic value used in comparison 'RUF005', # Consider iterable unpacking instead of concatenation - 'RUF012' # Mutable class attributes should be annotated with `typing.ClassVar` + 'RUF012', # Mutable class attributes should be annotated with `typing.ClassVar` + 'PLC0415', # `import` should be at the top-level of a file + 'N801', # Class name should use CapWords convention (for internal __NULL sentinel) ] select = [ 'E', # pydocstyle diff --git a/src/plumpy/base/state_machine.py b/src/plumpy/base/state_machine.py index 317d73bb..ea5f93fd 100644 --- a/src/plumpy/base/state_machine.py +++ b/src/plumpy/base/state_machine.py @@ -114,7 +114,7 @@ def transition(self: Any, *a: Any, **kw: Any) -> Any: raise EventError( evt_label, - 'Event produced invalid state transition from ' f'{initial.LABEL} to {self._state.LABEL}', + f'Event produced invalid state transition from {initial.LABEL} to {self._state.LABEL}', ) return result diff --git a/src/plumpy/lang.py b/src/plumpy/lang.py index 450927d6..1aa91e3a 100644 --- a/src/plumpy/lang.py +++ b/src/plumpy/lang.py @@ -67,9 +67,12 @@ def wrapped_fn(self: Any, *args: Any, **kwargs: Any) -> Callable[..., Any]: return wrap -class __NULL: # noqa: N801 +class __NULL: def __eq__(self, other: Any) -> bool: return isinstance(other, self.__class__) + def __hash__(self) -> int: + return id(self) + NULL = __NULL() diff --git a/src/plumpy/ports.py b/src/plumpy/ports.py index 25a05a5a..86411ad2 100644 --- a/src/plumpy/ports.py +++ b/src/plumpy/ports.py @@ -1,5 +1,6 @@ # -*- coding: utf-8 -*- """Module for process ports""" + import collections import copy import inspect @@ -663,9 +664,9 @@ def validate( else: message = self.validator(port_values_clone, self) if message is not None: - assert isinstance( - message, str - ), f"Validator returned something other than None or str: '{type(message)}'" + assert isinstance(message, str), ( + f"Validator returned something other than None or str: '{type(message)}'" + ) return PortValidationError(message, breadcrumbs_to_port(breadcrumbs_local)) return None diff --git a/src/plumpy/utils.py b/src/plumpy/utils.py index d81c936a..f627782f 100644 --- a/src/plumpy/utils.py +++ b/src/plumpy/utils.py @@ -135,7 +135,7 @@ def load_function(name: str, instance: Optional[Any] = None) -> Callable[..., An obj = load_object(name) if inspect.ismethod(obj): if instance is not None: - return obj.__get__(instance, instance.__class__) + return types.MethodType(obj.__func__, instance) return obj From 854960f925a270bd9d6df2e85e32457945fa5ff8 Mon Sep 17 00:00:00 2001 From: Alexander Goscinski Date: Mon, 13 Apr 2026 12:53:43 +0200 Subject: [PATCH 3/3] Fix assert formatting to match pre-commit ruff v0.8.0 The pre-commit hook uses ruff v0.8.0 which formats assert statements differently than the locally installed ruff v0.14.8. --- src/plumpy/ports.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/plumpy/ports.py b/src/plumpy/ports.py index 86411ad2..cfbd92d5 100644 --- a/src/plumpy/ports.py +++ b/src/plumpy/ports.py @@ -664,9 +664,9 @@ def validate( else: message = self.validator(port_values_clone, self) if message is not None: - assert isinstance(message, str), ( - f"Validator returned something other than None or str: '{type(message)}'" - ) + assert isinstance( + message, str + ), f"Validator returned something other than None or str: '{type(message)}'" return PortValidationError(message, breadcrumbs_to_port(breadcrumbs_local)) return None