11from dataclasses import dataclass
22from typing import Any , Optional
33
4+ from iwf .errors import WorkflowDefinitionError
45from iwf .iwf_api .models import (
56 ExecuteApiFailurePolicy ,
67 PersistenceLoadingPolicy ,
78 RetryPolicy ,
89 WaitUntilApiFailurePolicy ,
910 WorkflowStateOptions as IdlWorkflowStateOptions ,
1011)
12+ from iwf .iwf_api .types import Unset
1113
1214
1315@dataclass
@@ -19,7 +21,17 @@ class WorkflowStateOptions:
1921 # below are wait_until API specific options:
2022 wait_until_api_timeout_seconds : Optional [int ] = None
2123 wait_until_api_retry_policy : Optional [RetryPolicy ] = None
22- wait_until_api_failure_policy : Optional [WaitUntilApiFailurePolicy ] = None
24+ """
25+ By default, workflow would fail after waitUntil API retry exhausted.
26+ This policy to allow proceeding to the execute API after waitUntil API exhausted all retries.
27+ This is useful for some advanced use cases like SAGA pattern.
28+ RetryPolicy is required to be set with maximumAttempts or maximumAttemptsDurationSeconds for waitUntil API.
29+ NOTE: execute API will use commandResults to check whether the waitUntil has succeeded or not.
30+ See more in <a href="https://github.com/indeedeng/iwf/wiki/WorkflowStateOptions">wiki</a>
31+ """
32+ proceed_to_execute_when_wait_until_retry_exhausted : Optional [
33+ WaitUntilApiFailurePolicy
34+ ] = None
2335 wait_until_api_data_attributes_loading_policy : Optional [
2436 PersistenceLoadingPolicy
2537 ] = None
@@ -30,11 +42,14 @@ class WorkflowStateOptions:
3042 execute_api_timeout_seconds : Optional [int ] = None
3143 execute_api_retry_policy : Optional [RetryPolicy ] = None
3244 """
33- note that the failing handling state will take the same input as the failed state
34- the type is Optional[type[WorkflowState]] but there is an issue with type hint...
35- TODO fix this type hint
45+ By default, workflow would fail after execute API retry exhausted.
46+ Set the state to proceed to the specified state after the execute API exhausted all retries
47+ This is useful for some advanced use cases like SAGA pattern.
48+ RetryPolicy is required to be set with maximumAttempts or maximumAttemptsDurationSeconds for execute API.
49+ Note that the failure handling state will take the same input as the failed from state.
50+ TODO the type should be the type is Optional[type[WorkflowState]] but -- there is an issue with circular import...
3651 """
37- execute_failure_handling_state : Optional [type ] = None
52+ proceed_to_state_when_execute_retry_exhausted : Optional [type ] = None
3853 execute_api_data_attributes_loading_policy : Optional [PersistenceLoadingPolicy ] = (
3954 None
4055 )
@@ -77,8 +92,20 @@ def _to_idl_state_options(
7792 )
7893 if options .data_attributes_loading_policy is not None :
7994 res .data_attributes_loading_policy = options .data_attributes_loading_policy
80- if options .wait_until_api_failure_policy is not None :
81- res .wait_until_api_failure_policy = options .wait_until_api_failure_policy
95+ if options .proceed_to_execute_when_wait_until_retry_exhausted is not None :
96+ res .wait_until_api_failure_policy = (
97+ options .proceed_to_execute_when_wait_until_retry_exhausted
98+ )
99+ if options .wait_until_api_retry_policy is None :
100+ raise WorkflowDefinitionError ("wait_until API retry policy must be set" )
101+ if isinstance (
102+ options .wait_until_api_retry_policy .maximum_attempts , Unset
103+ ) and isinstance (
104+ options .wait_until_api_retry_policy .maximum_attempts_duration_seconds , Unset
105+ ):
106+ raise WorkflowDefinitionError (
107+ "wait_until API retry policy must be set with maximum_attempts or maximum_attempts_duration_seconds"
108+ )
82109 if options .wait_until_api_retry_policy is not None :
83110 res .wait_until_api_retry_policy = options .wait_until_api_retry_policy
84111 if options .wait_until_api_timeout_seconds is not None :
@@ -87,14 +114,25 @@ def _to_idl_state_options(
87114 res .execute_api_retry_policy = options .execute_api_retry_policy
88115 if options .execute_api_timeout_seconds is not None :
89116 res .execute_api_timeout_seconds = options .execute_api_timeout_seconds
90- if options .execute_failure_handling_state is not None :
117+ if options .proceed_to_state_when_execute_retry_exhausted is not None :
91118 res .execute_api_failure_policy = (
92119 ExecuteApiFailurePolicy .PROCEED_TO_CONFIGURED_STATE
93120 )
121+ if options .execute_api_retry_policy is None :
122+ raise WorkflowDefinitionError ("execute API retry policy must be set" )
123+ if isinstance (
124+ options .execute_api_retry_policy .maximum_attempts , Unset
125+ ) and isinstance (
126+ options .execute_api_retry_policy .maximum_attempts_duration_seconds , Unset
127+ ):
128+ raise WorkflowDefinitionError (
129+ "execute API retry policy must be set with maximum_attempts or maximum_attempts_duration_seconds"
130+ )
131+
94132 from iwf .workflow_state import get_state_id_by_class
95133
96134 res .execute_api_failure_proceed_state_id = get_state_id_by_class (
97- options .execute_failure_handling_state
135+ options .proceed_to_state_when_execute_retry_exhausted
98136 )
99137 state = state_store [res .execute_api_failure_proceed_state_id ]
100138 proceed_state_options = state .get_state_options ()
0 commit comments