diff --git a/src/nexusrpc/__init__.py b/src/nexusrpc/__init__.py index 019dc0e..e8aef51 100644 --- a/src/nexusrpc/__init__.py +++ b/src/nexusrpc/__init__.py @@ -18,7 +18,6 @@ from . import handler from ._common import ( HandlerError, - HandlerErrorRetryBehavior, HandlerErrorType, InputT, Link, @@ -43,7 +42,6 @@ "handler", "HandlerError", "HandlerErrorType", - "HandlerErrorRetryBehavior", "InputT", "LazyValue", "Link", diff --git a/src/nexusrpc/_common.py b/src/nexusrpc/_common.py index cca6baf..fa9c1a7 100644 --- a/src/nexusrpc/_common.py +++ b/src/nexusrpc/_common.py @@ -48,42 +48,42 @@ def __init__( message: str, *, type: HandlerErrorType, - retry_behavior: Optional[HandlerErrorRetryBehavior] = None, + retryable_override: Optional[bool] = None, ): """ Initialize a new HandlerError. - :param message: A descriptive message for the error. This will become the - `message` in the resulting Nexus Failure object. + :param message: A descriptive message for the error. This will become + the `message` in the resulting Nexus Failure object. :param type: The :py:class:`HandlerErrorType` of the error. - :param retry_behavior: Optional retry behavior for the error. + :param retryable_override: Optionally set whether the error should be + retried. By default, the error type is used + to determine this. """ super().__init__(message) self._type = type - self._retry_behavior = retry_behavior + self._retryable_override = retryable_override @property - def retry_behavior(self) -> Optional[HandlerErrorRetryBehavior]: + def retryable_override(self) -> Optional[bool]: """ - The retry behavior set for this error. + The optional retryability override set when this error was created. """ - return self._retry_behavior + return self._retryable_override @property def retryable(self) -> bool: """ Whether this error should be retried. - If :py:attr:`retry_behavior` is None, then the default behavior for the error - type is used. See + If :py:attr:`retryable_override` is None, then the default behavior for the + error type is used. See https://github.com/nexus-rpc/api/blob/main/SPEC.md#predefined-handler-errors """ - if self.retry_behavior == HandlerErrorRetryBehavior.RETRYABLE: - return True - elif self.retry_behavior == HandlerErrorRetryBehavior.NON_RETRYABLE: - return False + if self._retryable_override is not None: + return self._retryable_override non_retryable_types = { HandlerErrorType.BAD_REQUEST, @@ -116,22 +116,6 @@ def type(self) -> HandlerErrorType: return self._type -class HandlerErrorRetryBehavior(Enum): - """ - Retry behavior for a handler error. - """ - - RETRYABLE = "RETRYABLE" - """ - The error should be retried. - """ - - NON_RETRYABLE = "NON_RETRYABLE" - """ - The error should not be retried. - """ - - class HandlerErrorType(Enum): """Nexus handler error types. diff --git a/tests/test_common.py b/tests/test_common.py new file mode 100644 index 0000000..11e0abb --- /dev/null +++ b/tests/test_common.py @@ -0,0 +1,41 @@ +from nexusrpc._common import HandlerError, HandlerErrorType + + +def test_handler_error_retryable_type(): + retryable_error_type = HandlerErrorType.RESOURCE_EXHAUSTED + assert HandlerError( + "test", + type=retryable_error_type, + retryable_override=True, + ).retryable + + assert not HandlerError( + "test", + type=retryable_error_type, + retryable_override=False, + ).retryable + + assert HandlerError( + "test", + type=retryable_error_type, + ).retryable + + +def test_handler_error_non_retryable_type(): + non_retryable_error_type = HandlerErrorType.BAD_REQUEST + assert HandlerError( + "test", + type=non_retryable_error_type, + retryable_override=True, + ).retryable + + assert not HandlerError( + "test", + type=non_retryable_error_type, + retryable_override=False, + ).retryable + + assert not HandlerError( + "test", + type=non_retryable_error_type, + ).retryable