amit-temporalio 0.3.1-x86_64-linux-musl
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.
- checksums.yaml +7 -0
- data/.yardopts +2 -0
- data/Gemfile +23 -0
- data/Rakefile +101 -0
- data/lib/temporalio/activity/complete_async_error.rb +11 -0
- data/lib/temporalio/activity/context.rb +116 -0
- data/lib/temporalio/activity/definition.rb +189 -0
- data/lib/temporalio/activity/info.rb +64 -0
- data/lib/temporalio/activity.rb +12 -0
- data/lib/temporalio/api/activity/v1/message.rb +25 -0
- data/lib/temporalio/api/batch/v1/message.rb +31 -0
- data/lib/temporalio/api/cloud/account/v1/message.rb +28 -0
- data/lib/temporalio/api/cloud/cloudservice/v1/request_response.rb +126 -0
- data/lib/temporalio/api/cloud/cloudservice/v1/service.rb +25 -0
- data/lib/temporalio/api/cloud/cloudservice.rb +3 -0
- data/lib/temporalio/api/cloud/identity/v1/message.rb +41 -0
- data/lib/temporalio/api/cloud/namespace/v1/message.rb +42 -0
- data/lib/temporalio/api/cloud/nexus/v1/message.rb +31 -0
- data/lib/temporalio/api/cloud/operation/v1/message.rb +28 -0
- data/lib/temporalio/api/cloud/region/v1/message.rb +24 -0
- data/lib/temporalio/api/cloud/resource/v1/message.rb +23 -0
- data/lib/temporalio/api/cloud/sink/v1/message.rb +24 -0
- data/lib/temporalio/api/cloud/usage/v1/message.rb +31 -0
- data/lib/temporalio/api/command/v1/message.rb +46 -0
- data/lib/temporalio/api/common/v1/grpc_status.rb +23 -0
- data/lib/temporalio/api/common/v1/message.rb +47 -0
- data/lib/temporalio/api/enums/v1/batch_operation.rb +22 -0
- data/lib/temporalio/api/enums/v1/command_type.rb +21 -0
- data/lib/temporalio/api/enums/v1/common.rb +26 -0
- data/lib/temporalio/api/enums/v1/event_type.rb +21 -0
- data/lib/temporalio/api/enums/v1/failed_cause.rb +26 -0
- data/lib/temporalio/api/enums/v1/namespace.rb +23 -0
- data/lib/temporalio/api/enums/v1/query.rb +22 -0
- data/lib/temporalio/api/enums/v1/reset.rb +23 -0
- data/lib/temporalio/api/enums/v1/schedule.rb +21 -0
- data/lib/temporalio/api/enums/v1/task_queue.rb +25 -0
- data/lib/temporalio/api/enums/v1/update.rb +22 -0
- data/lib/temporalio/api/enums/v1/workflow.rb +30 -0
- data/lib/temporalio/api/errordetails/v1/message.rb +42 -0
- data/lib/temporalio/api/export/v1/message.rb +24 -0
- data/lib/temporalio/api/failure/v1/message.rb +35 -0
- data/lib/temporalio/api/filter/v1/message.rb +27 -0
- data/lib/temporalio/api/history/v1/message.rb +90 -0
- data/lib/temporalio/api/namespace/v1/message.rb +31 -0
- data/lib/temporalio/api/nexus/v1/message.rb +40 -0
- data/lib/temporalio/api/operatorservice/v1/request_response.rb +49 -0
- data/lib/temporalio/api/operatorservice/v1/service.rb +23 -0
- data/lib/temporalio/api/operatorservice.rb +3 -0
- data/lib/temporalio/api/payload_visitor.rb +1513 -0
- data/lib/temporalio/api/protocol/v1/message.rb +23 -0
- data/lib/temporalio/api/query/v1/message.rb +27 -0
- data/lib/temporalio/api/replication/v1/message.rb +26 -0
- data/lib/temporalio/api/schedule/v1/message.rb +43 -0
- data/lib/temporalio/api/sdk/v1/enhanced_stack_trace.rb +25 -0
- data/lib/temporalio/api/sdk/v1/task_complete_metadata.rb +21 -0
- data/lib/temporalio/api/sdk/v1/user_metadata.rb +23 -0
- data/lib/temporalio/api/sdk/v1/workflow_metadata.rb +23 -0
- data/lib/temporalio/api/taskqueue/v1/message.rb +45 -0
- data/lib/temporalio/api/testservice/v1/request_response.rb +31 -0
- data/lib/temporalio/api/testservice/v1/service.rb +23 -0
- data/lib/temporalio/api/update/v1/message.rb +33 -0
- data/lib/temporalio/api/version/v1/message.rb +26 -0
- data/lib/temporalio/api/workflow/v1/message.rb +43 -0
- data/lib/temporalio/api/workflowservice/v1/request_response.rb +204 -0
- data/lib/temporalio/api/workflowservice/v1/service.rb +23 -0
- data/lib/temporalio/api/workflowservice.rb +3 -0
- data/lib/temporalio/api.rb +14 -0
- data/lib/temporalio/cancellation.rb +170 -0
- data/lib/temporalio/client/activity_id_reference.rb +32 -0
- data/lib/temporalio/client/async_activity_handle.rb +85 -0
- data/lib/temporalio/client/connection/cloud_service.rb +726 -0
- data/lib/temporalio/client/connection/operator_service.rb +201 -0
- data/lib/temporalio/client/connection/service.rb +42 -0
- data/lib/temporalio/client/connection/test_service.rb +111 -0
- data/lib/temporalio/client/connection/workflow_service.rb +1041 -0
- data/lib/temporalio/client/connection.rb +316 -0
- data/lib/temporalio/client/interceptor.rb +416 -0
- data/lib/temporalio/client/schedule.rb +967 -0
- data/lib/temporalio/client/schedule_handle.rb +126 -0
- data/lib/temporalio/client/workflow_execution.rb +100 -0
- data/lib/temporalio/client/workflow_execution_count.rb +36 -0
- data/lib/temporalio/client/workflow_execution_status.rb +18 -0
- data/lib/temporalio/client/workflow_handle.rb +389 -0
- data/lib/temporalio/client/workflow_query_reject_condition.rb +14 -0
- data/lib/temporalio/client/workflow_update_handle.rb +65 -0
- data/lib/temporalio/client/workflow_update_wait_stage.rb +17 -0
- data/lib/temporalio/client.rb +484 -0
- data/lib/temporalio/common_enums.rb +41 -0
- data/lib/temporalio/converters/data_converter.rb +99 -0
- data/lib/temporalio/converters/failure_converter.rb +202 -0
- data/lib/temporalio/converters/payload_codec.rb +26 -0
- data/lib/temporalio/converters/payload_converter/binary_null.rb +34 -0
- data/lib/temporalio/converters/payload_converter/binary_plain.rb +35 -0
- data/lib/temporalio/converters/payload_converter/binary_protobuf.rb +42 -0
- data/lib/temporalio/converters/payload_converter/composite.rb +66 -0
- data/lib/temporalio/converters/payload_converter/encoding.rb +35 -0
- data/lib/temporalio/converters/payload_converter/json_plain.rb +44 -0
- data/lib/temporalio/converters/payload_converter/json_protobuf.rb +41 -0
- data/lib/temporalio/converters/payload_converter.rb +71 -0
- data/lib/temporalio/converters/raw_value.rb +20 -0
- data/lib/temporalio/converters.rb +9 -0
- data/lib/temporalio/error/failure.rb +219 -0
- data/lib/temporalio/error.rb +155 -0
- data/lib/temporalio/internal/bridge/3.2/temporalio_bridge.so +0 -0
- data/lib/temporalio/internal/bridge/3.3/temporalio_bridge.so +0 -0
- data/lib/temporalio/internal/bridge/3.4/temporalio_bridge.so +0 -0
- data/lib/temporalio/internal/bridge/api/activity_result/activity_result.rb +34 -0
- data/lib/temporalio/internal/bridge/api/activity_task/activity_task.rb +31 -0
- data/lib/temporalio/internal/bridge/api/child_workflow/child_workflow.rb +33 -0
- data/lib/temporalio/internal/bridge/api/common/common.rb +26 -0
- data/lib/temporalio/internal/bridge/api/core_interface.rb +40 -0
- data/lib/temporalio/internal/bridge/api/external_data/external_data.rb +27 -0
- data/lib/temporalio/internal/bridge/api/nexus/nexus.rb +33 -0
- data/lib/temporalio/internal/bridge/api/workflow_activation/workflow_activation.rb +56 -0
- data/lib/temporalio/internal/bridge/api/workflow_commands/workflow_commands.rb +57 -0
- data/lib/temporalio/internal/bridge/api/workflow_completion/workflow_completion.rb +30 -0
- data/lib/temporalio/internal/bridge/api.rb +3 -0
- data/lib/temporalio/internal/bridge/client.rb +95 -0
- data/lib/temporalio/internal/bridge/runtime.rb +53 -0
- data/lib/temporalio/internal/bridge/testing.rb +66 -0
- data/lib/temporalio/internal/bridge/worker.rb +85 -0
- data/lib/temporalio/internal/bridge.rb +36 -0
- data/lib/temporalio/internal/client/implementation.rb +700 -0
- data/lib/temporalio/internal/metric.rb +122 -0
- data/lib/temporalio/internal/proto_utils.rb +133 -0
- data/lib/temporalio/internal/worker/activity_worker.rb +376 -0
- data/lib/temporalio/internal/worker/multi_runner.rb +213 -0
- data/lib/temporalio/internal/worker/workflow_instance/child_workflow_handle.rb +54 -0
- data/lib/temporalio/internal/worker/workflow_instance/context.rb +333 -0
- data/lib/temporalio/internal/worker/workflow_instance/details.rb +44 -0
- data/lib/temporalio/internal/worker/workflow_instance/external_workflow_handle.rb +32 -0
- data/lib/temporalio/internal/worker/workflow_instance/externally_immutable_hash.rb +22 -0
- data/lib/temporalio/internal/worker/workflow_instance/handler_execution.rb +25 -0
- data/lib/temporalio/internal/worker/workflow_instance/handler_hash.rb +41 -0
- data/lib/temporalio/internal/worker/workflow_instance/illegal_call_tracer.rb +97 -0
- data/lib/temporalio/internal/worker/workflow_instance/inbound_implementation.rb +62 -0
- data/lib/temporalio/internal/worker/workflow_instance/outbound_implementation.rb +415 -0
- data/lib/temporalio/internal/worker/workflow_instance/replay_safe_logger.rb +37 -0
- data/lib/temporalio/internal/worker/workflow_instance/replay_safe_metric.rb +40 -0
- data/lib/temporalio/internal/worker/workflow_instance/scheduler.rb +163 -0
- data/lib/temporalio/internal/worker/workflow_instance.rb +730 -0
- data/lib/temporalio/internal/worker/workflow_worker.rb +236 -0
- data/lib/temporalio/internal.rb +7 -0
- data/lib/temporalio/metric.rb +109 -0
- data/lib/temporalio/retry_policy.rb +74 -0
- data/lib/temporalio/runtime.rb +314 -0
- data/lib/temporalio/scoped_logger.rb +96 -0
- data/lib/temporalio/search_attributes.rb +343 -0
- data/lib/temporalio/testing/activity_environment.rb +136 -0
- data/lib/temporalio/testing/workflow_environment.rb +383 -0
- data/lib/temporalio/testing.rb +10 -0
- data/lib/temporalio/version.rb +5 -0
- data/lib/temporalio/worker/activity_executor/fiber.rb +49 -0
- data/lib/temporalio/worker/activity_executor/thread_pool.rb +46 -0
- data/lib/temporalio/worker/activity_executor.rb +55 -0
- data/lib/temporalio/worker/interceptor.rb +362 -0
- data/lib/temporalio/worker/thread_pool.rb +237 -0
- data/lib/temporalio/worker/tuner.rb +189 -0
- data/lib/temporalio/worker/workflow_executor/thread_pool.rb +230 -0
- data/lib/temporalio/worker/workflow_executor.rb +26 -0
- data/lib/temporalio/worker/workflow_replayer.rb +343 -0
- data/lib/temporalio/worker.rb +569 -0
- data/lib/temporalio/workflow/activity_cancellation_type.rb +20 -0
- data/lib/temporalio/workflow/child_workflow_cancellation_type.rb +21 -0
- data/lib/temporalio/workflow/child_workflow_handle.rb +43 -0
- data/lib/temporalio/workflow/definition.rb +566 -0
- data/lib/temporalio/workflow/external_workflow_handle.rb +41 -0
- data/lib/temporalio/workflow/future.rb +151 -0
- data/lib/temporalio/workflow/handler_unfinished_policy.rb +13 -0
- data/lib/temporalio/workflow/info.rb +82 -0
- data/lib/temporalio/workflow/parent_close_policy.rb +19 -0
- data/lib/temporalio/workflow/update_info.rb +20 -0
- data/lib/temporalio/workflow.rb +529 -0
- data/lib/temporalio/workflow_history.rb +47 -0
- data/lib/temporalio.rb +11 -0
- data/temporalio.gemspec +28 -0
- metadata +238 -0
@@ -0,0 +1,343 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'temporalio/api'
|
4
|
+
require 'temporalio/converters'
|
5
|
+
require 'temporalio/internal/bridge'
|
6
|
+
require 'temporalio/internal/bridge/worker'
|
7
|
+
require 'temporalio/internal/worker/multi_runner'
|
8
|
+
require 'temporalio/internal/worker/workflow_worker'
|
9
|
+
require 'temporalio/worker/interceptor'
|
10
|
+
require 'temporalio/worker/thread_pool'
|
11
|
+
require 'temporalio/worker/tuner'
|
12
|
+
require 'temporalio/worker/workflow_executor'
|
13
|
+
require 'temporalio/workflow'
|
14
|
+
require 'temporalio/workflow_history'
|
15
|
+
|
16
|
+
module Temporalio
|
17
|
+
class Worker
|
18
|
+
# Replayer to replay workflows from existing history.
|
19
|
+
class WorkflowReplayer
|
20
|
+
Options = Data.define(
|
21
|
+
:workflows,
|
22
|
+
:namespace,
|
23
|
+
:task_queue,
|
24
|
+
:data_converter,
|
25
|
+
:workflow_executor,
|
26
|
+
:interceptors,
|
27
|
+
:build_id,
|
28
|
+
:identity,
|
29
|
+
:logger,
|
30
|
+
:illegal_workflow_calls,
|
31
|
+
:workflow_failure_exception_types,
|
32
|
+
:workflow_payload_codec_thread_pool,
|
33
|
+
:debug_mode,
|
34
|
+
:runtime
|
35
|
+
)
|
36
|
+
|
37
|
+
# Options as returned from {options} representing the options passed to the constructor.
|
38
|
+
class Options; end # rubocop:disable Lint/EmptyClass
|
39
|
+
|
40
|
+
# @return [Options] Options for this replayer which has the same attributes as {initialize}.
|
41
|
+
attr_reader :options
|
42
|
+
|
43
|
+
# Create a new replayer. This combines some options from both {Worker.initialize} and {Client.initialize}.
|
44
|
+
#
|
45
|
+
# @param workflows [Array<Class<Workflow::Definition>>] Workflows for this replayer.
|
46
|
+
# @param namespace [String] Namespace as set in the workflow info.
|
47
|
+
# @param task_queue [String] Task queue as set in the workflow info.
|
48
|
+
# @param data_converter [Converters::DataConverter] Data converter to use for all data conversions to/from
|
49
|
+
# payloads.
|
50
|
+
# @param workflow_executor [WorkflowExecutor] Workflow executor that workflow tasks run within. This must be a
|
51
|
+
# {WorkflowExecutor::ThreadPool} currently.
|
52
|
+
# @param interceptors [Array<Interceptor::Workflow>] Workflow interceptors.
|
53
|
+
# @param build_id [String] Unique identifier for the current runtime. This is best set as a unique value
|
54
|
+
# representing all code and should change only when code does. This can be something like a git commit hash. If
|
55
|
+
# unset, default is hash of known Ruby code.
|
56
|
+
# @param identity [String, nil] Override the identity for this replater.
|
57
|
+
# @param logger [Logger] Logger to use. Defaults to stdout with warn level. Callers setting this logger are
|
58
|
+
# responsible for closing it.
|
59
|
+
# @param illegal_workflow_calls [Hash<String, [:all, Array<Symbol>]>] Set of illegal workflow calls that are
|
60
|
+
# considered unsafe/non-deterministic and will raise if seen. The key of the hash is the fully qualified string
|
61
|
+
# class name (no leading `::`). The value is either `:all` which means any use of the class, or an array of
|
62
|
+
# symbols for methods on the class that cannot be used. The methods refer to either instance or class methods,
|
63
|
+
# there is no way to differentiate at this time.
|
64
|
+
# @param workflow_failure_exception_types [Array<Class<Exception>>] Workflow failure exception types. This is the
|
65
|
+
# set of exception types that, if a workflow-thrown exception extends, will cause the workflow/update to fail
|
66
|
+
# instead of suspending the workflow via task failure. These are applied in addition to the
|
67
|
+
# `workflow_failure_exception_type` on the workflow definition class itself. If {::Exception} is set, it
|
68
|
+
# effectively will fail a workflow/update in all user exception cases.
|
69
|
+
# @param workflow_payload_codec_thread_pool [ThreadPool, nil] Thread pool to run payload codec encode/decode
|
70
|
+
# within. This is required if a payload codec exists and the worker is not fiber based. Codecs can potentially
|
71
|
+
# block execution which is why they need to be run in the background.
|
72
|
+
# @param debug_mode [Boolean] If true, deadlock detection is disabled. Deadlock detection will fail workflow tasks
|
73
|
+
# if they block the thread for too long. This defaults to true if the `TEMPORAL_DEBUG` environment variable is
|
74
|
+
# `true` or `1`.
|
75
|
+
# @param runtime [Runtime] Runtime for this replayer.
|
76
|
+
#
|
77
|
+
# @yield If a block is present, this is the equivalent of calling {with_replay_worker} with the block and
|
78
|
+
# discarding the result.
|
79
|
+
def initialize(
|
80
|
+
workflows:,
|
81
|
+
namespace: 'ReplayNamespace',
|
82
|
+
task_queue: 'ReplayTaskQueue',
|
83
|
+
data_converter: Converters::DataConverter.default,
|
84
|
+
workflow_executor: WorkflowExecutor::ThreadPool.default,
|
85
|
+
interceptors: [],
|
86
|
+
build_id: Worker.default_build_id,
|
87
|
+
identity: nil,
|
88
|
+
logger: Logger.new($stdout, level: Logger::WARN),
|
89
|
+
illegal_workflow_calls: Worker.default_illegal_workflow_calls,
|
90
|
+
workflow_failure_exception_types: [],
|
91
|
+
workflow_payload_codec_thread_pool: nil,
|
92
|
+
debug_mode: %w[true 1].include?(ENV['TEMPORAL_DEBUG'].to_s.downcase),
|
93
|
+
runtime: Runtime.default,
|
94
|
+
&
|
95
|
+
)
|
96
|
+
@options = Options.new(
|
97
|
+
workflows:,
|
98
|
+
namespace:,
|
99
|
+
task_queue:,
|
100
|
+
data_converter:,
|
101
|
+
workflow_executor:,
|
102
|
+
interceptors:,
|
103
|
+
build_id:,
|
104
|
+
identity:,
|
105
|
+
logger:,
|
106
|
+
illegal_workflow_calls:,
|
107
|
+
workflow_failure_exception_types:,
|
108
|
+
workflow_payload_codec_thread_pool:,
|
109
|
+
debug_mode:,
|
110
|
+
runtime:
|
111
|
+
).freeze
|
112
|
+
# Preload definitions and other settings
|
113
|
+
@workflow_definitions = Internal::Worker::WorkflowWorker.workflow_definitions(workflows)
|
114
|
+
@nondeterminism_as_workflow_fail, @nondeterminism_as_workflow_fail_for_types =
|
115
|
+
Internal::Worker::WorkflowWorker.bridge_workflow_failure_exception_type_options(
|
116
|
+
workflow_failure_exception_types:, workflow_definitions: @workflow_definitions
|
117
|
+
)
|
118
|
+
# If there is a block, we'll go ahead and assume it's for with_replay_worker
|
119
|
+
with_replay_worker(&) if block_given? # steep:ignore
|
120
|
+
end
|
121
|
+
|
122
|
+
# Replay a workflow history.
|
123
|
+
#
|
124
|
+
# If doing multiple histories, it is better to use {replay_workflows} or {with_replay_worker} since they create
|
125
|
+
# a replay worker just once instead of each time like this call does.
|
126
|
+
#
|
127
|
+
# @param history [WorkflowHistory] History to replay.
|
128
|
+
# @param raise_on_replay_failure [Boolean] If true, the default, this will raise an exception on any replay
|
129
|
+
# failure. If false and the replay fails, the failure will be available in {ReplayResult.replay_failure}.
|
130
|
+
#
|
131
|
+
# @return [ReplayResult] Result of the replay.
|
132
|
+
def replay_workflow(history, raise_on_replay_failure: true)
|
133
|
+
with_replay_worker { |worker| worker.replay_workflow(history, raise_on_replay_failure:) }
|
134
|
+
end
|
135
|
+
|
136
|
+
# Replay multiple workflow histories.
|
137
|
+
#
|
138
|
+
# @param histories [Enumerable<WorkflowHistory>] Histories to replay.
|
139
|
+
# @param raise_on_replay_failure [Boolean] If true, this will raise an exception on any replay failure. If false,
|
140
|
+
# the default, and the replay fails, the failure will be available in {ReplayResult.replay_failure}.
|
141
|
+
#
|
142
|
+
# @return [Array<ReplayResult>] Results of the replay.
|
143
|
+
def replay_workflows(histories, raise_on_replay_failure: false)
|
144
|
+
with_replay_worker do |worker|
|
145
|
+
histories.map { |h| worker.replay_workflow(h, raise_on_replay_failure:) }
|
146
|
+
end
|
147
|
+
end
|
148
|
+
|
149
|
+
# Run a block of code with a {ReplayWorker} to execute replays.
|
150
|
+
#
|
151
|
+
# @yield Block of code to run with a replay worker.
|
152
|
+
# @yieldparam [ReplayWorker] Worker to run replays on. Note, only one workflow can replay at a time.
|
153
|
+
# @yieldreturn [Object] Result of the block.
|
154
|
+
def with_replay_worker(&)
|
155
|
+
worker = ReplayWorker.new(
|
156
|
+
options:,
|
157
|
+
workflow_definitions: @workflow_definitions,
|
158
|
+
nondeterminism_as_workflow_fail: @nondeterminism_as_workflow_fail,
|
159
|
+
nondeterminism_as_workflow_fail_for_types: @nondeterminism_as_workflow_fail_for_types
|
160
|
+
)
|
161
|
+
begin
|
162
|
+
yield worker
|
163
|
+
ensure
|
164
|
+
worker._shutdown
|
165
|
+
end
|
166
|
+
end
|
167
|
+
|
168
|
+
# Result of a single workflow replay run.
|
169
|
+
class ReplayResult
|
170
|
+
# @return [WorkflowHistory] History originally passed in to the replayer.
|
171
|
+
attr_reader :history
|
172
|
+
|
173
|
+
# @return [Exception, nil] Failure during replay if any.
|
174
|
+
attr_reader :replay_failure
|
175
|
+
|
176
|
+
# @!visibility private
|
177
|
+
def initialize(history:, replay_failure:)
|
178
|
+
@history = history
|
179
|
+
@replay_failure = replay_failure
|
180
|
+
end
|
181
|
+
end
|
182
|
+
|
183
|
+
# Replay worker that can be used to replay individual workflow runs. Only one call to {replay_workflow} can be
|
184
|
+
# made at a time.
|
185
|
+
class ReplayWorker
|
186
|
+
# @!visibility private
|
187
|
+
def initialize(
|
188
|
+
options:,
|
189
|
+
workflow_definitions:,
|
190
|
+
nondeterminism_as_workflow_fail:,
|
191
|
+
nondeterminism_as_workflow_fail_for_types:
|
192
|
+
)
|
193
|
+
# Create the bridge worker and the replayer
|
194
|
+
@bridge_replayer, @bridge_worker = Internal::Bridge::Worker::WorkflowReplayer.new(
|
195
|
+
options.runtime._core_runtime,
|
196
|
+
Internal::Bridge::Worker::Options.new(
|
197
|
+
activity: false,
|
198
|
+
workflow: true,
|
199
|
+
namespace: options.namespace,
|
200
|
+
task_queue: options.task_queue,
|
201
|
+
tuner: Tuner.create_fixed(
|
202
|
+
workflow_slots: 2, activity_slots: 1, local_activity_slots: 1
|
203
|
+
)._to_bridge_options,
|
204
|
+
build_id: options.build_id,
|
205
|
+
identity_override: options.identity,
|
206
|
+
max_cached_workflows: 2,
|
207
|
+
max_concurrent_workflow_task_polls: 1,
|
208
|
+
nonsticky_to_sticky_poll_ratio: 1.0,
|
209
|
+
max_concurrent_activity_task_polls: 1,
|
210
|
+
no_remote_activities: true,
|
211
|
+
sticky_queue_schedule_to_start_timeout: 1.0,
|
212
|
+
max_heartbeat_throttle_interval: 1.0,
|
213
|
+
default_heartbeat_throttle_interval: 1.0,
|
214
|
+
max_worker_activities_per_second: nil,
|
215
|
+
max_task_queue_activities_per_second: nil,
|
216
|
+
graceful_shutdown_period: 0.0,
|
217
|
+
use_worker_versioning: false,
|
218
|
+
nondeterminism_as_workflow_fail:,
|
219
|
+
nondeterminism_as_workflow_fail_for_types:
|
220
|
+
)
|
221
|
+
)
|
222
|
+
|
223
|
+
# Create the workflow worker
|
224
|
+
@workflow_worker = Internal::Worker::WorkflowWorker.new(
|
225
|
+
bridge_worker: @bridge_worker,
|
226
|
+
namespace: options.namespace,
|
227
|
+
task_queue: options.task_queue,
|
228
|
+
workflow_definitions:,
|
229
|
+
workflow_executor: options.workflow_executor,
|
230
|
+
logger: options.logger,
|
231
|
+
data_converter: options.data_converter,
|
232
|
+
metric_meter: options.runtime.metric_meter,
|
233
|
+
workflow_interceptors: options.interceptors.select do |i|
|
234
|
+
i.is_a?(Interceptor::Workflow)
|
235
|
+
end,
|
236
|
+
disable_eager_activity_execution: false,
|
237
|
+
illegal_workflow_calls: options.illegal_workflow_calls,
|
238
|
+
workflow_failure_exception_types: options.workflow_failure_exception_types,
|
239
|
+
workflow_payload_codec_thread_pool: options.workflow_payload_codec_thread_pool,
|
240
|
+
debug_mode: options.debug_mode,
|
241
|
+
on_eviction: proc { |_, remove_job| @last_workflow_remove_job = remove_job } # steep:ignore
|
242
|
+
)
|
243
|
+
|
244
|
+
# Create the runner
|
245
|
+
@runner = Internal::Worker::MultiRunner.new(workers: [self], shutdown_signals: [])
|
246
|
+
end
|
247
|
+
|
248
|
+
# Replay a workflow history.
|
249
|
+
#
|
250
|
+
# @param history [WorkflowHistory] History to replay.
|
251
|
+
# @param raise_on_replay_failure [Boolean] If true, the default, this will raise an exception on any replay
|
252
|
+
# failure. If false and the replay fails, the failure will be available in {ReplayResult.replay_failure}.
|
253
|
+
#
|
254
|
+
# @return [ReplayResult] Result of the replay.
|
255
|
+
def replay_workflow(history, raise_on_replay_failure: true)
|
256
|
+
raise ArgumentError, 'Expected history as WorkflowHistory' unless history.is_a?(WorkflowHistory)
|
257
|
+
# Due to our event processing model, only one can run at a time
|
258
|
+
raise 'Already running' if @running
|
259
|
+
raise 'Replayer shutdown' if @shutdown
|
260
|
+
|
261
|
+
# Push history proto
|
262
|
+
# TODO(cretz): Unset this
|
263
|
+
@running = true
|
264
|
+
@last_workflow_remove_job = nil
|
265
|
+
begin
|
266
|
+
@bridge_replayer.push_history(
|
267
|
+
history.workflow_id, Api::History::V1::History.new(events: history.events).to_proto
|
268
|
+
)
|
269
|
+
|
270
|
+
# Process events until workflow complete
|
271
|
+
until @last_workflow_remove_job
|
272
|
+
event = @runner.next_event
|
273
|
+
case event
|
274
|
+
when Internal::Worker::MultiRunner::Event::PollSuccess
|
275
|
+
@workflow_worker.handle_activation(
|
276
|
+
runner: @runner,
|
277
|
+
activation: Internal::Bridge::Api::WorkflowActivation::WorkflowActivation.decode(event.bytes),
|
278
|
+
decoded: false
|
279
|
+
)
|
280
|
+
when Internal::Worker::MultiRunner::Event::WorkflowActivationDecoded
|
281
|
+
@workflow_worker.handle_activation(runner: @runner, activation: event.activation, decoded: true)
|
282
|
+
when Internal::Worker::MultiRunner::Event::WorkflowActivationComplete
|
283
|
+
@workflow_worker.handle_activation_complete(
|
284
|
+
runner: @runner,
|
285
|
+
activation_completion: event.activation_completion,
|
286
|
+
encoded: event.encoded,
|
287
|
+
completion_complete_queue: event.completion_complete_queue
|
288
|
+
)
|
289
|
+
when Internal::Worker::MultiRunner::Event::WorkflowActivationCompletionComplete
|
290
|
+
# Ignore
|
291
|
+
else
|
292
|
+
raise "Unexpected event: #{event}"
|
293
|
+
end
|
294
|
+
end
|
295
|
+
|
296
|
+
# Create exception if removal is due to error
|
297
|
+
err = if @last_workflow_remove_job.reason == :NONDETERMINISM
|
298
|
+
Workflow::NondeterminismError.new(
|
299
|
+
"#{@last_workflow_remove_job.reason}: #{@last_workflow_remove_job.message}"
|
300
|
+
)
|
301
|
+
elsif !%i[CACHE_FULL LANG_REQUESTED].include?(@last_workflow_remove_job.reason)
|
302
|
+
Workflow::InvalidWorkflowStateError.new(
|
303
|
+
"#{@last_workflow_remove_job.reason}: #{@last_workflow_remove_job.message}"
|
304
|
+
)
|
305
|
+
end
|
306
|
+
# Raise if wanting to raise, otherwise return result
|
307
|
+
raise err if raise_on_replay_failure && err
|
308
|
+
|
309
|
+
ReplayResult.new(history:, replay_failure: err)
|
310
|
+
ensure
|
311
|
+
@running = false
|
312
|
+
end
|
313
|
+
end
|
314
|
+
|
315
|
+
# @!visibility private
|
316
|
+
def _shutdown
|
317
|
+
@shutdown = true
|
318
|
+
@runner.initiate_shutdown
|
319
|
+
# Wait for all-pollers-shutdown before finalizing
|
320
|
+
until @runner.next_event.is_a?(Internal::Worker::MultiRunner::Event::AllPollersShutDown); end
|
321
|
+
@runner.wait_complete_and_finalize_shutdown
|
322
|
+
@workflow_worker.on_shutdown_complete
|
323
|
+
@workflow_worker = nil
|
324
|
+
end
|
325
|
+
|
326
|
+
# @!visibility private
|
327
|
+
def _bridge_worker
|
328
|
+
@bridge_worker
|
329
|
+
end
|
330
|
+
|
331
|
+
# @!visibility private
|
332
|
+
def _initiate_shutdown
|
333
|
+
_bridge_worker.initiate_shutdown
|
334
|
+
end
|
335
|
+
|
336
|
+
# @!visibility private
|
337
|
+
def _wait_all_complete
|
338
|
+
# Do nothing
|
339
|
+
end
|
340
|
+
end
|
341
|
+
end
|
342
|
+
end
|
343
|
+
end
|