azure-functions-durable 1.2.9__py3-none-any.whl → 1.3.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (104) hide show
  1. azure/durable_functions/__init__.py +81 -81
  2. azure/durable_functions/constants.py +9 -9
  3. azure/durable_functions/decorators/__init__.py +3 -3
  4. azure/durable_functions/decorators/durable_app.py +260 -249
  5. azure/durable_functions/decorators/metadata.py +109 -109
  6. azure/durable_functions/entity.py +129 -125
  7. azure/durable_functions/models/DurableEntityContext.py +201 -201
  8. azure/durable_functions/models/DurableHttpRequest.py +58 -58
  9. azure/durable_functions/models/DurableOrchestrationBindings.py +66 -66
  10. azure/durable_functions/models/DurableOrchestrationClient.py +812 -781
  11. azure/durable_functions/models/DurableOrchestrationContext.py +761 -707
  12. azure/durable_functions/models/DurableOrchestrationStatus.py +156 -156
  13. azure/durable_functions/models/EntityStateResponse.py +23 -23
  14. azure/durable_functions/models/FunctionContext.py +7 -7
  15. azure/durable_functions/models/OrchestrationRuntimeStatus.py +32 -32
  16. azure/durable_functions/models/OrchestratorState.py +117 -116
  17. azure/durable_functions/models/PurgeHistoryResult.py +33 -33
  18. azure/durable_functions/models/ReplaySchema.py +9 -8
  19. azure/durable_functions/models/RetryOptions.py +69 -69
  20. azure/durable_functions/models/RpcManagementOptions.py +86 -86
  21. azure/durable_functions/models/Task.py +540 -426
  22. azure/durable_functions/models/TaskOrchestrationExecutor.py +352 -336
  23. azure/durable_functions/models/TokenSource.py +56 -56
  24. azure/durable_functions/models/__init__.py +26 -24
  25. azure/durable_functions/models/actions/Action.py +23 -23
  26. azure/durable_functions/models/actions/ActionType.py +18 -18
  27. azure/durable_functions/models/actions/CallActivityAction.py +41 -41
  28. azure/durable_functions/models/actions/CallActivityWithRetryAction.py +45 -45
  29. azure/durable_functions/models/actions/CallEntityAction.py +46 -46
  30. azure/durable_functions/models/actions/CallHttpAction.py +35 -35
  31. azure/durable_functions/models/actions/CallSubOrchestratorAction.py +40 -40
  32. azure/durable_functions/models/actions/CallSubOrchestratorWithRetryAction.py +44 -44
  33. azure/durable_functions/models/actions/CompoundAction.py +35 -35
  34. azure/durable_functions/models/actions/ContinueAsNewAction.py +36 -36
  35. azure/durable_functions/models/actions/CreateTimerAction.py +48 -48
  36. azure/durable_functions/models/actions/NoOpAction.py +35 -35
  37. azure/durable_functions/models/actions/SignalEntityAction.py +47 -47
  38. azure/durable_functions/models/actions/WaitForExternalEventAction.py +63 -63
  39. azure/durable_functions/models/actions/WhenAllAction.py +14 -14
  40. azure/durable_functions/models/actions/WhenAnyAction.py +14 -14
  41. azure/durable_functions/models/actions/__init__.py +24 -24
  42. azure/durable_functions/models/entities/EntityState.py +74 -74
  43. azure/durable_functions/models/entities/OperationResult.py +94 -76
  44. azure/durable_functions/models/entities/RequestMessage.py +53 -53
  45. azure/durable_functions/models/entities/ResponseMessage.py +48 -48
  46. azure/durable_functions/models/entities/Signal.py +62 -62
  47. azure/durable_functions/models/entities/__init__.py +17 -17
  48. azure/durable_functions/models/history/HistoryEvent.py +92 -92
  49. azure/durable_functions/models/history/HistoryEventType.py +27 -27
  50. azure/durable_functions/models/history/__init__.py +8 -8
  51. azure/durable_functions/models/utils/__init__.py +7 -7
  52. azure/durable_functions/models/utils/entity_utils.py +103 -91
  53. azure/durable_functions/models/utils/http_utils.py +80 -69
  54. azure/durable_functions/models/utils/json_utils.py +96 -56
  55. azure/durable_functions/orchestrator.py +73 -71
  56. azure/durable_functions/testing/OrchestratorGeneratorWrapper.py +42 -0
  57. azure/durable_functions/testing/__init__.py +6 -0
  58. {azure_functions_durable-1.2.9.dist-info → azure_functions_durable-1.3.0.dist-info}/LICENSE +21 -21
  59. {azure_functions_durable-1.2.9.dist-info → azure_functions_durable-1.3.0.dist-info}/METADATA +59 -58
  60. azure_functions_durable-1.3.0.dist-info/RECORD +103 -0
  61. {azure_functions_durable-1.2.9.dist-info → azure_functions_durable-1.3.0.dist-info}/WHEEL +1 -1
  62. tests/models/test_DecoratorMetadata.py +135 -135
  63. tests/models/test_Decorators.py +107 -107
  64. tests/models/test_DurableOrchestrationBindings.py +68 -68
  65. tests/models/test_DurableOrchestrationClient.py +730 -730
  66. tests/models/test_DurableOrchestrationContext.py +102 -102
  67. tests/models/test_DurableOrchestrationStatus.py +59 -59
  68. tests/models/test_OrchestrationState.py +28 -28
  69. tests/models/test_RpcManagementOptions.py +79 -79
  70. tests/models/test_TokenSource.py +10 -10
  71. tests/orchestrator/models/OrchestrationInstance.py +18 -18
  72. tests/orchestrator/orchestrator_test_utils.py +130 -130
  73. tests/orchestrator/schemas/OrchetrationStateSchema.py +66 -66
  74. tests/orchestrator/test_call_http.py +235 -176
  75. tests/orchestrator/test_continue_as_new.py +67 -67
  76. tests/orchestrator/test_create_timer.py +126 -126
  77. tests/orchestrator/test_entity.py +397 -395
  78. tests/orchestrator/test_external_event.py +53 -53
  79. tests/orchestrator/test_fan_out_fan_in.py +175 -175
  80. tests/orchestrator/test_is_replaying_flag.py +101 -101
  81. tests/orchestrator/test_retries.py +308 -308
  82. tests/orchestrator/test_sequential_orchestrator.py +841 -841
  83. tests/orchestrator/test_sequential_orchestrator_custom_status.py +119 -119
  84. tests/orchestrator/test_sequential_orchestrator_with_retry.py +465 -465
  85. tests/orchestrator/test_serialization.py +30 -30
  86. tests/orchestrator/test_sub_orchestrator.py +95 -95
  87. tests/orchestrator/test_sub_orchestrator_with_retry.py +129 -129
  88. tests/orchestrator/test_task_any.py +60 -60
  89. tests/tasks/tasks_test_utils.py +17 -17
  90. tests/tasks/test_long_timers.py +70 -0
  91. tests/tasks/test_new_uuid.py +34 -34
  92. tests/test_utils/ContextBuilder.py +174 -174
  93. tests/test_utils/EntityContextBuilder.py +56 -56
  94. tests/test_utils/constants.py +1 -1
  95. tests/test_utils/json_utils.py +30 -30
  96. tests/test_utils/testClasses.py +56 -56
  97. tests/utils/__init__.py +1 -0
  98. tests/utils/test_entity_utils.py +24 -0
  99. azure_functions_durable-1.2.9.data/data/_manifest/bsi.json +0 -1
  100. azure_functions_durable-1.2.9.data/data/_manifest/manifest.cat +0 -0
  101. azure_functions_durable-1.2.9.data/data/_manifest/manifest.spdx.json +0 -11985
  102. azure_functions_durable-1.2.9.data/data/_manifest/manifest.spdx.json.sha256 +0 -1
  103. azure_functions_durable-1.2.9.dist-info/RECORD +0 -102
  104. {azure_functions_durable-1.2.9.dist-info → azure_functions_durable-1.3.0.dist-info}/top_level.txt +0 -0
