@temporalio/core-bridge 1.8.6 → 1.9.0
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.
- package/Cargo.lock +670 -594
- package/Cargo.toml +2 -1
- package/lib/errors.js +6 -6
- package/lib/errors.js.map +1 -1
- package/lib/index.d.ts +17 -44
- package/lib/index.js.map +1 -1
- package/package.json +5 -6
- package/releases/aarch64-apple-darwin/index.node +0 -0
- package/releases/aarch64-unknown-linux-gnu/index.node +0 -0
- package/releases/x86_64-apple-darwin/index.node +0 -0
- package/releases/x86_64-pc-windows-msvc/index.node +0 -0
- package/releases/x86_64-unknown-linux-gnu/index.node +0 -0
- package/sdk-core/.github/workflows/heavy.yml +4 -0
- package/sdk-core/.github/workflows/per-pr.yml +96 -0
- package/sdk-core/ARCHITECTURE.md +1 -1
- package/sdk-core/Cargo.toml +10 -0
- package/sdk-core/LICENSE.txt +0 -2
- package/sdk-core/README.md +37 -21
- package/sdk-core/client/Cargo.toml +7 -4
- package/sdk-core/client/src/lib.rs +274 -142
- package/sdk-core/client/src/metrics.rs +68 -57
- package/sdk-core/client/src/raw.rs +191 -45
- package/sdk-core/client/src/retry.rs +20 -0
- package/sdk-core/client/src/worker_registry/mod.rs +264 -0
- package/sdk-core/client/src/workflow_handle/mod.rs +2 -1
- package/sdk-core/core/Cargo.toml +17 -19
- package/sdk-core/core/src/core_tests/activity_tasks.rs +4 -2
- package/sdk-core/core/src/core_tests/child_workflows.rs +7 -7
- package/sdk-core/core/src/core_tests/mod.rs +1 -0
- package/sdk-core/core/src/core_tests/queries.rs +42 -1
- package/sdk-core/core/src/core_tests/replay_flag.rs +29 -39
- package/sdk-core/core/src/core_tests/updates.rs +73 -0
- package/sdk-core/core/src/core_tests/workflow_tasks.rs +52 -1
- package/sdk-core/core/src/ephemeral_server/mod.rs +34 -11
- package/sdk-core/core/src/internal_flags.rs +7 -1
- package/sdk-core/core/src/lib.rs +19 -36
- package/sdk-core/core/src/protosext/mod.rs +12 -4
- package/sdk-core/core/src/protosext/protocol_messages.rs +102 -0
- package/sdk-core/core/src/replay/mod.rs +99 -48
- package/sdk-core/core/src/telemetry/log_export.rs +161 -28
- package/sdk-core/core/src/telemetry/metrics.rs +869 -248
- package/sdk-core/core/src/telemetry/mod.rs +153 -257
- package/sdk-core/core/src/telemetry/prometheus_server.rs +36 -31
- package/sdk-core/core/src/test_help/mod.rs +64 -5
- package/sdk-core/core/src/worker/activities/activity_heartbeat_manager.rs +12 -2
- package/sdk-core/core/src/worker/activities.rs +276 -10
- package/sdk-core/core/src/worker/client/mocks.rs +18 -0
- package/sdk-core/core/src/worker/client.rs +16 -3
- package/sdk-core/core/src/worker/mod.rs +45 -28
- package/sdk-core/core/src/worker/slot_provider.rs +175 -0
- package/sdk-core/core/src/worker/workflow/driven_workflow.rs +27 -34
- package/sdk-core/core/src/worker/workflow/history_update.rs +5 -2
- package/sdk-core/core/src/worker/workflow/machines/activity_state_machine.rs +71 -95
- package/sdk-core/core/src/worker/workflow/machines/cancel_external_state_machine.rs +34 -22
- package/sdk-core/core/src/worker/workflow/machines/cancel_workflow_state_machine.rs +50 -34
- package/sdk-core/core/src/worker/workflow/machines/child_workflow_state_machine.rs +106 -92
- package/sdk-core/core/src/worker/workflow/machines/continue_as_new_workflow_state_machine.rs +22 -21
- package/sdk-core/core/src/worker/workflow/machines/local_activity_state_machine.rs +386 -499
- package/sdk-core/core/src/worker/workflow/machines/mod.rs +12 -2
- package/sdk-core/core/src/worker/workflow/machines/modify_workflow_properties_state_machine.rs +33 -26
- package/sdk-core/core/src/worker/workflow/machines/patch_state_machine.rs +198 -215
- package/sdk-core/core/src/worker/workflow/machines/signal_external_state_machine.rs +67 -63
- package/sdk-core/core/src/worker/workflow/machines/timer_state_machine.rs +88 -119
- package/sdk-core/core/src/worker/workflow/machines/transition_coverage.rs +3 -1
- package/sdk-core/core/src/worker/workflow/machines/update_state_machine.rs +411 -0
- package/sdk-core/core/src/worker/workflow/machines/upsert_search_attributes_state_machine.rs +27 -26
- package/sdk-core/core/src/worker/workflow/machines/workflow_machines.rs +319 -94
- package/sdk-core/core/src/worker/workflow/managed_run.rs +179 -132
- package/sdk-core/core/src/worker/workflow/mod.rs +129 -58
- package/sdk-core/core/src/worker/workflow/run_cache.rs +16 -26
- package/sdk-core/core/src/worker/workflow/workflow_stream/saved_wf_inputs.rs +2 -2
- package/sdk-core/core/src/worker/workflow/workflow_stream.rs +48 -43
- package/sdk-core/core-api/Cargo.toml +8 -7
- package/sdk-core/core-api/src/lib.rs +4 -12
- package/sdk-core/core-api/src/telemetry/metrics.rs +334 -0
- package/sdk-core/core-api/src/telemetry.rs +53 -42
- package/sdk-core/core-api/src/worker.rs +7 -0
- package/sdk-core/{.buildkite/docker → docker}/docker-compose.yaml +1 -1
- package/sdk-core/etc/dynamic-config.yaml +11 -1
- package/sdk-core/fsm/LICENSE.txt +0 -2
- package/sdk-core/fsm/rustfsm_procmacro/Cargo.toml +1 -1
- package/sdk-core/fsm/rustfsm_procmacro/LICENSE.txt +0 -2
- package/sdk-core/fsm/rustfsm_procmacro/src/lib.rs +1 -3
- package/sdk-core/fsm/rustfsm_procmacro/tests/trybuild/no_handle_conversions_require_into_fail.stderr +2 -2
- package/sdk-core/fsm/rustfsm_trait/LICENSE.txt +0 -2
- package/sdk-core/sdk/Cargo.toml +2 -2
- package/sdk-core/sdk/src/lib.rs +85 -7
- package/sdk-core/sdk/src/workflow_context/options.rs +4 -0
- package/sdk-core/sdk/src/workflow_context.rs +43 -15
- package/sdk-core/sdk/src/workflow_future.rs +334 -204
- package/sdk-core/sdk-core-protos/Cargo.toml +3 -3
- package/sdk-core/sdk-core-protos/build.rs +14 -14
- package/sdk-core/sdk-core-protos/protos/api_upstream/.buildkite/Dockerfile +2 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/Makefile +99 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/api-linter.yaml +56 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/buf.gen.yaml +20 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/buf.lock +11 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/buf.yaml +18 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/api/annotations.proto +31 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/api/http.proto +379 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/protobuf/any.proto +162 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/protobuf/descriptor.proto +1212 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/protobuf/duration.proto +115 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/protobuf/empty.proto +51 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/protobuf/timestamp.proto +144 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/google/protobuf/wrappers.proto +123 -0
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/batch/v1/message.proto +12 -9
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/command/v1/message.proto +11 -13
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/common/v1/message.proto +33 -4
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/failed_cause.proto +2 -0
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/reset.proto +4 -4
- package/sdk-core/{protos/api_upstream/build/tools.go → sdk-core-protos/protos/api_upstream/temporal/api/export/v1/message.proto} +22 -6
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/filter/v1/message.proto +2 -4
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/history/v1/message.proto +21 -23
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/namespace/v1/message.proto +2 -4
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/operatorservice/v1/request_response.proto +2 -0
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/operatorservice/v1/service.proto +4 -0
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/replication/v1/message.proto +1 -3
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/schedule/v1/message.proto +36 -20
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/sdk/v1/task_complete_metadata.proto +13 -0
- package/sdk-core/sdk-core-protos/protos/api_upstream/temporal/api/sdk/v1/workflow_metadata.proto +66 -0
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/taskqueue/v1/message.proto +2 -4
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/update/v1/message.proto +1 -1
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/version/v1/message.proto +2 -3
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/workflow/v1/message.proto +24 -22
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/workflowservice/v1/request_response.proto +84 -32
- package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/workflowservice/v1/service.proto +205 -47
- package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/workflow_activation/workflow_activation.proto +57 -0
- package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/workflow_commands/workflow_commands.proto +27 -0
- package/sdk-core/sdk-core-protos/src/history_builder.rs +67 -2
- package/sdk-core/sdk-core-protos/src/history_info.rs +1 -1
- package/sdk-core/sdk-core-protos/src/lib.rs +76 -3
- package/sdk-core/sdk-core-protos/src/utilities.rs +14 -0
- package/sdk-core/test-utils/Cargo.toml +6 -1
- package/sdk-core/test-utils/src/canned_histories.rs +3 -57
- package/sdk-core/test-utils/src/interceptors.rs +46 -0
- package/sdk-core/test-utils/src/lib.rs +106 -38
- package/sdk-core/tests/integ_tests/metrics_tests.rs +110 -15
- package/sdk-core/tests/integ_tests/queries_tests.rs +174 -3
- package/sdk-core/tests/integ_tests/update_tests.rs +908 -0
- package/sdk-core/tests/integ_tests/visibility_tests.rs +4 -4
- package/sdk-core/tests/integ_tests/workflow_tests/activities.rs +44 -1
- package/sdk-core/tests/integ_tests/workflow_tests/cancel_external.rs +1 -1
- package/sdk-core/tests/integ_tests/workflow_tests/cancel_wf.rs +1 -1
- package/sdk-core/tests/integ_tests/workflow_tests/child_workflows.rs +4 -4
- package/sdk-core/tests/integ_tests/workflow_tests/eager.rs +61 -0
- package/sdk-core/tests/integ_tests/workflow_tests/replay.rs +27 -2
- package/sdk-core/tests/integ_tests/workflow_tests.rs +142 -3
- package/sdk-core/tests/main.rs +2 -1
- package/sdk-core/tests/runner.rs +15 -2
- package/src/conversions.rs +107 -96
- package/src/helpers.rs +74 -0
- package/src/runtime.rs +29 -15
- package/src/worker.rs +14 -61
- package/ts/index.ts +23 -54
- package/sdk-core/.buildkite/docker/Dockerfile +0 -9
- package/sdk-core/.buildkite/docker/build.sh +0 -5
- package/sdk-core/.buildkite/docker/docker-compose-ci.yaml +0 -27
- package/sdk-core/.buildkite/pipeline.yml +0 -57
- package/sdk-core/.github/workflows/semgrep.yml +0 -25
- package/sdk-core/client/LICENSE.txt +0 -23
- package/sdk-core/core/LICENSE.txt +0 -23
- package/sdk-core/core/src/worker/workflow/bridge.rs +0 -35
- package/sdk-core/core/src/worker/workflow/managed_run/managed_wf_test.rs +0 -215
- package/sdk-core/core-api/LICENSE.txt +0 -23
- package/sdk-core/protos/api_upstream/.buildkite/Dockerfile +0 -2
- package/sdk-core/protos/api_upstream/Makefile +0 -80
- package/sdk-core/protos/api_upstream/api-linter.yaml +0 -40
- package/sdk-core/protos/api_upstream/buf.yaml +0 -9
- package/sdk-core/protos/api_upstream/build/go.mod +0 -7
- package/sdk-core/protos/api_upstream/build/go.sum +0 -5
- package/sdk-core/protos/api_upstream/go.mod +0 -6
- package/sdk-core/protos/testsrv_upstream/dependencies/gogoproto/gogo.proto +0 -141
- package/sdk-core/sdk/LICENSE.txt +0 -23
- package/sdk-core/sdk-core-protos/LICENSE.txt +0 -23
- /package/sdk-core/{.buildkite/docker → docker}/docker-compose-telem.yaml +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/.buildkite/docker-compose.yml +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/.buildkite/pipeline.yml +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/.github/CODEOWNERS +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/.github/PULL_REQUEST_TEMPLATE.md +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/.github/workflows/publish-docs.yml +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/.github/workflows/trigger-api-go-update.yml +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/LICENSE +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/README.md +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/batch_operation.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/command_type.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/common.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/event_type.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/namespace.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/query.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/schedule.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/task_queue.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/update.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/enums/v1/workflow.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/errordetails/v1/message.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/failure/v1/message.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/protocol/v1/message.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/api_upstream/temporal/api/query/v1/message.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/google/rpc/status.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/grpc/health/v1/health.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/activity_result/activity_result.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/activity_task/activity_task.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/child_workflow/child_workflow.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/common/common.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/core_interface.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/external_data/external_data.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/local/temporal/sdk/core/workflow_completion/workflow_completion.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/testsrv_upstream/Makefile +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/testsrv_upstream/api-linter.yaml +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/testsrv_upstream/buf.yaml +0 -0
- /package/sdk-core/{protos/api_upstream → sdk-core-protos/protos/testsrv_upstream}/dependencies/gogoproto/gogo.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/testsrv_upstream/temporal/api/testservice/v1/request_response.proto +0 -0
- /package/sdk-core/{protos → sdk-core-protos/protos}/testsrv_upstream/temporal/api/testservice/v1/service.proto +0 -0
|
@@ -13,6 +13,7 @@ use crate::{
|
|
|
13
13
|
LocalActivityExecutionResult,
|
|
14
14
|
},
|
|
15
15
|
};
|
|
16
|
+
use itertools::Itertools;
|
|
16
17
|
use rustfsm::{fsm, MachineError, StateMachine, TransitionResult};
|
|
17
18
|
use std::{
|
|
18
19
|
convert::TryFrom,
|
|
@@ -30,7 +31,7 @@ use temporal_sdk_core_protos::{
|
|
|
30
31
|
workflow_commands::ActivityCancellationType,
|
|
31
32
|
},
|
|
32
33
|
temporal::api::{
|
|
33
|
-
command::v1::{
|
|
34
|
+
command::v1::{command, RecordMarkerCommandAttributes},
|
|
34
35
|
enums::v1::{CommandType, EventType, RetryState},
|
|
35
36
|
failure::v1::{failure::FailureInfo, Failure},
|
|
36
37
|
history::v1::HistoryEvent,
|
|
@@ -617,10 +618,8 @@ impl Cancellable for LocalActivityMachine {
|
|
|
617
618
|
let mach_resps = cmds
|
|
618
619
|
.into_iter()
|
|
619
620
|
.map(|mc| self.adapt_response(mc, None))
|
|
620
|
-
.
|
|
621
|
-
.
|
|
622
|
-
.flatten()
|
|
623
|
-
.collect();
|
|
621
|
+
.flatten_ok()
|
|
622
|
+
.try_collect()?;
|
|
624
623
|
Ok(mach_resps)
|
|
625
624
|
}
|
|
626
625
|
|
|
@@ -781,10 +780,9 @@ impl WFMachinesAdapter for LocalActivityMachine {
|
|
|
781
780
|
header: None,
|
|
782
781
|
failure: maybe_failure,
|
|
783
782
|
};
|
|
784
|
-
responses.push(MachineResponse::IssueNewCommand(
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
}));
|
|
783
|
+
responses.push(MachineResponse::IssueNewCommand(
|
|
784
|
+
command::Attributes::RecordMarkerCommandAttributes(marker_data).into(),
|
|
785
|
+
));
|
|
788
786
|
}
|
|
789
787
|
Ok(responses)
|
|
790
788
|
}
|
|
@@ -879,27 +877,40 @@ fn verify_marker_data_matches(
|
|
|
879
877
|
mod tests {
|
|
880
878
|
use super::*;
|
|
881
879
|
use crate::{
|
|
882
|
-
replay::TestHistoryBuilder,
|
|
880
|
+
replay::TestHistoryBuilder,
|
|
881
|
+
test_help::{build_fake_sdk, canned_histories, MockPollCfg, ResponseType},
|
|
883
882
|
};
|
|
883
|
+
use anyhow::anyhow;
|
|
884
884
|
use rstest::rstest;
|
|
885
|
-
use std::
|
|
885
|
+
use std::{
|
|
886
|
+
sync::atomic::{AtomicI64, Ordering},
|
|
887
|
+
time::Duration,
|
|
888
|
+
};
|
|
886
889
|
use temporal_sdk::{
|
|
887
|
-
|
|
890
|
+
ActContext, ActivityCancelledError, CancellableFuture, LocalActivityOptions, WfContext,
|
|
891
|
+
WorkflowResult,
|
|
888
892
|
};
|
|
889
893
|
use temporal_sdk_core_protos::{
|
|
890
894
|
coresdk::{
|
|
891
|
-
activity_result::ActivityExecutionResult,
|
|
892
895
|
workflow_activation::{workflow_activation_job, WorkflowActivationJob},
|
|
896
|
+
AsJsonPayloadExt,
|
|
893
897
|
},
|
|
894
898
|
temporal::api::{
|
|
895
|
-
|
|
899
|
+
common::v1::RetryPolicy, enums::v1::WorkflowTaskFailedCause, failure::v1::Failure,
|
|
896
900
|
},
|
|
897
|
-
DEFAULT_ACTIVITY_TYPE,
|
|
901
|
+
DEFAULT_ACTIVITY_TYPE, DEFAULT_WORKFLOW_TYPE,
|
|
898
902
|
};
|
|
903
|
+
use temporal_sdk_core_test_utils::interceptors::ActivationAssertionsInterceptor;
|
|
904
|
+
use tokio_util::sync::CancellationToken;
|
|
899
905
|
|
|
900
906
|
async fn la_wf(ctx: WfContext) -> WorkflowResult<()> {
|
|
901
907
|
ctx.local_activity(LocalActivityOptions {
|
|
902
908
|
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
909
|
+
input: ().as_json_payload().unwrap(),
|
|
910
|
+
retry_policy: RetryPolicy {
|
|
911
|
+
maximum_attempts: 1,
|
|
912
|
+
..Default::default()
|
|
913
|
+
},
|
|
903
914
|
..Default::default()
|
|
904
915
|
})
|
|
905
916
|
.await;
|
|
@@ -913,7 +924,6 @@ mod tests {
|
|
|
913
924
|
#[case::replay_fail(true, false)]
|
|
914
925
|
#[tokio::test]
|
|
915
926
|
async fn one_la_success(#[case] replay: bool, #[case] completes_ok: bool) {
|
|
916
|
-
let func = WorkflowFunction::new(la_wf);
|
|
917
927
|
let activity_id = "1";
|
|
918
928
|
let mut t = TestHistoryBuilder::default();
|
|
919
929
|
t.add_by_type(EventType::WorkflowExecutionStarted);
|
|
@@ -927,202 +937,95 @@ mod tests {
|
|
|
927
937
|
Failure::application_failure("I failed".to_string(), false),
|
|
928
938
|
);
|
|
929
939
|
}
|
|
930
|
-
t.
|
|
940
|
+
t.add_workflow_task_scheduled_and_started();
|
|
931
941
|
|
|
932
|
-
let
|
|
933
|
-
t
|
|
942
|
+
let mut mock_cfg = if replay {
|
|
943
|
+
MockPollCfg::from_resps(t, [ResponseType::AllHistory])
|
|
934
944
|
} else {
|
|
935
|
-
t
|
|
945
|
+
MockPollCfg::from_hist_builder(t)
|
|
936
946
|
};
|
|
937
|
-
|
|
938
|
-
|
|
939
|
-
|
|
940
|
-
|
|
941
|
-
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
commands[0].command_type,
|
|
975
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
976
|
-
);
|
|
977
|
-
} else {
|
|
978
|
-
assert_eq!(commands.len(), 2);
|
|
979
|
-
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
980
|
-
if completes_ok {
|
|
981
|
-
assert_matches!(
|
|
982
|
-
commands[0].attributes.as_ref().unwrap(),
|
|
983
|
-
command::Attributes::RecordMarkerCommandAttributes(
|
|
984
|
-
RecordMarkerCommandAttributes { failure: None, .. }
|
|
985
|
-
)
|
|
986
|
-
);
|
|
987
|
-
} else {
|
|
988
|
-
assert_matches!(
|
|
989
|
-
commands[0].attributes.as_ref().unwrap(),
|
|
990
|
-
command::Attributes::RecordMarkerCommandAttributes(
|
|
991
|
-
RecordMarkerCommandAttributes {
|
|
992
|
-
failure: Some(_),
|
|
993
|
-
..
|
|
994
|
-
}
|
|
995
|
-
)
|
|
996
|
-
);
|
|
997
|
-
}
|
|
998
|
-
assert_eq!(
|
|
999
|
-
commands[1].command_type,
|
|
1000
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1001
|
-
);
|
|
1002
|
-
}
|
|
1003
|
-
|
|
1004
|
-
if !replay {
|
|
1005
|
-
wfm.new_history(t.get_full_history_info().unwrap().into())
|
|
1006
|
-
.await
|
|
1007
|
-
.unwrap();
|
|
1008
|
-
}
|
|
1009
|
-
assert_eq!(wfm.drain_queued_local_activities().len(), 0);
|
|
1010
|
-
assert_eq!(wfm.get_next_activation().await.unwrap().jobs.len(), 0);
|
|
1011
|
-
let commands = wfm.get_server_commands().commands;
|
|
1012
|
-
assert_eq!(commands.len(), 0);
|
|
947
|
+
mock_cfg.completion_asserts_from_expectations(|mut asserts| {
|
|
948
|
+
asserts.then(move |wft| {
|
|
949
|
+
let commands = &wft.commands;
|
|
950
|
+
if !replay {
|
|
951
|
+
assert_eq!(commands.len(), 2);
|
|
952
|
+
assert_eq!(commands[0].command_type(), CommandType::RecordMarker);
|
|
953
|
+
if completes_ok {
|
|
954
|
+
assert_matches!(
|
|
955
|
+
commands[0].attributes.as_ref().unwrap(),
|
|
956
|
+
command::Attributes::RecordMarkerCommandAttributes(
|
|
957
|
+
RecordMarkerCommandAttributes { failure: None, .. }
|
|
958
|
+
)
|
|
959
|
+
);
|
|
960
|
+
} else {
|
|
961
|
+
assert_matches!(
|
|
962
|
+
commands[0].attributes.as_ref().unwrap(),
|
|
963
|
+
command::Attributes::RecordMarkerCommandAttributes(
|
|
964
|
+
RecordMarkerCommandAttributes {
|
|
965
|
+
failure: Some(_),
|
|
966
|
+
..
|
|
967
|
+
}
|
|
968
|
+
)
|
|
969
|
+
);
|
|
970
|
+
}
|
|
971
|
+
assert_eq!(
|
|
972
|
+
commands[1].command_type(),
|
|
973
|
+
CommandType::CompleteWorkflowExecution
|
|
974
|
+
);
|
|
975
|
+
} else {
|
|
976
|
+
assert_eq!(commands.len(), 1);
|
|
977
|
+
assert_matches!(
|
|
978
|
+
commands[0].command_type(),
|
|
979
|
+
CommandType::CompleteWorkflowExecution
|
|
980
|
+
);
|
|
981
|
+
}
|
|
982
|
+
});
|
|
983
|
+
});
|
|
1013
984
|
|
|
1014
|
-
|
|
985
|
+
let mut worker = build_fake_sdk(mock_cfg);
|
|
986
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, la_wf);
|
|
987
|
+
worker.register_activity(
|
|
988
|
+
DEFAULT_ACTIVITY_TYPE,
|
|
989
|
+
move |_ctx: ActContext, _: ()| async move {
|
|
990
|
+
if replay {
|
|
991
|
+
panic!("Should not be invoked on replay");
|
|
992
|
+
}
|
|
993
|
+
if completes_ok {
|
|
994
|
+
Ok("hi")
|
|
995
|
+
} else {
|
|
996
|
+
Err(anyhow!("Oh no I failed!"))
|
|
997
|
+
}
|
|
998
|
+
},
|
|
999
|
+
);
|
|
1000
|
+
worker.run().await.unwrap();
|
|
1015
1001
|
}
|
|
1016
1002
|
|
|
1017
1003
|
async fn two_la_wf(ctx: WfContext) -> WorkflowResult<()> {
|
|
1018
1004
|
ctx.local_activity(LocalActivityOptions {
|
|
1019
1005
|
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1006
|
+
input: ().as_json_payload().unwrap(),
|
|
1020
1007
|
..Default::default()
|
|
1021
1008
|
})
|
|
1022
1009
|
.await;
|
|
1023
1010
|
ctx.local_activity(LocalActivityOptions {
|
|
1024
1011
|
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1012
|
+
input: ().as_json_payload().unwrap(),
|
|
1025
1013
|
..Default::default()
|
|
1026
1014
|
})
|
|
1027
1015
|
.await;
|
|
1028
1016
|
Ok(().into())
|
|
1029
1017
|
}
|
|
1030
1018
|
|
|
1031
|
-
#[rstest]
|
|
1032
|
-
#[case::incremental(false)]
|
|
1033
|
-
#[case::replay(true)]
|
|
1034
|
-
#[tokio::test]
|
|
1035
|
-
async fn two_sequential_las(#[case] replay: bool) {
|
|
1036
|
-
let func = WorkflowFunction::new(two_la_wf);
|
|
1037
|
-
let t = canned_histories::two_local_activities_one_wft(false);
|
|
1038
|
-
let histinfo = if replay {
|
|
1039
|
-
t.get_full_history_info().unwrap().into()
|
|
1040
|
-
} else {
|
|
1041
|
-
t.get_history_info(1).unwrap().into()
|
|
1042
|
-
};
|
|
1043
|
-
let mut wfm = ManagedWFFunc::new_from_update(histinfo, func, vec![]);
|
|
1044
|
-
|
|
1045
|
-
// First activation will have no server commands. Activity will be put into the activity
|
|
1046
|
-
// queue locally
|
|
1047
|
-
let act = wfm.get_next_activation().await.unwrap();
|
|
1048
|
-
let first_act_ts = act.timestamp.unwrap();
|
|
1049
|
-
let commands = wfm.get_server_commands().commands;
|
|
1050
|
-
assert_eq!(commands.len(), 0);
|
|
1051
|
-
let ready_to_execute_las = wfm.drain_queued_local_activities();
|
|
1052
|
-
let num_queued = usize::from(!replay);
|
|
1053
|
-
assert_eq!(ready_to_execute_las.len(), num_queued);
|
|
1054
|
-
|
|
1055
|
-
if !replay {
|
|
1056
|
-
wfm.complete_local_activity(1, ActivityExecutionResult::ok(b"Resolved".into()))
|
|
1057
|
-
.unwrap();
|
|
1058
|
-
}
|
|
1059
|
-
|
|
1060
|
-
let act = wfm.get_next_activation().await.unwrap();
|
|
1061
|
-
// Verify LAs advance time (they take 1s in this test)
|
|
1062
|
-
assert_eq!(act.timestamp.unwrap().seconds, first_act_ts.seconds + 1);
|
|
1063
|
-
assert_matches!(
|
|
1064
|
-
act.jobs.as_slice(),
|
|
1065
|
-
[WorkflowActivationJob {
|
|
1066
|
-
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra))
|
|
1067
|
-
}] => assert_eq!(ra.seq, 1)
|
|
1068
|
-
);
|
|
1069
|
-
let ready_to_execute_las = wfm.drain_queued_local_activities();
|
|
1070
|
-
if !replay {
|
|
1071
|
-
assert_eq!(ready_to_execute_las.len(), 1);
|
|
1072
|
-
} else {
|
|
1073
|
-
assert_eq!(ready_to_execute_las.len(), 0);
|
|
1074
|
-
}
|
|
1075
|
-
|
|
1076
|
-
if !replay {
|
|
1077
|
-
wfm.complete_local_activity(2, ActivityExecutionResult::ok(b"Resolved".into()))
|
|
1078
|
-
.unwrap();
|
|
1079
|
-
}
|
|
1080
|
-
|
|
1081
|
-
let act = wfm.get_next_activation().await.unwrap();
|
|
1082
|
-
assert_eq!(act.timestamp.unwrap().seconds, first_act_ts.seconds + 2);
|
|
1083
|
-
assert_matches!(
|
|
1084
|
-
act.jobs.as_slice(),
|
|
1085
|
-
[WorkflowActivationJob {
|
|
1086
|
-
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra))
|
|
1087
|
-
}] => assert_eq!(ra.seq, 2)
|
|
1088
|
-
);
|
|
1089
|
-
let commands = wfm.get_server_commands().commands;
|
|
1090
|
-
if replay {
|
|
1091
|
-
assert_eq!(commands.len(), 1);
|
|
1092
|
-
assert_eq!(
|
|
1093
|
-
commands[0].command_type,
|
|
1094
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1095
|
-
);
|
|
1096
|
-
} else {
|
|
1097
|
-
assert_eq!(commands.len(), 3);
|
|
1098
|
-
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1099
|
-
assert_eq!(commands[1].command_type, CommandType::RecordMarker as i32);
|
|
1100
|
-
assert_eq!(
|
|
1101
|
-
commands[2].command_type,
|
|
1102
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1103
|
-
);
|
|
1104
|
-
}
|
|
1105
|
-
|
|
1106
|
-
if !replay {
|
|
1107
|
-
wfm.new_history(t.get_full_history_info().unwrap().into())
|
|
1108
|
-
.await
|
|
1109
|
-
.unwrap();
|
|
1110
|
-
}
|
|
1111
|
-
assert_eq!(wfm.get_next_activation().await.unwrap().jobs.len(), 0);
|
|
1112
|
-
let commands = wfm.get_server_commands().commands;
|
|
1113
|
-
assert_eq!(commands.len(), 0);
|
|
1114
|
-
|
|
1115
|
-
wfm.shutdown().await.unwrap();
|
|
1116
|
-
}
|
|
1117
|
-
|
|
1118
1019
|
async fn two_la_wf_parallel(ctx: WfContext) -> WorkflowResult<()> {
|
|
1119
1020
|
tokio::join!(
|
|
1120
1021
|
ctx.local_activity(LocalActivityOptions {
|
|
1121
1022
|
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1023
|
+
input: ().as_json_payload().unwrap(),
|
|
1122
1024
|
..Default::default()
|
|
1123
1025
|
}),
|
|
1124
1026
|
ctx.local_activity(LocalActivityOptions {
|
|
1125
1027
|
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1028
|
+
input: ().as_json_payload().unwrap(),
|
|
1126
1029
|
..Default::default()
|
|
1127
1030
|
})
|
|
1128
1031
|
);
|
|
@@ -1130,91 +1033,112 @@ mod tests {
|
|
|
1130
1033
|
}
|
|
1131
1034
|
|
|
1132
1035
|
#[rstest]
|
|
1133
|
-
#[case::incremental(false)]
|
|
1134
|
-
#[case::replay(true)]
|
|
1135
1036
|
#[tokio::test]
|
|
1136
|
-
async fn
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1037
|
+
async fn two_sequential_las(
|
|
1038
|
+
#[values(true, false)] replay: bool,
|
|
1039
|
+
#[values(true, false)] parallel: bool,
|
|
1040
|
+
) {
|
|
1041
|
+
let t = canned_histories::two_local_activities_one_wft(parallel);
|
|
1042
|
+
let mut mock_cfg = if replay {
|
|
1043
|
+
MockPollCfg::from_resps(t, [ResponseType::AllHistory])
|
|
1141
1044
|
} else {
|
|
1142
|
-
t
|
|
1045
|
+
MockPollCfg::from_hist_builder(t)
|
|
1143
1046
|
};
|
|
1144
|
-
let mut wfm = ManagedWFFunc::new_from_update(histinfo, func, vec![]);
|
|
1145
|
-
|
|
1146
|
-
// First activation will have no server commands. Activity(ies) will be put into the queue
|
|
1147
|
-
// for execution
|
|
1148
|
-
let act = wfm.get_next_activation().await.unwrap();
|
|
1149
|
-
let first_act_ts = act.timestamp.unwrap();
|
|
1150
|
-
let commands = wfm.get_server_commands().commands;
|
|
1151
|
-
assert_eq!(commands.len(), 0);
|
|
1152
|
-
let ready_to_execute_las = wfm.drain_queued_local_activities();
|
|
1153
|
-
let num_queued = if !replay { 2 } else { 0 };
|
|
1154
|
-
assert_eq!(ready_to_execute_las.len(), num_queued);
|
|
1155
1047
|
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1048
|
+
let mut aai = ActivationAssertionsInterceptor::default();
|
|
1049
|
+
let first_act_ts_seconds: &'static _ = Box::leak(Box::new(AtomicI64::new(-1)));
|
|
1050
|
+
aai.then(|a| {
|
|
1051
|
+
first_act_ts_seconds.store(a.timestamp.as_ref().unwrap().seconds, Ordering::Relaxed)
|
|
1052
|
+
});
|
|
1053
|
+
// Verify LAs advance time (they take 1s as defined in the canned history)
|
|
1054
|
+
aai.then(move |a| {
|
|
1055
|
+
if !parallel {
|
|
1056
|
+
assert_matches!(
|
|
1057
|
+
a.jobs.as_slice(),
|
|
1058
|
+
[WorkflowActivationJob {
|
|
1059
|
+
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra))
|
|
1060
|
+
}] => assert_eq!(ra.seq, 1)
|
|
1061
|
+
);
|
|
1062
|
+
} else {
|
|
1063
|
+
assert_matches!(
|
|
1064
|
+
a.jobs.as_slice(),
|
|
1065
|
+
[WorkflowActivationJob {
|
|
1066
|
+
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra))
|
|
1067
|
+
}, WorkflowActivationJob {
|
|
1068
|
+
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra2))
|
|
1069
|
+
}] => {assert_eq!(ra.seq, 1); assert_eq!(ra2.seq, 2)}
|
|
1070
|
+
);
|
|
1071
|
+
}
|
|
1072
|
+
if replay {
|
|
1073
|
+
assert!(
|
|
1074
|
+
a.timestamp.as_ref().unwrap().seconds
|
|
1075
|
+
> first_act_ts_seconds.load(Ordering::Relaxed)
|
|
1076
|
+
)
|
|
1077
|
+
}
|
|
1078
|
+
});
|
|
1079
|
+
if !parallel {
|
|
1080
|
+
aai.then(move |a| {
|
|
1081
|
+
assert_matches!(
|
|
1082
|
+
a.jobs.as_slice(),
|
|
1083
|
+
[WorkflowActivationJob {
|
|
1084
|
+
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra))
|
|
1085
|
+
}] => assert_eq!(ra.seq, 2)
|
|
1086
|
+
);
|
|
1087
|
+
if replay {
|
|
1088
|
+
assert!(
|
|
1089
|
+
a.timestamp.as_ref().unwrap().seconds
|
|
1090
|
+
>= first_act_ts_seconds.load(Ordering::Relaxed) + 2
|
|
1091
|
+
)
|
|
1092
|
+
}
|
|
1093
|
+
});
|
|
1161
1094
|
}
|
|
1162
1095
|
|
|
1163
|
-
|
|
1164
|
-
|
|
1165
|
-
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
|
|
1170
|
-
|
|
1171
|
-
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1176
|
-
|
|
1177
|
-
|
|
1178
|
-
|
|
1179
|
-
|
|
1180
|
-
|
|
1181
|
-
|
|
1182
|
-
|
|
1183
|
-
);
|
|
1184
|
-
} else {
|
|
1185
|
-
assert_eq!(commands.len(), 3);
|
|
1186
|
-
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1187
|
-
assert_eq!(commands[1].command_type, CommandType::RecordMarker as i32);
|
|
1188
|
-
assert_eq!(
|
|
1189
|
-
commands[2].command_type,
|
|
1190
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1191
|
-
);
|
|
1192
|
-
}
|
|
1096
|
+
mock_cfg.completion_asserts_from_expectations(|mut asserts| {
|
|
1097
|
+
asserts.then(move |wft| {
|
|
1098
|
+
let commands = &wft.commands;
|
|
1099
|
+
if !replay {
|
|
1100
|
+
assert_eq!(commands.len(), 3);
|
|
1101
|
+
assert_eq!(commands[0].command_type(), CommandType::RecordMarker);
|
|
1102
|
+
assert_eq!(commands[1].command_type(), CommandType::RecordMarker);
|
|
1103
|
+
assert_matches!(
|
|
1104
|
+
commands[2].command_type(),
|
|
1105
|
+
CommandType::CompleteWorkflowExecution
|
|
1106
|
+
);
|
|
1107
|
+
} else {
|
|
1108
|
+
assert_eq!(commands.len(), 1);
|
|
1109
|
+
assert_matches!(
|
|
1110
|
+
commands[0].command_type(),
|
|
1111
|
+
CommandType::CompleteWorkflowExecution
|
|
1112
|
+
);
|
|
1113
|
+
}
|
|
1114
|
+
});
|
|
1115
|
+
});
|
|
1193
1116
|
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1117
|
+
let mut worker = build_fake_sdk(mock_cfg);
|
|
1118
|
+
worker.set_worker_interceptor(aai);
|
|
1119
|
+
if parallel {
|
|
1120
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, two_la_wf_parallel);
|
|
1121
|
+
} else {
|
|
1122
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, two_la_wf);
|
|
1198
1123
|
}
|
|
1199
|
-
|
|
1200
|
-
|
|
1201
|
-
|
|
1202
|
-
|
|
1203
|
-
|
|
1204
|
-
assert_eq!(commands.len(), 0);
|
|
1205
|
-
|
|
1206
|
-
wfm.shutdown().await.unwrap();
|
|
1124
|
+
worker.register_activity(
|
|
1125
|
+
DEFAULT_ACTIVITY_TYPE,
|
|
1126
|
+
move |_ctx: ActContext, _: ()| async move { Ok("Resolved") },
|
|
1127
|
+
);
|
|
1128
|
+
worker.run().await.unwrap();
|
|
1207
1129
|
}
|
|
1208
1130
|
|
|
1209
1131
|
async fn la_timer_la(ctx: WfContext) -> WorkflowResult<()> {
|
|
1210
1132
|
ctx.local_activity(LocalActivityOptions {
|
|
1211
1133
|
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1134
|
+
input: ().as_json_payload().unwrap(),
|
|
1212
1135
|
..Default::default()
|
|
1213
1136
|
})
|
|
1214
1137
|
.await;
|
|
1215
1138
|
ctx.timer(Duration::from_secs(5)).await;
|
|
1216
1139
|
ctx.local_activity(LocalActivityOptions {
|
|
1217
1140
|
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1141
|
+
input: ().as_json_payload().unwrap(),
|
|
1218
1142
|
..Default::default()
|
|
1219
1143
|
})
|
|
1220
1144
|
.await;
|
|
@@ -1226,98 +1150,81 @@ mod tests {
|
|
|
1226
1150
|
#[case::replay(true)]
|
|
1227
1151
|
#[tokio::test]
|
|
1228
1152
|
async fn las_separated_by_timer(#[case] replay: bool) {
|
|
1229
|
-
let
|
|
1230
|
-
|
|
1231
|
-
|
|
1232
|
-
|
|
1153
|
+
let mut t = TestHistoryBuilder::default();
|
|
1154
|
+
t.add_by_type(EventType::WorkflowExecutionStarted);
|
|
1155
|
+
t.add_full_wf_task();
|
|
1156
|
+
t.add_local_activity_result_marker(1, "1", b"hi".into());
|
|
1157
|
+
let timer_started_event_id = t.add_by_type(EventType::TimerStarted);
|
|
1158
|
+
t.add_timer_fired(timer_started_event_id, "1".to_string());
|
|
1159
|
+
t.add_full_wf_task();
|
|
1160
|
+
t.add_local_activity_result_marker(2, "2", b"hi2".into());
|
|
1161
|
+
t.add_workflow_task_scheduled_and_started();
|
|
1162
|
+
let mut mock_cfg = if replay {
|
|
1163
|
+
MockPollCfg::from_resps(t, [ResponseType::AllHistory])
|
|
1233
1164
|
} else {
|
|
1234
|
-
t
|
|
1165
|
+
MockPollCfg::from_hist_builder(t)
|
|
1235
1166
|
};
|
|
1236
|
-
let mut wfm = ManagedWFFunc::new_from_update(histinfo, func, vec![]);
|
|
1237
|
-
|
|
1238
|
-
wfm.get_next_activation().await.unwrap();
|
|
1239
|
-
let commands = wfm.get_server_commands().commands;
|
|
1240
|
-
assert_eq!(commands.len(), 0);
|
|
1241
|
-
let ready_to_execute_las = wfm.drain_queued_local_activities();
|
|
1242
|
-
let num_queued = usize::from(!replay);
|
|
1243
|
-
assert_eq!(ready_to_execute_las.len(), num_queued);
|
|
1244
|
-
|
|
1245
|
-
if !replay {
|
|
1246
|
-
wfm.complete_local_activity(1, ActivityExecutionResult::ok(b"Resolved".into()))
|
|
1247
|
-
.unwrap();
|
|
1248
|
-
}
|
|
1249
|
-
|
|
1250
|
-
let act = wfm.get_next_activation().await.unwrap();
|
|
1251
|
-
assert_matches!(
|
|
1252
|
-
act.jobs.as_slice(),
|
|
1253
|
-
[WorkflowActivationJob {
|
|
1254
|
-
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra))
|
|
1255
|
-
}] => assert_eq!(ra.seq, 1)
|
|
1256
|
-
);
|
|
1257
|
-
let ready_to_execute_las = wfm.drain_queued_local_activities();
|
|
1258
|
-
assert_eq!(ready_to_execute_las.len(), 0);
|
|
1259
1167
|
|
|
1260
|
-
let
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
|
|
1168
|
+
let mut aai = ActivationAssertionsInterceptor::default();
|
|
1169
|
+
aai.skip_one()
|
|
1170
|
+
.then(|a| {
|
|
1171
|
+
assert_matches!(
|
|
1172
|
+
a.jobs.as_slice(),
|
|
1173
|
+
[WorkflowActivationJob {
|
|
1174
|
+
variant: Some(workflow_activation_job::Variant::ResolveActivity(ra))
|
|
1175
|
+
}] => assert_eq!(ra.seq, 1)
|
|
1176
|
+
);
|
|
1177
|
+
})
|
|
1178
|
+
.then(|a| {
|
|
1179
|
+
assert_matches!(
|
|
1180
|
+
a.jobs.as_slice(),
|
|
1181
|
+
[WorkflowActivationJob {
|
|
1182
|
+
variant: Some(workflow_activation_job::Variant::FireTimer(_))
|
|
1183
|
+
}]
|
|
1184
|
+
);
|
|
1185
|
+
});
|
|
1269
1186
|
|
|
1270
|
-
|
|
1271
|
-
|
|
1272
|
-
.
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
|
|
1282
|
-
|
|
1283
|
-
|
|
1284
|
-
|
|
1285
|
-
|
|
1286
|
-
|
|
1287
|
-
|
|
1288
|
-
|
|
1289
|
-
|
|
1187
|
+
mock_cfg.completion_asserts_from_expectations(|mut asserts| {
|
|
1188
|
+
if replay {
|
|
1189
|
+
asserts.then(|wft| {
|
|
1190
|
+
assert_eq!(wft.commands.len(), 1);
|
|
1191
|
+
assert_eq!(
|
|
1192
|
+
wft.commands[0].command_type,
|
|
1193
|
+
CommandType::CompleteWorkflowExecution as i32
|
|
1194
|
+
);
|
|
1195
|
+
});
|
|
1196
|
+
} else {
|
|
1197
|
+
asserts
|
|
1198
|
+
.then(|wft| {
|
|
1199
|
+
let commands = &wft.commands;
|
|
1200
|
+
assert_eq!(commands.len(), 2);
|
|
1201
|
+
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1202
|
+
assert_eq!(commands[1].command_type, CommandType::StartTimer as i32);
|
|
1203
|
+
})
|
|
1204
|
+
.then(|wft| {
|
|
1205
|
+
let commands = &wft.commands;
|
|
1206
|
+
assert_eq!(commands.len(), 2);
|
|
1207
|
+
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1208
|
+
assert_eq!(
|
|
1209
|
+
commands[1].command_type,
|
|
1210
|
+
CommandType::CompleteWorkflowExecution as i32
|
|
1211
|
+
);
|
|
1212
|
+
});
|
|
1213
|
+
}
|
|
1214
|
+
});
|
|
1290
1215
|
|
|
1291
|
-
let
|
|
1292
|
-
|
|
1293
|
-
|
|
1294
|
-
|
|
1295
|
-
|
|
1296
|
-
|
|
1216
|
+
let mut worker = build_fake_sdk(mock_cfg);
|
|
1217
|
+
worker.set_worker_interceptor(aai);
|
|
1218
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, la_timer_la);
|
|
1219
|
+
worker.register_activity(
|
|
1220
|
+
DEFAULT_ACTIVITY_TYPE,
|
|
1221
|
+
move |_ctx: ActContext, _: ()| async move { Ok("Resolved") },
|
|
1297
1222
|
);
|
|
1298
|
-
|
|
1299
|
-
let commands = wfm.get_server_commands().commands;
|
|
1300
|
-
if replay {
|
|
1301
|
-
assert_eq!(commands.len(), 1);
|
|
1302
|
-
assert_eq!(
|
|
1303
|
-
commands[0].command_type,
|
|
1304
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1305
|
-
);
|
|
1306
|
-
} else {
|
|
1307
|
-
assert_eq!(commands.len(), 2);
|
|
1308
|
-
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1309
|
-
assert_eq!(
|
|
1310
|
-
commands[1].command_type,
|
|
1311
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1312
|
-
);
|
|
1313
|
-
}
|
|
1314
|
-
|
|
1315
|
-
wfm.shutdown().await.unwrap();
|
|
1223
|
+
worker.run().await.unwrap();
|
|
1316
1224
|
}
|
|
1317
1225
|
|
|
1318
1226
|
#[tokio::test]
|
|
1319
1227
|
async fn one_la_heartbeating_wft_failure_still_executes() {
|
|
1320
|
-
let func = WorkflowFunction::new(la_wf);
|
|
1321
1228
|
let mut t = TestHistoryBuilder::default();
|
|
1322
1229
|
t.add_by_type(EventType::WorkflowExecutionStarted);
|
|
1323
1230
|
// Heartbeats
|
|
@@ -1330,21 +1237,26 @@ mod tests {
|
|
|
1330
1237
|
);
|
|
1331
1238
|
t.add_workflow_task_scheduled_and_started();
|
|
1332
1239
|
|
|
1333
|
-
let
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1338
|
-
|
|
1339
|
-
|
|
1340
|
-
|
|
1341
|
-
|
|
1342
|
-
|
|
1343
|
-
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1347
|
-
|
|
1240
|
+
let mut mock_cfg = MockPollCfg::from_hist_builder(t);
|
|
1241
|
+
mock_cfg.completion_asserts_from_expectations(|mut asserts| {
|
|
1242
|
+
asserts.then(move |wft| {
|
|
1243
|
+
assert_eq!(wft.commands.len(), 2);
|
|
1244
|
+
assert_eq!(wft.commands[0].command_type(), CommandType::RecordMarker);
|
|
1245
|
+
assert_matches!(
|
|
1246
|
+
wft.commands[1].command_type(),
|
|
1247
|
+
CommandType::CompleteWorkflowExecution
|
|
1248
|
+
);
|
|
1249
|
+
});
|
|
1250
|
+
});
|
|
1251
|
+
|
|
1252
|
+
let mut worker = build_fake_sdk(mock_cfg);
|
|
1253
|
+
dbg!("Past thing");
|
|
1254
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, la_wf);
|
|
1255
|
+
worker.register_activity(
|
|
1256
|
+
DEFAULT_ACTIVITY_TYPE,
|
|
1257
|
+
move |_ctx: ActContext, _: ()| async move { Ok("Resolved") },
|
|
1258
|
+
);
|
|
1259
|
+
worker.run().await.unwrap();
|
|
1348
1260
|
}
|
|
1349
1261
|
|
|
1350
1262
|
/// This test verifies something that technically shouldn't really be possible but is worth
|
|
@@ -1352,7 +1264,6 @@ mod tests {
|
|
|
1352
1264
|
/// chunk comes back with it failing? We should fail with a mismatch.
|
|
1353
1265
|
#[tokio::test]
|
|
1354
1266
|
async fn exec_passes_but_history_has_fail() {
|
|
1355
|
-
let func = WorkflowFunction::new(la_wf);
|
|
1356
1267
|
let mut t = TestHistoryBuilder::default();
|
|
1357
1268
|
t.add_by_type(EventType::WorkflowExecutionStarted);
|
|
1358
1269
|
t.add_full_wf_task();
|
|
@@ -1361,36 +1272,30 @@ mod tests {
|
|
|
1361
1272
|
"1",
|
|
1362
1273
|
Failure::application_failure("I failed".to_string(), false),
|
|
1363
1274
|
);
|
|
1364
|
-
t.
|
|
1275
|
+
t.add_workflow_task_scheduled_and_started();
|
|
1365
1276
|
|
|
1366
|
-
let
|
|
1367
|
-
|
|
1368
|
-
|
|
1369
|
-
|
|
1370
|
-
|
|
1371
|
-
|
|
1372
|
-
|
|
1373
|
-
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
let commands = wfm.get_server_commands().commands;
|
|
1381
|
-
assert_eq!(commands.len(), 2);
|
|
1382
|
-
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1383
|
-
assert_eq!(
|
|
1384
|
-
commands[1].command_type,
|
|
1385
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1386
|
-
);
|
|
1277
|
+
let mut mock_cfg = MockPollCfg::from_hist_builder(t);
|
|
1278
|
+
// We expect to see a nondeterminism failure (after we respond with record marker, and then
|
|
1279
|
+
// apply the failed marker from history).
|
|
1280
|
+
mock_cfg.num_expected_fails = 1;
|
|
1281
|
+
mock_cfg.completion_asserts_from_expectations(|mut asserts| {
|
|
1282
|
+
asserts.then(|wft| {
|
|
1283
|
+
assert_eq!(wft.commands.len(), 2);
|
|
1284
|
+
assert_eq!(wft.commands[0].command_type(), CommandType::RecordMarker);
|
|
1285
|
+
assert_matches!(
|
|
1286
|
+
wft.commands[1].command_type(),
|
|
1287
|
+
CommandType::CompleteWorkflowExecution
|
|
1288
|
+
);
|
|
1289
|
+
});
|
|
1290
|
+
});
|
|
1387
1291
|
|
|
1388
|
-
let
|
|
1389
|
-
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
|
|
1393
|
-
|
|
1292
|
+
let mut worker = build_fake_sdk(mock_cfg);
|
|
1293
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, la_wf);
|
|
1294
|
+
worker.register_activity(
|
|
1295
|
+
DEFAULT_ACTIVITY_TYPE,
|
|
1296
|
+
move |_ctx: ActContext, _: ()| async move { Ok("Resolved") },
|
|
1297
|
+
);
|
|
1298
|
+
worker.run().await.unwrap();
|
|
1394
1299
|
}
|
|
1395
1300
|
|
|
1396
1301
|
#[rstest]
|
|
@@ -1403,7 +1308,26 @@ mod tests {
|
|
|
1403
1308
|
)]
|
|
1404
1309
|
cancel_type: ActivityCancellationType,
|
|
1405
1310
|
) {
|
|
1406
|
-
let
|
|
1311
|
+
let mut t = TestHistoryBuilder::default();
|
|
1312
|
+
t.add_by_type(EventType::WorkflowExecutionStarted);
|
|
1313
|
+
t.add_full_wf_task();
|
|
1314
|
+
t.add_workflow_execution_completed();
|
|
1315
|
+
|
|
1316
|
+
let mut mock_cfg = MockPollCfg::from_hist_builder(t);
|
|
1317
|
+
mock_cfg.completion_asserts_from_expectations(|mut asserts| {
|
|
1318
|
+
asserts.then(|wft| {
|
|
1319
|
+
assert_eq!(wft.commands.len(), 2);
|
|
1320
|
+
// We record the cancel marker
|
|
1321
|
+
assert_eq!(wft.commands[0].command_type(), CommandType::RecordMarker);
|
|
1322
|
+
assert_matches!(
|
|
1323
|
+
wft.commands[1].command_type(),
|
|
1324
|
+
CommandType::CompleteWorkflowExecution
|
|
1325
|
+
);
|
|
1326
|
+
});
|
|
1327
|
+
});
|
|
1328
|
+
|
|
1329
|
+
let mut worker = build_fake_sdk(mock_cfg);
|
|
1330
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, move |ctx: WfContext| async move {
|
|
1407
1331
|
let la = ctx.local_activity(LocalActivityOptions {
|
|
1408
1332
|
cancel_type,
|
|
1409
1333
|
..Default::default()
|
|
@@ -1412,34 +1336,8 @@ mod tests {
|
|
|
1412
1336
|
la.await;
|
|
1413
1337
|
Ok(().into())
|
|
1414
1338
|
});
|
|
1415
|
-
|
|
1416
|
-
|
|
1417
|
-
t.add_full_wf_task();
|
|
1418
|
-
t.add_workflow_execution_completed();
|
|
1419
|
-
|
|
1420
|
-
let histinfo = t.get_history_info(1).unwrap().into();
|
|
1421
|
-
let mut wfm = ManagedWFFunc::new_from_update(histinfo, func, vec![]);
|
|
1422
|
-
|
|
1423
|
-
wfm.get_next_activation().await.unwrap();
|
|
1424
|
-
let commands = wfm.get_server_commands().commands;
|
|
1425
|
-
assert_eq!(commands.len(), 1);
|
|
1426
|
-
// We record the cancel marker
|
|
1427
|
-
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1428
|
-
// Importantly, the activity shouldn't get executed since it was insta-cancelled
|
|
1429
|
-
let ready_to_execute_las = wfm.drain_queued_local_activities();
|
|
1430
|
-
assert_eq!(ready_to_execute_las.len(), 0);
|
|
1431
|
-
|
|
1432
|
-
// next activation unblocks LA, which is cancelled now.
|
|
1433
|
-
wfm.get_next_activation().await.unwrap();
|
|
1434
|
-
let commands = wfm.get_server_commands().commands;
|
|
1435
|
-
assert_eq!(commands.len(), 2);
|
|
1436
|
-
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1437
|
-
assert_eq!(
|
|
1438
|
-
commands[1].command_type,
|
|
1439
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1440
|
-
);
|
|
1441
|
-
|
|
1442
|
-
wfm.shutdown().await.unwrap();
|
|
1339
|
+
// Explicitly don't register an activity, since we shouldn't need to run one.
|
|
1340
|
+
worker.run().await.unwrap();
|
|
1443
1341
|
}
|
|
1444
1342
|
|
|
1445
1343
|
#[rstest]
|
|
@@ -1455,37 +1353,19 @@ mod tests {
|
|
|
1455
1353
|
)]
|
|
1456
1354
|
cancel_type: ActivityCancellationType,
|
|
1457
1355
|
) {
|
|
1458
|
-
let func = WorkflowFunction::new(move |ctx| async move {
|
|
1459
|
-
let la = ctx.local_activity(LocalActivityOptions {
|
|
1460
|
-
cancel_type,
|
|
1461
|
-
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1462
|
-
..Default::default()
|
|
1463
|
-
});
|
|
1464
|
-
ctx.timer(Duration::from_secs(1)).await;
|
|
1465
|
-
la.cancel(&ctx);
|
|
1466
|
-
// This extra timer is here to ensure the presence of another WF task doesn't mess up
|
|
1467
|
-
// resolving the LA with cancel on replay
|
|
1468
|
-
ctx.timer(Duration::from_secs(1)).await;
|
|
1469
|
-
let resolution = la.await;
|
|
1470
|
-
assert!(resolution.cancelled());
|
|
1471
|
-
let rfail = resolution.unwrap_failure();
|
|
1472
|
-
assert_matches!(
|
|
1473
|
-
rfail.failure_info,
|
|
1474
|
-
Some(FailureInfo::ActivityFailureInfo(_))
|
|
1475
|
-
);
|
|
1476
|
-
assert_matches!(
|
|
1477
|
-
rfail.cause.unwrap().failure_info,
|
|
1478
|
-
Some(FailureInfo::CanceledFailureInfo(_))
|
|
1479
|
-
);
|
|
1480
|
-
Ok(().into())
|
|
1481
|
-
});
|
|
1482
|
-
|
|
1483
1356
|
let mut t = TestHistoryBuilder::default();
|
|
1484
|
-
t.
|
|
1357
|
+
t.add_wfe_started_with_wft_timeout(Duration::from_millis(100));
|
|
1485
1358
|
t.add_full_wf_task();
|
|
1486
1359
|
let timer_started_event_id = t.add_by_type(EventType::TimerStarted);
|
|
1487
1360
|
t.add_timer_fired(timer_started_event_id, "1".to_string());
|
|
1488
1361
|
t.add_full_wf_task();
|
|
1362
|
+
// This extra workflow task serves to prevent looking ahead and pre-resolving during
|
|
1363
|
+
// wait-cancel.
|
|
1364
|
+
// TODO: including this on non wait-cancel seems to cause double-send of
|
|
1365
|
+
// marker recorded cmd
|
|
1366
|
+
if cancel_type == ActivityCancellationType::WaitCancellationCompleted {
|
|
1367
|
+
t.add_full_wf_task();
|
|
1368
|
+
}
|
|
1489
1369
|
if cancel_type != ActivityCancellationType::WaitCancellationCompleted {
|
|
1490
1370
|
// With non-wait cancels, the cancel is immediate
|
|
1491
1371
|
t.add_local_activity_cancel_marker(1, "1");
|
|
@@ -1499,79 +1379,86 @@ mod tests {
|
|
|
1499
1379
|
t.add_full_wf_task();
|
|
1500
1380
|
t.add_workflow_execution_completed();
|
|
1501
1381
|
|
|
1502
|
-
let
|
|
1503
|
-
t
|
|
1382
|
+
let mut mock_cfg = if replay {
|
|
1383
|
+
MockPollCfg::from_resps(t, [ResponseType::AllHistory])
|
|
1504
1384
|
} else {
|
|
1505
|
-
t
|
|
1506
|
-
};
|
|
1507
|
-
let mut wfm = ManagedWFFunc::new_from_update(histinfo, func, vec![]);
|
|
1508
|
-
|
|
1509
|
-
wfm.get_next_activation().await.unwrap();
|
|
1510
|
-
let commands = wfm.get_server_commands().commands;
|
|
1511
|
-
assert_eq!(commands.len(), 1);
|
|
1512
|
-
assert_eq!(commands[0].command_type, CommandType::StartTimer as i32);
|
|
1513
|
-
let ready_to_execute_las = wfm.drain_queued_local_activities();
|
|
1514
|
-
let num_queued = usize::from(!replay);
|
|
1515
|
-
assert_eq!(ready_to_execute_las.len(), num_queued);
|
|
1516
|
-
|
|
1517
|
-
// Next activation timer fires and activity cancel will be requested
|
|
1518
|
-
if replay {
|
|
1519
|
-
wfm.get_next_activation().await.unwrap()
|
|
1520
|
-
} else {
|
|
1521
|
-
wfm.new_history(t.get_history_info(2).unwrap().into())
|
|
1522
|
-
.await
|
|
1523
|
-
.unwrap()
|
|
1385
|
+
MockPollCfg::from_hist_builder(t)
|
|
1524
1386
|
};
|
|
1387
|
+
let allow_cancel_barr = CancellationToken::new();
|
|
1388
|
+
let allow_cancel_barr_clone = allow_cancel_barr.clone();
|
|
1525
1389
|
|
|
1526
|
-
|
|
1527
|
-
|
|
1528
|
-
|
|
1529
|
-
|
|
1530
|
-
|
|
1531
|
-
|
|
1532
|
-
|
|
1533
|
-
|
|
1534
|
-
|
|
1390
|
+
if !replay {
|
|
1391
|
+
mock_cfg.completion_asserts_from_expectations(|mut asserts| {
|
|
1392
|
+
asserts
|
|
1393
|
+
.then(move |wft| {
|
|
1394
|
+
assert_eq!(wft.commands.len(), 1);
|
|
1395
|
+
assert_eq!(wft.commands[0].command_type, CommandType::StartTimer as i32);
|
|
1396
|
+
})
|
|
1397
|
+
.then(move |wft| {
|
|
1398
|
+
let commands = &wft.commands;
|
|
1399
|
+
if cancel_type == ActivityCancellationType::WaitCancellationCompleted {
|
|
1400
|
+
assert_eq!(commands.len(), 1);
|
|
1401
|
+
assert_eq!(commands[0].command_type, CommandType::StartTimer as i32);
|
|
1402
|
+
} else {
|
|
1403
|
+
// Try-cancel/abandon immediately recordsmarker (when not replaying)
|
|
1404
|
+
assert_eq!(commands.len(), 2);
|
|
1405
|
+
assert_eq!(commands[0].command_type, CommandType::RecordMarker as i32);
|
|
1406
|
+
assert_eq!(commands[1].command_type, CommandType::StartTimer as i32);
|
|
1407
|
+
}
|
|
1408
|
+
// Allow the wait-cancel to actually cancel
|
|
1409
|
+
allow_cancel_barr.cancel();
|
|
1410
|
+
})
|
|
1411
|
+
.then(move |wft| {
|
|
1412
|
+
let commands = &wft.commands;
|
|
1413
|
+
if cancel_type == ActivityCancellationType::WaitCancellationCompleted {
|
|
1414
|
+
assert_eq!(commands[0].command_type, CommandType::StartTimer as i32);
|
|
1415
|
+
assert_eq!(commands[1].command_type, CommandType::RecordMarker as i32);
|
|
1416
|
+
} else {
|
|
1417
|
+
assert_eq!(
|
|
1418
|
+
commands[0].command_type,
|
|
1419
|
+
CommandType::CompleteWorkflowExecution as i32
|
|
1420
|
+
);
|
|
1421
|
+
}
|
|
1422
|
+
});
|
|
1423
|
+
});
|
|
1535
1424
|
}
|
|
1536
1425
|
|
|
1537
|
-
let
|
|
1538
|
-
|
|
1539
|
-
|
|
1540
|
-
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
|
|
1544
|
-
|
|
1545
|
-
|
|
1546
|
-
|
|
1547
|
-
|
|
1548
|
-
|
|
1549
|
-
|
|
1550
|
-
|
|
1551
|
-
|
|
1552
|
-
let
|
|
1553
|
-
|
|
1554
|
-
|
|
1555
|
-
|
|
1556
|
-
|
|
1557
|
-
|
|
1558
|
-
|
|
1559
|
-
|
|
1426
|
+
let mut worker = build_fake_sdk(mock_cfg);
|
|
1427
|
+
worker.register_wf(DEFAULT_WORKFLOW_TYPE, move |ctx: WfContext| async move {
|
|
1428
|
+
let la = ctx.local_activity(LocalActivityOptions {
|
|
1429
|
+
cancel_type,
|
|
1430
|
+
input: ().as_json_payload().unwrap(),
|
|
1431
|
+
activity_type: DEFAULT_ACTIVITY_TYPE.to_string(),
|
|
1432
|
+
..Default::default()
|
|
1433
|
+
});
|
|
1434
|
+
ctx.timer(Duration::from_secs(1)).await;
|
|
1435
|
+
la.cancel(&ctx);
|
|
1436
|
+
// This extra timer is here to ensure the presence of another WF task doesn't mess up
|
|
1437
|
+
// resolving the LA with cancel on replay
|
|
1438
|
+
ctx.timer(Duration::from_secs(1)).await;
|
|
1439
|
+
let resolution = la.await;
|
|
1440
|
+
assert!(resolution.cancelled());
|
|
1441
|
+
let rfail = resolution.unwrap_failure();
|
|
1442
|
+
assert_matches!(
|
|
1443
|
+
rfail.failure_info,
|
|
1444
|
+
Some(FailureInfo::ActivityFailureInfo(_))
|
|
1445
|
+
);
|
|
1446
|
+
assert_matches!(
|
|
1447
|
+
rfail.cause.unwrap().failure_info,
|
|
1448
|
+
Some(FailureInfo::CanceledFailureInfo(_))
|
|
1449
|
+
);
|
|
1450
|
+
Ok(().into())
|
|
1451
|
+
});
|
|
1452
|
+
worker.register_activity(DEFAULT_ACTIVITY_TYPE, move |ctx: ActContext, _: ()| {
|
|
1453
|
+
let allow_cancel_barr_clone = allow_cancel_barr_clone.clone();
|
|
1454
|
+
async move {
|
|
1455
|
+
if cancel_type == ActivityCancellationType::WaitCancellationCompleted {
|
|
1456
|
+
ctx.cancelled().await;
|
|
1457
|
+
}
|
|
1458
|
+
allow_cancel_barr_clone.cancelled().await;
|
|
1459
|
+
Result::<(), _>::Err(anyhow!(ActivityCancelledError::default()))
|
|
1560
1460
|
}
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
.await
|
|
1564
|
-
.unwrap();
|
|
1565
|
-
wfm.get_next_activation().await.unwrap();
|
|
1566
|
-
wfm.get_server_commands().commands
|
|
1567
|
-
};
|
|
1568
|
-
|
|
1569
|
-
assert_eq!(commands.len(), 1);
|
|
1570
|
-
assert_eq!(
|
|
1571
|
-
commands[0].command_type,
|
|
1572
|
-
CommandType::CompleteWorkflowExecution as i32
|
|
1573
|
-
);
|
|
1574
|
-
|
|
1575
|
-
wfm.shutdown().await.unwrap();
|
|
1461
|
+
});
|
|
1462
|
+
worker.run().await.unwrap();
|
|
1576
1463
|
}
|
|
1577
1464
|
}
|