@@ -1,48 +1,48 @@
1
- from typing import Dict, Any
2
- import json
3
-
4
-
5
- class ResponseMessage:
6
- """ResponseMessage.
7
-
8
- Specifies the response of an entity, as processed by the durable-extension.
9
- """
10
-
11
- def __init__(self, result: str, is_exception: bool = False):
12
- """Instantiate a ResponseMessage.
13
-
14
- Specifies the response of an entity, as processed by the durable-extension.
15
-
16
- Parameters
17
- ----------
18
- result: str
19
- The result provided by the entity
20
- """
21
- # The time-out case seems to be handled by the Functions-Host, so
22
- # its result is not doubly-serialized. In this branch, we compensate
23
- # for this by re-serializing the payload.
24
- if result.strip().startswith("Timeout value of"):
25
- is_exception = True
26
- result = json.dumps(result)
27
-
28
- self.result = result
29
- self.is_exception = is_exception
30
- # TODO: JS has an additional exceptionType field, but does not use it
31
-
32
- @classmethod
33
- def from_dict(cls, d: Dict[str, Any]) -> 'ResponseMessage':
34
- """Instantiate a ResponseMessage from a dict of the JSON-response by the extension.
35
-
36
- Parameters
37
- ----------
38
- d: Dict[str, Any]
39
- The dictionary parsed from the JSON-response by the durable-extension
40
-
41
- Returns
42
- -------
43
- ResponseMessage:
44
- The ResponseMessage built from the provided dictionary
45
- """
46
- is_error = "exceptionType" in d.keys()
47
- result = cls(d["result"], is_error)
48
- return result
1
+ from typing import Dict, Any
2
+ import json
3
+
4
+
5
+ class ResponseMessage:
6
+ """ResponseMessage.
7
+
8
+ Specifies the response of an entity, as processed by the durable-extension.
9
+ """
10
+
11
+ def __init__(self, result: str, is_exception: bool = False):
12
+ """Instantiate a ResponseMessage.
13
+
14
+ Specifies the response of an entity, as processed by the durable-extension.
15
+
16
+ Parameters
17
+ ----------
18
+ result: str
19
+ The result provided by the entity
20
+ """
21
+ # The time-out case seems to be handled by the Functions-Host, so
22
+ # its result is not doubly-serialized. In this branch, we compensate
23
+ # for this by re-serializing the payload.
24
+ if result.strip().startswith("Timeout value of"):
25
+ is_exception = True
26
+ result = json.dumps(result)
27
+
28
+ self.result = result
29
+ self.is_exception = is_exception
30
+ # TODO: JS has an additional exceptionType field, but does not use it
31
+
32
+ @classmethod
33
+ def from_dict(cls, d: Dict[str, Any]) -> 'ResponseMessage':
34
+ """Instantiate a ResponseMessage from a dict of the JSON-response by the extension.
35
+
36
+ Parameters
37
+ ----------
38
+ d: Dict[str, Any]
39
+ The dictionary parsed from the JSON-response by the durable-extension
40
+
41
+ Returns
42
+ -------
43
+ ResponseMessage:
44
+ The ResponseMessage built from the provided dictionary
45
+ """
46
+ is_error = "exceptionType" in d.keys()
47
+ result = cls(d["result"], is_error)
48
+ return result
@@ -1,62 +1,62 @@
1
- from ..utils.entity_utils import EntityId
2
-
3
-
4
- class Signal:
5
- """An EntitySignal.
6
-
7
- Describes a signal call to a Durable Entity.
8
- """
9
-
10
- def __init__(self,
11
- target: EntityId,
12
- name: str,
13
- input_: str):
14
- """Instantiate an EntitySignal.
15
-
16
- Instantiate a signal call to a Durable Entity.
17
-
18
- Parameters
19
- ----------
20
- target: EntityId
21
- The target of signal
22
- name: str
23
- The name of the signal
24
- input_: str
25
- The signal's input
26
- """
27
- self._target = target
28
- self._name = name
29
- self._input = input_
30
-
31
- @property
32
- def target(self) -> EntityId:
33
- """Get the Signal's target entity.
34
-
35
- Returns
36
- -------
37
- EntityId
38
- EntityId of the target
39
- """
40
- return self._target
41
-
42
- @property
43
- def name(self) -> str:
44
- """Get the Signal's name.
45
-
46
- Returns
47
- -------
48
- str
49
- The Signal's name
50
- """
51
- return self._name
52
-
53
- @property
54
- def input(self) -> str:
55
- """Get the Signal's input.
56
-
57
- Returns
58
- -------
59
- str
60
- The Signal's input
61
- """
62
- return self._input
1
+ from ..utils.entity_utils import EntityId
2
+
3
+
4
+ class Signal:
5
+ """An EntitySignal.
6
+
7
+ Describes a signal call to a Durable Entity.
8
+ """
9
+
10
+ def __init__(self,
11
+ target: EntityId,
12
+ name: str,
13
+ input_: str):
14
+ """Instantiate an EntitySignal.
15
+
16
+ Instantiate a signal call to a Durable Entity.
17
+
18
+ Parameters
19
+ ----------
20
+ target: EntityId
21
+ The target of signal
22
+ name: str
23
+ The name of the signal
24
+ input_: str
25
+ The signal's input
26
+ """
27
+ self._target = target
28
+ self._name = name
29
+ self._input = input_
30
+
31
+ @property
32
+ def target(self) -> EntityId:
33
+ """Get the Signal's target entity.
34
+
35
+ Returns
36
+ -------
37
+ EntityId
38
+ EntityId of the target
39
+ """
40
+ return self._target
41
+
42
+ @property
43
+ def name(self) -> str:
44
+ """Get the Signal's name.
45
+
46
+ Returns
47
+ -------
48
+ str
49
+ The Signal's name
50
+ """
51
+ return self._name
52
+
53
+ @property
54
+ def input(self) -> str:
55
+ """Get the Signal's input.
56
+
57
+ Returns
58
+ -------
59
+ str
60
+ The Signal's input
61
+ """
62
+ return self._input
@@ -1,17 +1,17 @@
1
- """Utility classes used by the Durable Function python library for dealing with entities.
2
-
3
- _Internal Only_
4
- """
5
-
6
- from .RequestMessage import RequestMessage
7
- from .OperationResult import OperationResult
8
- from .EntityState import EntityState
9
- from .Signal import Signal
10
-
11
-
12
- __all__ = [
13
- 'RequestMessage',
14
- 'OperationResult',
15
- 'Signal',
16
- 'EntityState'
17
- ]
1
+ """Utility classes used by the Durable Function python library for dealing with entities.
2
+
3
+ _Internal Only_
4
+ """
5
+
6
+ from .RequestMessage import RequestMessage
7
+ from .OperationResult import OperationResult
8
+ from .EntityState import EntityState
9
+ from .Signal import Signal
10
+
11
+
12
+ __all__ = [
13
+ 'RequestMessage',
14
+ 'OperationResult',
15
+ 'Signal',
16
+ 'EntityState'
17
+ ]
@@ -1,92 +1,92 @@
1
- import datetime
2
- from dateutil.parser import parse as dt_parse
3
- from .HistoryEventType import HistoryEventType
4
-
5
-
6
- class HistoryEvent:
7
- """Used to communicate state relevant information from the durable extension to the client."""
8
-
9
- # parameter names are as defined by JSON schema and do not conform to PEP8 naming conventions
10
- def __init__(self, EventType: HistoryEventType, EventId: int, IsPlayed: bool, Timestamp: str,
11
- **kwargs):
12
- self._event_type: HistoryEventType = EventType
13
- self._event_id: int = EventId
14
- self._is_played: bool = IsPlayed
15
- self._timestamp: datetime.datetime = dt_parse(Timestamp)
16
- self._is_processed: bool = False
17
-
18
- self.Name = None
19
- self.InstanceId = None
20
- self.TaskScheduledId = None
21
- self.Reason = None
22
- self.Details = None
23
- self.Input = None
24
- if kwargs is not None:
25
- for key, value in kwargs.items():
26
- self.__setattr__(key, value)
27
-
28
- @property
29
- def event_type(self) -> HistoryEventType:
30
- """Get the history event type property.
31
-
32
- Returns
33
- -------
34
- HistoryEventType
35
- The type of history event
36
- """
37
- return self._event_type
38
-
39
- @property
40
- def event_id(self) -> int:
41
- """Get the event ID property.
42
-
43
- Returns
44
- -------
45
- int
46
- The value that represents the event sequence
47
- """
48
- return self._event_id
49
-
50
- @property
51
- def is_played(self) -> bool:
52
- """Get the is played property.
53
-
54
- Returns
55
- -------
56
- bool
57
- Value indicating whether the event has been played
58
- """
59
- return self._is_played
60
-
61
- @property
62
- def is_processed(self) -> bool:
63
- """Get the is process property.
64
-
65
- Returns
66
- -------
67
- bool
68
- Value indicating whether the orchestrator has processed the event
69
- """
70
- return self._is_processed
71
-
72
- @is_processed.setter
73
- def is_processed(self, value: bool):
74
- """Set the is processed property.
75
-
76
- Parameters
77
- ----------
78
- bool
79
- Value to set the property to
80
- """
81
- self._is_processed = value
82
-
83
- @property
84
- def timestamp(self) -> datetime.datetime:
85
- """Get the timestamp property.
86
-
87
- Returns
88
- -------
89
- datetime
90
- Value indicating the the time the event occurred
91
- """
92
- return self._timestamp
1
+ import datetime
2
+ from dateutil.parser import parse as dt_parse
3
+ from .HistoryEventType import HistoryEventType
4
+
5
+
6
+ class HistoryEvent:
7
+ """Used to communicate state relevant information from the durable extension to the client."""
8
+
9
+ # parameter names are as defined by JSON schema and do not conform to PEP8 naming conventions
10
+ def __init__(self, EventType: HistoryEventType, EventId: int, IsPlayed: bool, Timestamp: str,
11
+ **kwargs):
12
+ self._event_type: HistoryEventType = EventType
13
+ self._event_id: int = EventId
14
+ self._is_played: bool = IsPlayed
15
+ self._timestamp: datetime.datetime = dt_parse(Timestamp)
16
+ self._is_processed: bool = False
17
+
18
+ self.Name = None
19
+ self.InstanceId = None
20
+ self.TaskScheduledId = None
21
+ self.Reason = None
22
+ self.Details = None
23
+ self.Input = None
24
+ if kwargs is not None:
25
+ for key, value in kwargs.items():
26
+ self.__setattr__(key, value)
27
+
28
+ @property
29
+ def event_type(self) -> HistoryEventType:
30
+ """Get the history event type property.
31
+
32
+ Returns
33
+ -------
34
+ HistoryEventType
35
+ The type of history event
36
+ """
37
+ return self._event_type
38
+
39
+ @property
40
+ def event_id(self) -> int:
41
+ """Get the event ID property.
42
+
43
+ Returns
44
+ -------
45
+ int
46
+ The value that represents the event sequence
47
+ """
48
+ return self._event_id
49
+
50
+ @property
51
+ def is_played(self) -> bool:
52
+ """Get the is played property.
53
+
54
+ Returns
55
+ -------
56
+ bool
57
+ Value indicating whether the event has been played
58
+ """
59
+ return self._is_played
60
+
61
+ @property
62
+ def is_processed(self) -> bool:
63
+ """Get the is process property.
64
+
65
+ Returns
66
+ -------
67
+ bool
68
+ Value indicating whether the orchestrator has processed the event
69
+ """
70
+ return self._is_processed
71
+
72
+ @is_processed.setter
73
+ def is_processed(self, value: bool):
74
+ """Set the is processed property.
75
+
76
+ Parameters
77
+ ----------
78
+ bool
79
+ Value to set the property to
80
+ """
81
+ self._is_processed = value
82
+
83
+ @property
84
+ def timestamp(self) -> datetime.datetime:
85
+ """Get the timestamp property.
86
+
87
+ Returns
88
+ -------
89
+ datetime
90
+ Value indicating the the time the event occurred
91
+ """
92
+ return self._timestamp
@@ -1,27 +1,27 @@
1
- from enum import IntEnum
2
-
3
-
4
- class HistoryEventType(IntEnum):
5
- """Defines the different types of history events being communicated."""
6
-
7
- EXECUTION_STARTED = 0
8
- EXECUTION_COMPLETED = 1
9
- EXECUTION_FAILED = 2
10
- EXECUTION_TERMINATED = 3
11
- TASK_SCHEDULED = 4
12
- TASK_COMPLETED = 5
13
- TASK_FAILED = 6
14
- SUB_ORCHESTRATION_INSTANCE_CREATED = 7
15
- SUB_ORCHESTRATION_INSTANCE_COMPLETED = 8
16
- SUB_ORCHESTRATION_INSTANCE_FAILED = 9
17
- TIMER_CREATED = 10
18
- TIMER_FIRED = 11
19
- ORCHESTRATOR_STARTED = 12
20
- ORCHESTRATOR_COMPLETED = 13
21
- EVENT_SENT = 14
22
- EVENT_RAISED = 15
23
- CONTINUE_AS_NEW = 16
24
- GENERIC_EVENT = 17
25
- HISTORY_STATE = 18
26
- EXECUTION_SUSPENDED = 19
27
- EXECUTION_RESUMED = 20
1
+ from enum import IntEnum
2
+
3
+
4
+ class HistoryEventType(IntEnum):
5
+ """Defines the different types of history events being communicated."""
6
+
7
+ EXECUTION_STARTED = 0
8
+ EXECUTION_COMPLETED = 1
9
+ EXECUTION_FAILED = 2
10
+ EXECUTION_TERMINATED = 3
11
+ TASK_SCHEDULED = 4
12
+ TASK_COMPLETED = 5
13
+ TASK_FAILED = 6
14
+ SUB_ORCHESTRATION_INSTANCE_CREATED = 7
15
+ SUB_ORCHESTRATION_INSTANCE_COMPLETED = 8
16
+ SUB_ORCHESTRATION_INSTANCE_FAILED = 9
17
+ TIMER_CREATED = 10
18
+ TIMER_FIRED = 11
19
+ ORCHESTRATOR_STARTED = 12
20
+ ORCHESTRATOR_COMPLETED = 13
21
+ EVENT_SENT = 14
22
+ EVENT_RAISED = 15
23
+ CONTINUE_AS_NEW = 16
24
+ GENERIC_EVENT = 17
25
+ HISTORY_STATE = 18
26
+ EXECUTION_SUSPENDED = 19
27
+ EXECUTION_RESUMED = 20
@@ -1,8 +1,8 @@
1
- """Contains models related to the orchestration history of the durable functions."""
2
- from .HistoryEvent import HistoryEvent
3
- from .HistoryEventType import HistoryEventType
4
-
5
- __all__ = [
6
- 'HistoryEvent',
7
- 'HistoryEventType'
8
- ]
1
+ """Contains models related to the orchestration history of the durable functions."""
2
+ from .HistoryEvent import HistoryEvent
3
+ from .HistoryEventType import HistoryEventType
4
+
5
+ __all__ = [
6
+ 'HistoryEvent',
7
+ 'HistoryEventType'
8
+ ]
@@ -1,7 +1,7 @@
1
- """Utility functions used by the Durable Function python library.
2
-
3
- _Internal Only_
4
- """
5
- from pkgutil import extend_path
6
- import typing
7
- __path__: typing.Iterable[str] = extend_path(__path__, __name__) # type: ignore
1
+ """Utility functions used by the Durable Function python library.
2
+
3
+ _Internal Only_
4
+ """
5
+ from pkgutil import extend_path
6
+ import typing
7
+ __path__: typing.Iterable[str] = extend_path(__path__, __name__) # type: ignore