// Copyright (c) 2026 Super Durable, Inc.
//
// Licensed under the Super Durable Source License 1.0.
// You may not use this file except in compliance with the License.
// See the LICENSE file in the repository root.
//
// SPDX-License-Identifier: LicenseRef-Super-Durable-1.0
syntax = "proto3";
package dex;
import "google/protobuf/empty.proto";
import "google/protobuf/duration.proto";
import "google/protobuf/struct.proto";
import "google/protobuf/timestamp.proto";
option java_multiple_files = true;
option java_package = "io.superdurable.gen";
option java_outer_classname = "DexProto";
// ---------------------------------------------------------------------------
// FlowService error handling
//
// Failures return a gRPC status with dexpb.ServiceErrorResponse in status details
// (see ServiceErrorResponse / ErrorSubStatus). Clients should read both the gRPC code
// and ServiceErrorResponse.sub_status / detail / original_worker_error_*.
//
// Common gRPC codes (all RPCs unless noted):
// InvalidArgument — bad request / invalid Value / empty lock keys, etc.
// sub_status usually UNCATEGORIZED
// AlreadyExists — StartFlow when ID already running
// sub_status FLOW_ALREADY_STARTED
// NotFound — unknown flow/run
// sub_status FLOW_NOT_EXISTS
// FailedPrecondition — closed/invalid flow state; blob-backed WaitForAttribute;
// Dex application WorkerService failures (business errors
// and unreachable/dial/transport to the app worker). These
// must not use Unavailable so they do not count against
// server SLA/SLO. sub_status WORKER_API_ERROR when from
// WorkerService; raw worker code/detail/type in
// original_worker_error_* when available
// Aborted — locking RPC attribute lock contention
// sub_status WORKER_API_ERROR
// ResourceExhausted — worker connection pool / message size limits
// DeadlineExceeded — wait past effective deadline (WaitForFlow,
// WaitForStepCompletion, WaitForAttribute)
// sub_status LONG_POLL_TIME_OUT
// Canceled — caller canceled the RPC context
// Unavailable — Temporal/Cadence backend (workflow engine) unavailable
// only — never Dex application WorkerService
// Internal — unexpected / violated trusted invariant
// Unimplemented — Cadence: WaitForStepCompletion, WaitForAttribute,
// locking InvokeRPC (Temporal sync update required)
//
// Notable per-RPC behavior:
// InvokeRPC — empty LockAttributeKeys uses query + WorkerService + optional
// signal by default. Temporal can opt into synchronous Updates for all RPCs.
// Non-empty LockAttributeKeys requires a Temporal synchronous Update;
// Cadence returns Unimplemented.
// WorkerService errors (app or transport-to-worker) → FailedPrecondition +
// WORKER_API_ERROR + OriginalWorker* when present.
// WaitForStepCompletion / WaitForAttribute — Temporal-only sync updates; API
// retries CONTINUE_AS_NEW_PREEMPTED (not exposed as Internal). Timeout →
// DeadlineExceeded + LONG_POLL_TIME_OUT. WaitForAttribute rejects waiting on
// blob-backed stored attributes with FailedPrecondition.
// WaitForFlow — long-poll timeout while still running → DeadlineExceeded +
// LONG_POLL_TIME_OUT.
// ---------------------------------------------------------------------------
// Hosted by Dex server; SDKs call these RPCs.
service FlowService {
rpc StartFlow(StartFlowRequest) returns (StartFlowResponse);
rpc PublishToChannel(PublishToChannelRequest) returns (google.protobuf.Empty);
rpc StopFlow(StopFlowRequest) returns (google.protobuf.Empty);
rpc GetAttributes(GetAttributesRequest) returns (GetAttributesResponse);
rpc SetAttributes(SetAttributesRequest) returns (google.protobuf.Empty);
rpc LoadBlobs(LoadBlobsRequest) returns (LoadBlobsResponse);
rpc WaitForFlow(WaitForFlowRequest) returns (FlowResult);
rpc SearchFlows(SearchFlowsRequest) returns (SearchFlowsResponse);
rpc SyncAttributeIndexes(SyncAttributeIndexRequest) returns (SyncAttributeIndexResponse);
rpc GetFlowSummary(GetFlowSummaryRequest) returns (GetFlowSummaryResponse);
rpc GetHistoryEvents(GetHistoryEventsRequest) returns (GetHistoryEventsResponse);
rpc WaitForHistoryEvent(WaitForHistoryEventRequest) returns (WaitForHistoryEventResponse);
rpc GetFlowState(GetFlowStateRequest) returns (GetFlowStateResponse);
rpc ResetFlow(ResetFlowRequest) returns (ResetFlowResponse);
rpc InvokeRPC(InvokeRPCRequest) returns (InvokeRPCResponse);
rpc SkipTimer(SkipTimerRequest) returns (google.protobuf.Empty);
rpc UpdateFlowConfig(UpdateFlowConfigRequest) returns (google.protobuf.Empty);
rpc WaitForStepCompletion(WaitForStepCompletionRequest) returns (WaitForStepCompletionResponse);
rpc WaitForAttribute(WaitForAttributeRequest) returns (google.protobuf.Empty);
rpc TriggerContinueAsNew(TriggerContinueAsNewRequest) returns (google.protobuf.Empty);
rpc HealthCheck(google.protobuf.Empty) returns (HealthInfo);
}
// Hosted by Dex worker; server calls these RPCs.
service WorkerService {
rpc InvokeWaitForMethod(InvokeWaitForMethodRequest) returns (InvokeWaitForMethodResponse);
rpc InvokeExecuteMethod(InvokeExecuteMethodRequest) returns (InvokeExecuteMethodResponse);
rpc InvokeWorkerRPC(InvokeWorkerRPCRequest) returns (InvokeWorkerRPCResponse);
}
// Server-internal only (interpreter CAN activity → API). Not SDK-facing.
service InternalService {
rpc DumpFlowForContinueAsNew(ContinueAsNewDumpRequest) returns (ContinueAsNewDumpResponse);
}
message Value {
oneof kind {
// Hydrate from blob storage, then replace with string_value.
string internal_blob_id_for_string_value = 1;
// Hydrate from blob storage, then replace with obj_value.
string internal_blob_id_for_obj_value = 2;
string string_value = 3;
EncodedObject obj_value = 4;
int64 int_value = 5;
double double_value = 6;
bool bool_value = 7;
// Null deletes an attribute in storage.
google.protobuf.NullValue null_value = 8;
}
}
message EncodedObject {
string encoding = 1;
bytes payload = 2;
}
message AttributeWrite {
string key = 1;
Value value = 2;
// Omit when indexing is inferred or attribute is not indexed.
IndexConfig index_config = 3;
// Omit or disable to keep this write out of the configured Attribute Store.
AttributeSyncConfig sync_config = 4;
}
message AttributeSyncConfig {
// Enqueues this write for the Flow's current Attribute Store target.
bool enabled = 1;
}
message KV {
string key = 1;
Value value = 2;
}
message IndexConfig {
bool enable = 1;
IndexType type = 2;
// Omit to use the attribute key; set for dynamic attrs.
string index_key = 3;
}
enum IndexType {
INDEX_TYPE_UNSPECIFIED = 0;
// Default for string/object when type is omitted.
INDEX_TYPE_KEYWORD = 1;
INDEX_TYPE_TEXT = 2;
INDEX_TYPE_KEYWORD_ARRAY = 3;
// Usually inferred from Value; optional to set explicitly.
INDEX_TYPE_INT = 4;
INDEX_TYPE_DOUBLE = 5;
INDEX_TYPE_BOOL = 6;
INDEX_TYPE_DATETIME = 7;
}
message Context {
string flow_id = 1;
string run_id = 2;
int64 flow_started_timestamp = 3;
string step_execution_id = 4;
int64 first_attempt_timestamp = 5;
int32 attempt = 6;
// Step execution that scheduled this execution, or a reserved source.
string from_step_execution_id = 7;
// Previous Step method failure supplied only to its configured recovery method.
RecoveryErrorInfo recovery_error = 8;
}
message LocalActivityMetadata {
string current_step_execution_id = 1;
string from_step_execution_id = 2;
}
message RetryPolicy {
int32 initial_interval_seconds = 1;
float backoff_coefficient = 2;
int32 maximum_interval_seconds = 3;
int32 maximum_attempts = 4;
int32 total_duration_seconds = 5;
}
message FlowRetryPolicy {
int32 initial_interval_seconds = 1;
float backoff_coefficient = 2;
int32 maximum_interval_seconds = 3;
int32 maximum_attempts = 4;
}
enum WaitForMethodFailurePolicy {
WAIT_FOR_METHOD_FAILURE_POLICY_UNSPECIFIED = 0;
WAIT_FOR_METHOD_FAILURE_POLICY_FAIL_FLOW_ON_FAILURE = 1;
WAIT_FOR_METHOD_FAILURE_POLICY_PROCEED_ON_FAILURE = 2;
}
enum ExecuteMethodFailurePolicy {
EXECUTE_METHOD_FAILURE_POLICY_UNSPECIFIED = 0;
EXECUTE_METHOD_FAILURE_POLICY_FAIL_FLOW_ON_EXECUTE_METHOD_FAILURE = 1;
EXECUTE_METHOD_FAILURE_POLICY_PROCEED_TO_CONFIGURED_STEP = 2;
}
message StepOptions {
int32 wait_for_timeout_seconds = 1;
int32 execute_timeout_seconds = 2;
RetryPolicy wait_for_retry_policy = 3;
RetryPolicy execute_retry_policy = 4;
WaitForMethodFailurePolicy wait_for_failure_policy = 5;
ExecuteMethodFailurePolicy execute_failure_policy = 6;
string execute_failure_proceed_step_type = 7;
StepOptions execute_failure_proceed_step_options = 8;
bool skip_wait_for = 9;
StepDurability wait_for_durability_override = 10;
StepDurability execute_durability_override = 11;
repeated string wait_for_lock_attribute_keys = 12;
repeated string execute_lock_attribute_keys = 13;
int32 heartbeat_timeout_seconds = 14;
}
enum IdReusePolicy {
ID_REUSE_POLICY_UNSPECIFIED = 0;
ID_REUSE_POLICY_ALLOW_IF_PREVIOUS_EXISTS_ABNORMALLY = 1;
ID_REUSE_POLICY_ALLOW_IF_NO_RUNNING = 2;
ID_REUSE_POLICY_DISALLOW_REUSE = 3;
ID_REUSE_POLICY_ALLOW_TERMINATE_IF_RUNNING = 4;
}
message FlowAlreadyStartedOptions {
bool ignore_already_started_error = 1;
}
message FlowStartOptions {
IdReusePolicy id_reuse_policy = 1;
int32 flow_start_delay_seconds = 2;
FlowRetryPolicy retry_policy = 3;
repeated AttributeWrite attributes = 4;
FlowConfig flow_config_override = 5;
FlowAlreadyStartedOptions flow_already_started_options = 6;
}
enum ActiveStepSearchMode {
ACTIVE_STEP_SEARCH_MODE_UNSPECIFIED = 0;
ACTIVE_STEP_SEARCH_MODE_ENABLED_FOR_ALL = 1;
ACTIVE_STEP_SEARCH_MODE_ENABLED_FOR_STEPS_WITH_WAIT_FOR = 2;
ACTIVE_STEP_SEARCH_MODE_DISABLED = 3;
}
// Was optimize_activity: false=SYNC, true=ASYNC. Timer is always optimized by the server.
enum StepDurability {
STEP_DURABILITY_UNSPECIFIED = 0;
STEP_DURABILITY_SYNC = 1;
STEP_DURABILITY_ASYNC = 2;
}
message FlowConfig {
optional ActiveStepSearchMode active_step_search_mode = 1;
optional int32 continue_as_new_threshold = 2;
optional int32 continue_as_new_page_size_in_bytes = 3;
optional StepDurability step_durability = 4;
WorkerTarget worker_target = 5;
// Present empty disables future synchronization; non-empty selects a Server-configured store.
optional string attribute_sync_config_name = 6;
}
message WorkerTarget {
// Plaintext gRPC dial target, not an HTTP URL.
string address = 1;
bool is_headless_address = 2;
}
message StartFlowRequest {
string flow_id = 1;
string flow_type = 2;
int32 flow_timeout_seconds = 3;
FlowTimeoutPolicy flow_timeout_policy = 4;
string start_step_type = 5;
Value step_input = 8;
StepOptions step_options = 9;
FlowStartOptions flow_start_options = 10;
string request_id = 11;
}
enum FlowTimeoutPolicy {
FLOW_TIMEOUT_POLICY_UNSPECIFIED = 0;
FLOW_TIMEOUT_POLICY_FAIL = 1;
FLOW_TIMEOUT_POLICY_CANCEL = 2;
FLOW_TIMEOUT_POLICY_HANDLER = 3;
}
message StartFlowResponse {
string run_id = 1;
}
message PublishToChannelRequest {
string flow_id = 1;
string run_id = 2;
repeated ChannelMessage messages = 3;
}
message ChannelMessage {
string channel_name = 1;
Value value = 2;
}
enum StopType {
STOP_TYPE_UNSPECIFIED = 0;
STOP_TYPE_CANCEL = 1;
STOP_TYPE_TERMINATE = 2;
STOP_TYPE_FAIL = 3;
}
message StopFlowRequest {
string flow_id = 1;
string run_id = 2;
string reason = 3;
StopType stop_type = 4;
}
message GetAttributesRequest {
string flow_id = 1;
string run_id = 2;
repeated string keys = 3;
// When true, return all attributes (keys is ignored).
bool all_keys = 4;
}
message GetAttributesResponse {
repeated KV attributes = 1;
}
message SetAttributesRequest {
string flow_id = 1;
string run_id = 2;
repeated AttributeWrite attributes = 3;
string request_id = 4;
}
message LoadBlobsRequest {
// Each value must be a blob-id only
// (internal_blob_id_for_string_value or internal_blob_id_for_obj_value).
// Concrete payload arms (string_value / obj_value) are rejected.
repeated Value values = 1;
}
message LoadBlobsResponse {
// Hydrated concrete values keyed by blob id.
map<string, Value> values = 1;
}
message WaitForFlowRequest {
string flow_id = 1;
string run_id = 2;
bool needs_results = 3;
// Zero/omit uses the configured API maximum wait.
int32 wait_time_seconds = 4;
}
enum FlowStatus {
FLOW_STATUS_UNSPECIFIED = 0;
FLOW_STATUS_RUNNING = 1;
FLOW_STATUS_COMPLETED = 2;
FLOW_STATUS_FAILED = 3;
// Reserved for reporting a backend hard timeout; applications must not depend on this status.
FLOW_STATUS_SERVER_SIDE_TIMEOUT_INTERNAL_ONLY = 4;
FLOW_STATUS_TERMINATED = 5;
FLOW_STATUS_CANCELED = 6;
FLOW_STATUS_CONTINUED_AS_NEW = 7;
}
enum FlowErrorType {
FLOW_ERROR_TYPE_UNSPECIFIED = 0;
FLOW_ERROR_TYPE_STEP_DECISION_FAILING_FLOW = 1;
FLOW_ERROR_TYPE_CLIENT_API_FAILING_FLOW = 2;
// includes waitFor/execute/rpc methods
FLOW_ERROR_TYPE_WORKER_API_FAIL = 3;
FLOW_ERROR_TYPE_INVALID_USER_FLOW_CODE = 4;
FLOW_ERROR_TYPE_FLOW_TIMEOUT = 5;
// either bug in sdk or server
FLOW_ERROR_TYPE_INTERNAL = 6;
}
message StepCompletionOutput {
string completed_step_type = 1;
string completed_step_execution_id = 2;
Value completed_step_output = 3;
}
message FlowResult {
FlowStatus flow_status = 1;
repeated StepCompletionOutput results = 2;
FlowErrorType error_type = 3;
string error_message = 4;
}
message SearchFlowsRequest {
string query = 1;
int32 page_size = 2;
string next_page_token = 3;
}
message SearchFlowsResponse {
repeated SearchFlowsResponseEntry flow_runs = 1;
string next_page_token = 2;
}
message SearchFlowsResponseEntry {
string flow_id = 1;
string run_id = 2;
repeated KV indexed_attributes = 3;
string flow_type = 4;
FlowStatus flow_status = 5;
google.protobuf.Timestamp start_time = 6;
google.protobuf.Timestamp close_time = 7;
}
message SyncAttributeIndexRequest {
map<string, IndexType> attribute_indexes = 1;
}
message SyncAttributeIndexResponse {}
message FlowExecutionID {
string flow_id = 1;
string run_id = 2;
}
message GetFlowSummaryRequest {
string flow_id = 1;
string run_id = 2;
}
message GetFlowSummaryResponse {
FlowExecutionID flow_execution_id = 1;
string first_run_id = 2;
string request_id = 3;
string flow_type = 4;
FlowStatus flow_status = 5;
google.protobuf.Timestamp start_time = 6;
google.protobuf.Timestamp close_time = 7;
}
message InternalAsyncStepInputSnapshot {
StepMethodOptions method_options = 1;
oneof request {
InvokeWaitForMethodRequest wait_for_request = 2;
InvokeExecuteMethodRequest execute_request = 3;
}
}
message InternalLocalActivityInput {
int64 current_run_started_timestamp = 1;
StepMethodOptions method_options = 2;
}
message GetHistoryEventsRequest {
string flow_id = 1;
string run_id = 2;
int64 start_internal_event_id = 3;
int32 estimate_page_size = 4;
bytes next_page_token = 5;
}
message GetHistoryEventsResponse {
repeated FlowHistoryEvent events = 1;
bytes next_page_token = 2;
int64 next_internal_event_id = 3;
}
message FlowHistoryEvent {
int64 event_id = 1;
google.protobuf.Timestamp event_time = 2;
oneof payload {
FlowStartedOrContinuedHistoryEvent flow_started_or_continued = 20;
FlowClosedHistoryEvent flow_closed = 21;
StepWaitForCompletedEvent step_wait_for_completed = 22;
StepWaitForFailedEvent step_wait_for_failed = 23;
StepExecuteCompletedEvent step_execute_completed = 24;
StepExecuteFailedEvent step_execute_failed = 25;
RpcExecutionCompletedEvent rpc_execution_completed = 26;
ChannelExternalPublishEvent channel_external_publish = 27;
StepMethodPendingEvent step_wait_for_pending = 28;
StepMethodPendingEvent step_execute_pending = 29;
TimeTravelForkHistoryEvent time_travel_fork = 30;
}
}
// TimeTravelForkHistoryEvent identifies the preserved run whose history Time Travel forked.
message TimeTravelForkHistoryEvent {
// Previous run containing the original history branch.
string previous_run_id = 1;
}
message FlowStartedOrContinuedHistoryEvent {
FlowExecutionID flow_execution_id = 1;
string flow_type = 2;
FlowConfig flow_config = 3;
google.protobuf.Duration flow_timeout = 4;
FlowTimeoutPolicy flow_timeout_policy = 5;
oneof start_or_continue {
FlowInitialStart initial_start = 10;
FlowContinuedStart continued_start = 11;
}
}
message FlowInitialStart {
string start_step_type = 1;
Value step_input = 2;
StepOptions step_options = 3;
repeated KV initial_attributes = 4;
}
message FlowContinuedStart {
string previous_run_id = 1;
repeated StepMovement steps_to_start = 2;
repeated StepExecutionResumeInfo steps_to_resume = 3;
map<string, ChannelValues> pending_channel_messages = 4;
repeated KV attributes = 5;
repeated StepCompletionOutput completed_steps = 6;
}
message FlowClosedHistoryEvent {
FlowStatus flow_status = 1;
repeated StepCompletionOutput results = 2;
FlowErrorType error_type = 3;
string error_message = 4;
string continued_to_run_id = 5;
}
// PendingStepMethodPhase reports the latest persisted backend lifecycle event.
enum PendingStepMethodPhase {
PENDING_STEP_METHOD_PHASE_UNSPECIFIED = 0;
PENDING_STEP_METHOD_PHASE_SCHEDULED = 1;
PENDING_STEP_METHOD_PHASE_STARTED = 2;
}
// StepMethodPendingEvent describes a regular Step activity unresolved at flow closure.
message StepMethodPendingEvent {
StepMethodEventInput input = 1;
StepMethodEventContext context = 2;
PendingStepMethodPhase phase = 3;
}
message StepMethodFailure {
string backend_error = 1;
ServiceErrorResponse details = 2;
int32 attempt = 3;
}
message StepMethodOptions {
int32 timeout_seconds = 1;
RetryPolicy retry_policy = 2;
int32 heartbeat_timeout_seconds = 3;
}
message StepMethodEventInput {
bool unavailable = 1;
Value step_input = 2;
ConditionResults condition_results = 3;
repeated KV attributes = 4;
repeated KV step_execution_locals = 5;
}
message StepMethodEventContext {
string step_execution_id = 1;
string from_step_execution_id = 2;
string step_type = 3;
StepDurability durability = 4;
int32 final_attempt = 5;
google.protobuf.Timestamp started_time = 6;
google.protobuf.Duration duration = 7;
StepMethodOptions method_options = 8;
StepMethodFailure last_failure_info = 9;
}
message StepWaitForCompletedOutput {
WaitingCondition wait_for_condition = 1;
repeated AttributeWrite upsert_attributes = 2;
repeated ChannelMessage publish_to_channel = 3;
repeated KV record_events = 4;
repeated KV upsert_step_execution_locals = 5;
}
message StepExecuteCompletedOutput {
StepDecision step_decision = 1;
repeated AttributeWrite upsert_attributes = 2;
repeated ChannelMessage publish_to_channel = 3;
repeated KV record_events = 4;
repeated KV upsert_step_execution_locals = 5;
}
message StepMethodFailedOutput {
StepMethodFailure failure = 1;
}
message StepWaitForCompletedEvent {
StepMethodEventInput input = 1;
StepWaitForCompletedOutput output = 2;
StepMethodEventContext context = 3;
}
message StepWaitForFailedEvent {
StepMethodEventInput input = 1;
StepMethodFailedOutput output = 2;
StepMethodEventContext context = 3;
}
message StepExecuteCompletedEvent {
StepMethodEventInput input = 1;
StepExecuteCompletedOutput output = 2;
StepMethodEventContext context = 3;
}
message StepExecuteFailedEvent {
StepMethodEventInput input = 1;
StepMethodFailedOutput output = 2;
StepMethodEventContext context = 3;
}
// Successful RPC history projection. Updates include input/output; signals include
// them only when configured.
message RpcExecutionCompletedEvent {
string rpc_name = 1;
Value input = 2;
Value output = 3;
StepDecision step_decision = 4;
repeated AttributeWrite upsert_attributes = 5;
repeated KV record_events = 6;
repeated ChannelMessage publish_to_channel = 7;
bool is_set_attribute_api = 8;
}
message ChannelExternalPublishEvent {
repeated ChannelMessage messages = 1;
}
message WaitForHistoryEventRequest {
string flow_id = 1;
string run_id = 2;
int64 next_internal_event_id = 3;
}
message WaitForHistoryEventResponse {
bool event_available = 1;
int64 available_internal_event_id = 2;
FlowStatus flow_status = 3;
}
enum ActiveStepPhase {
ACTIVE_STEP_PHASE_UNSPECIFIED = 0;
ACTIVE_STEP_PHASE_ACTIVE = 1;
ACTIVE_STEP_PHASE_WAITING = 2;
}
message ActiveStepExecutionState {
string step_execution_id = 1;
string from_step_execution_id = 2;
string step_type = 3;
ActiveStepPhase phase = 4;
StepMovement movement = 5;
WaitingConditionState waiting_condition = 6;
StepExecutionCompletedConditions completed_conditions = 7;
repeated KV step_execution_locals = 8;
repeated TimerInfo timers = 9;
StepMethodFailure last_failure_info = 10;
}
message GetFlowStateRequest {
string flow_id = 1;
string run_id = 2;
}
message GetFlowStateResponse {
FlowConfig flow_config = 1;
repeated KV attributes = 2;
repeated ActiveStepExecutionState active_step_executions = 3;
repeated StepMovement queued_steps = 4;
map<string, ChannelValues> pending_channel_messages = 5;
repeated StepCompletionOutput completed_steps = 6;
}
enum FlowResetType {
FLOW_RESET_TYPE_UNSPECIFIED = 0;
FLOW_RESET_TYPE_BEGINNING = 1;
FLOW_RESET_TYPE_HISTORY_EVENT_TIME = 2;
FLOW_RESET_TYPE_STEP_TYPE = 3;
FLOW_RESET_TYPE_STEP_EXECUTION_ID = 4;
}
enum FlowResetStepMethod {
FLOW_RESET_STEP_METHOD_UNSPECIFIED = 0;
FLOW_RESET_STEP_METHOD_WAIT_FOR = 1;
FLOW_RESET_STEP_METHOD_EXECUTE = 2;
}
message ResetFlowRequest {
string flow_id = 1;
string run_id = 2;
FlowResetType reset_type = 3;
string reason = 4;
string history_event_time = 5;
string step_type = 6;
string step_execution_id = 7;
// Skips reapplying RPCs, Channel publications, and Attribute writes after the reset point.
bool skip_writes_reapply = 8;
FlowResetStepMethod step_method = 9;
}
message ResetFlowResponse {
string run_id = 1;
}
message InvokeRPCRequest {
string flow_id = 1;
// Targets this run when set.
string run_id = 2;
string rpc_name = 3;
Value input = 4;
int32 timeout_seconds = 5;
// Acquire exclusive lock on these attribute keys for the RPC's
// read-modify-write. Empty means no locking and uses the configured RPC path.
repeated string lock_attribute_keys = 6;
// Per-call UUID, SDK-generated and future-overridable; identical retries reuse it. Temporal Update paths use it as the run-scoped Update ID; Continue-as-New resets scope.
string request_id = 7;
}
message InvokeRPCResponse {
Value output = 1;
}
message SkipTimerRequest {
string flow_id = 1;
string run_id = 2;
string step_execution_id = 3;
string timer_condition_id = 4;
optional int32 timer_condition_index = 5;
}
message UpdateFlowConfigRequest {
string flow_id = 1;
string run_id = 2;
FlowConfig flow_config = 3;
}
message WaitForStepCompletionRequest {
string flow_id = 1;
// Identifies a step execution by type and its per-type execution number.
string step_type = 2;
string step_execution_number = 3;
int32 wait_time_seconds = 5;
// Required per-call UUID is SDK-generated and future-overridable; identical retries reuse it. Server forwards run-scoped UpdateID; Continue-as-New resets scope.
string request_id = 6;
}
message WaitForStepCompletionResponse {}
message WaitForAttributeRequest {
string flow_id = 1;
string run_id = 2;
WaitForAttributeCondition condition = 3;
// Zero/omit checks once; positive waits until match or timeout.
int32 wait_time_seconds = 4;
// Required per-call UUID is SDK-generated and future-overridable; identical retries reuse it. Server forwards run-scoped UpdateID; Continue-as-New resets scope.
string request_id = 5;
}
message WaitForAttributeCondition {
oneof kind {
WaitForAttributeEqual equal = 1;
}
}
message WaitForAttributeEqual {
string key = 1;
Value value = 2;
}
message TriggerContinueAsNewRequest {
string flow_id = 1;
string run_id = 2;
}
message HealthInfo {
string condition = 1;
string hostname = 2;
int32 duration = 3;
}
message ServiceErrorResponse {
string detail = 1;
ErrorSubStatus sub_status = 2;
string original_worker_error_detail = 3;
string original_worker_error_type = 4;
int32 original_worker_error_status = 5;
string original_worker_error_stack_trace = 6;
}
enum ErrorSubStatus {
ERROR_SUB_STATUS_UNSPECIFIED = 0;
ERROR_SUB_STATUS_UNCATEGORIZED = 1;
ERROR_SUB_STATUS_FLOW_ALREADY_STARTED = 2;
ERROR_SUB_STATUS_FLOW_NOT_EXISTS = 3;
ERROR_SUB_STATUS_WORKER_API_ERROR = 4;
ERROR_SUB_STATUS_LONG_POLL_TIME_OUT = 5;
}
message WorkerErrorResponse {
string detail = 1;
string error_type = 2;
string stack_trace = 3;
int32 retry_after_seconds = 4;
}
message InternalActivityError {
string server_detail = 1;
int32 worker_grpc_status = 2;
InternalWorkerError worker_error = 3;
}
message InternalWorkerError {
string detail = 1;
string error_type = 2;
string stack_trace = 3;
}
message InternalFlowError {
oneof failure {
string server_detail = 1;
InternalActivityError activity_error = 2;
}
}
message ChannelInfo {
int32 size = 1;
}
message InvokeWaitForMethodRequest {
Context context = 1;
string flow_type = 2;
string step_type = 3;
Value step_input = 4;
repeated KV attributes = 5;
}
message InvokeWaitForMethodResponse {
// Server-populated lineage input for local activity history.
LocalActivityMetadata local_activity_metadata = 1;
repeated AttributeWrite upsert_attributes = 2;
WaitingCondition waiting_condition = 3;
repeated KV upsert_step_exe_locals = 4;
repeated KV record_events = 5;
repeated ChannelMessage publish_to_channel = 6;
}
message InvokeExecuteMethodRequest {
Context context = 1;
string flow_type = 2;
string step_type = 3;
Value step_input = 4;
repeated KV attributes = 5;
repeated KV step_exe_locals = 6;
ConditionResults condition_results = 7;
}
message InvokeExecuteMethodResponse {
// Server-populated lineage input for local activity history.
LocalActivityMetadata local_activity_metadata = 1;
StepDecision step_decision = 2;
repeated AttributeWrite upsert_attributes = 3;
repeated KV record_events = 4;
repeated KV upsert_step_exe_locals = 5;
repeated ChannelMessage publish_to_channel = 6;
}
message InvokeWorkerRPCRequest {
Context context = 1;
string flow_type = 2;
string rpc_name = 3;
Value input = 4;
repeated KV attributes = 5;
map<string, ChannelInfo> channel_infos = 6;
}
message InvokeWorkerRPCResponse {
Value output = 1;
StepDecision step_decision = 2;
repeated AttributeWrite upsert_attributes = 3;
repeated KV record_events = 4;
repeated ChannelMessage publish_to_channel = 6;
}
message StepDecision {
repeated StepMovement next_steps = 1;
CloseDecision close_decision = 2;
repeated string cancel_step_types = 3;
repeated string cancel_sibling_step_types = 4;
}
enum CloseDecisionType {
CLOSE_DECISION_TYPE_UNSPECIFIED = 0;
CLOSE_DECISION_TYPE_FORCE_COMPLETE_ON_CHANNELS_EMPTY = 1;
CLOSE_DECISION_TYPE_GRACEFUL_COMPLETE = 2;
CLOSE_DECISION_TYPE_FORCE_COMPLETE = 3;
CLOSE_DECISION_TYPE_FORCE_FAIL = 4;
CLOSE_DECISION_TYPE_DEAD_END = 5;
}
message CloseDecision {
CloseDecisionType close_decision_type = 1;
repeated string conditional_channel_names = 2;
Value close_input = 3;
}
message StepMovement {
string step_type = 1;
Value step_input = 2;
StepOptions step_options = 3;
// Server-owned scheduling source; workers must leave this empty.
string from_step_execution_id_internal_only = 4;
// Server-owned error passed only to an Execute failure recovery Step.
RecoveryErrorInfo recovery_error_internal_only = 5;
}
enum WaitingConditionType {
WAITING_CONDITION_TYPE_UNSPECIFIED = 0;
WAITING_CONDITION_TYPE_ALL_COMPLETED = 1;
WAITING_CONDITION_TYPE_ANY_COMPLETED = 2;
WAITING_CONDITION_TYPE_ANY_COMBINATION_COMPLETED = 3;
}
message ConditionCombination {
repeated string condition_ids = 1;
}
message WaitingCondition {
WaitingConditionType waiting_condition_type = 1;
repeated TimerCondition timer_conditions = 2;
repeated ChannelCondition channel_conditions = 3;
repeated ConditionCombination condition_combinations = 4;
repeated SubFlowCondition sub_flow_conditions = 5;
}
message WaitingConditionState {
WaitingConditionType waiting_condition_type = 1;
repeated TimerCondition timer_conditions = 2;
repeated ChannelCondition channel_conditions = 3;
repeated ConditionCombination condition_combinations = 4;
repeated SubFlowConditionState sub_flow_conditions = 5;
}
enum SubFlowReusePolicy {
SUB_FLOW_REUSE_POLICY_UNSPECIFIED = 0;
SUB_FLOW_REUSE_POLICY_ATTACH = 1;
SUB_FLOW_REUSE_POLICY_RESTART_IF_PREVIOUS_EXITS_ABNORMALLY = 2;
SUB_FLOW_REUSE_POLICY_ALWAYS_RESTART = 3;
}
message SubFlowOptions {
SubFlowReusePolicy reuse_policy = 1;
int32 flow_timeout_seconds = 2;
int32 flow_start_delay_seconds = 3;
FlowRetryPolicy retry_policy = 4;
repeated AttributeWrite attributes = 5;
FlowConfig flow_config_override = 6;
FlowTimeoutPolicy flow_timeout_policy = 7;
}
message SubFlowCondition {
// Optional unless waiting_condition_type is ANY_COMBINATION_COMPLETED.
string condition_id = 1;
string sub_flow_type = 2;
string start_step_type = 3;
Value step_input = 4;
StepOptions step_options = 5;
SubFlowOptions options = 6;
int32 sub_flow_index = 7;
}
message SubFlowConditionState {
string condition_id = 1;
}
message TimerCondition {
// Optional unless waiting_condition_type is ANY_COMBINATION_COMPLETED.
string condition_id = 1;
// Worker-relative delay; interpreter clears this after converted to firing_unix_timestamp_seconds.
int64 duration_seconds = 2;
// Interpreter-normalized deadline; workers leave this zero.
int64 firing_unix_timestamp_seconds = 3;
}
message ChannelCondition {
// Optional unless waiting_condition_type is ANY_COMBINATION_COMPLETED.
string condition_id = 1;
string channel_name = 2;
// Both omitted means exact one. Omitted at_least means zero; omitted at_most means unbounded.
optional int32 at_least = 3;
optional int32 at_most = 4;
}
message ConditionResults {
repeated ChannelResult channel_results = 1;
repeated TimerResult timer_results = 2;
bool wait_for_failed = 3;
repeated FlowResult sub_flow_results = 4;
}
enum ConditionStatus {
CONDITION_STATUS_UNSPECIFIED = 0;
CONDITION_STATUS_WAITING = 1;
CONDITION_STATUS_COMPLETED = 2;
}
message TimerResult {
string condition_id = 1;
ConditionStatus condition_status = 2;
}
message ChannelResult {
string condition_id = 1;
ConditionStatus condition_status = 2;
string channel_name = 3;
repeated Value values = 4;
}
// --- Continue-as-new dump (InternalService) ---
message ContinueAsNewDumpRequest {
string flow_id = 1;
string run_id = 2;
int32 page_num = 3;
int32 page_size_in_bytes = 4;
}
message ContinueAsNewDumpResponse {
// Slice of the deterministic proto-marshaled ContinueAsNewDump.
bytes page_content = 1;
int32 page_num = 2;
int32 total_pages = 3;
// Hash of the full marshaled dump; guards snapshot drift across pages.
string checksum = 4;
}
message ChannelValues {
repeated Value values = 1;
}
message StepExecutionCompletedConditions {
map<int32, InternalTimerStatus> completed_timer_conditions = 1;
map<int32, FlowResult> completed_sub_flow_results = 2;
}
message StepExecutionResumeInfo {
string step_execution_id = 1;
StepMovement step = 2;
StepExecutionCompletedConditions completed_conditions = 3;
WaitingConditionState waiting_condition = 4;
repeated KV step_exe_locals = 5;
}
message StepExecutionCounterInfo {
map<string, int32> step_type_started_count = 1;
map<string, int32> step_type_currently_executing_count = 2;
int32 total_currently_executing_count = 3;
map<string, StepExecutionNumbers> step_active_execution_nums = 4;
}
message StaleSkipTimer {
string step_execution_id = 1;
string timer_condition_id = 2;
int32 timer_condition_index = 3;
}
message ContinueAsNewDump {
repeated StepMovement steps_to_start_from_beginning = 1;
repeated StepExecutionResumeInfo step_executions_to_resume = 2;
map<string, ChannelValues> channel_received = 3;
StepExecutionCounterInfo counter_info = 4;
repeated StepCompletionOutput step_outputs = 5;
repeated StaleSkipTimer stale_skip_timers = 6;
// Stored values only; index metadata remains in backend search attributes.
repeated KV attributes = 7;
repeated AttributeSyncItem pending_attribute_sync_items = 8;
}
// --- Internal serializable types (history / query / activity) ---
// Serialized by Temporal/Cadence DataConverters as binary protobuf. Not FlowService RPCs.
enum InternalTimerStatus {
INTERNAL_TIMER_STATUS_UNSPECIFIED = 0;
INTERNAL_TIMER_STATUS_PENDING = 1;
INTERNAL_TIMER_STATUS_FIRED = 2;
INTERNAL_TIMER_STATUS_SKIPPED = 3;
}
enum UpdateErrorType {
UPDATE_ERROR_TYPE_UNSPECIFIED = 0;
UPDATE_ERROR_TYPE_CONTINUE_AS_NEW_PREEMPTED = 1;
UPDATE_ERROR_TYPE_INVALID_ARGUMENT = 2;
UPDATE_ERROR_TYPE_FAILED_PRECONDITION = 3;
UPDATE_ERROR_TYPE_DEADLINE_EXCEEDED = 4;
UPDATE_ERROR_TYPE_RPC_ACQUIRE_LOCK_FAILURE = 5;
UPDATE_ERROR_TYPE_SERVER_INTERNAL = 6;
}
message ContinueAsNewInput {
string previous_internal_run_id = 1;
}
message InterpreterWorkflowInput {
string flow_type = 1;
int32 configured_flow_timeout_seconds = 2;
FlowTimeoutPolicy flow_timeout_policy = 3;
string start_step_type = 4;
Value step_input = 5;
StepOptions step_options = 6;
repeated AttributeWrite init_attributes = 7;
FlowConfig config = 8;
// When true, ignore start_step_type / step_input / step_options / init_attributes.
bool is_resume_from_continue_as_new = 9;
ContinueAsNewInput continue_as_new_input = 10;
}
message InterpreterWorkflowOutput {
repeated StepCompletionOutput step_completion_outputs = 1;
}
message BlobStoreCleanupWorkflowInput {
string store_id = 1;
}
message BlobStoreCleanupWorkflowOutput {
int32 total_deleted = 1;
}
message InvokeWaitForMethodActivityInput {
WorkerTarget worker_target = 1;
InvokeWaitForMethodRequest request = 2;
}
message InvokeWaitForMethodActivityOutput {
InvokeWaitForMethodResponse response = 1;
}
message InvokeExecuteMethodActivityInput {
WorkerTarget worker_target = 1;
InvokeExecuteMethodRequest request = 2;
}
message RecoveryErrorInfo {
string detail = 1;
string error_type = 2;
}
message InternalLocalStepActivityFailure {
LocalActivityMetadata local_activity_metadata = 1;
int64 first_attempt_timestamp = 2;
StepMethodOptions method_options = 3;
int32 attempt = 4;
InternalActivityError activity_error = 5;
}
message InvokeExecuteMethodActivityOutput {
InvokeExecuteMethodResponse response = 1;
}
message DumpFlowForContinueAsNewActivityInput {
ContinueAsNewDumpRequest request = 1;
}
message DumpFlowForContinueAsNewActivityOutput {
ContinueAsNewDumpResponse response = 1;
}
message InvokeWorkerRPCActivityInput {
PrepareRpcQueryResponse rpc_prep = 1;
InvokeRPCRequest request = 2;
}
message InvokeWorkerRPCActivityOutput {
InvokeWorkerRPCResponse response = 1;
// Correlates this local Activity result with its InvokeRpc Update.
string request_id = 2;
}
message CleanupBlobStoreActivityInput {
string store_id = 1;
}
message CleanupBlobStoreActivityOutput {
int32 total_deleted = 1;
}
message AttributeSyncItem {
string config_name = 1;
string key = 2;
Value value = 3;
}
message SyncAttributeBatchActivityInput {
string flow_id = 1;
string config_name = 2;
repeated AttributeSyncItem items = 3;
}
message StartSubFlowActivityInput {
SubFlowCondition condition = 1;
FlowConfig parent_flow_config = 2;
// Source Step; activity context supplies parent Flow and run IDs.
string parent_step_execution_id = 3;
}
message StartSubFlowActivityOutput {
FlowResult immediate_flow_result = 1;
}
message SubFlowCompletionSignalRequest {
string sub_flow_id = 1;
FlowResult flow_result = 2;
}
enum SubFlowCompletionDeliveryStatus {
SUB_FLOW_COMPLETION_DELIVERY_STATUS_UNSPECIFIED = 0;
SUB_FLOW_COMPLETION_DELIVERY_STATUS_DELIVERED = 1;
SUB_FLOW_COMPLETION_DELIVERY_STATUS_PARENT_CLOSED_OR_NOT_FOUND = 2;
}
message ReportSubFlowCompletionActivityInput {
string parent_flow_id = 1;
SubFlowCompletionSignalRequest request = 2;
}
message ReportSubFlowCompletionActivityOutput {
SubFlowCompletionDeliveryStatus status = 1;
}
message ExecuteRpcSignalRequest {
Value rpc_input = 1;
Value rpc_output = 2;
repeated AttributeWrite upsert_attributes = 3;
StepDecision step_decision = 4;
repeated KV record_events = 5;
repeated ChannelMessage publish_to_channel = 6;
bool is_set_attribute_api = 7;
}
message SkipTimerSignalRequest {
string step_execution_id = 1;
string timer_condition_id = 2;
int32 timer_condition_index = 3;
}
message StopFlowSignalRequest {
StopType stop_type = 1;
string reason = 2;
}
message GetAttributesQueryRequest {
repeated string keys = 1;
bool all_keys = 2;
}
message GetAttributesQueryResponse {
repeated KV attributes = 1;
}
message PrepareRpcQueryRequest {
repeated string lock_attribute_keys = 1;
}
message PrepareRpcQueryResponse {
repeated KV attributes = 1;
string run_id = 2;
int64 flow_started_timestamp = 3;
string flow_type = 4;
WorkerTarget worker_target = 5;
map<string, ChannelInfo> channel_infos = 6;
}
message TimerInfo {
// Empty when the timer has no condition id.
string condition_id = 1;
int64 firing_unix_timestamp_seconds = 2;
InternalTimerStatus status = 3;
}
message TimerInfoList {
repeated TimerInfo timers = 1;
}
message GetCurrentTimerInfosQueryResponse {
// Key is step_execution_id.
map<string, TimerInfoList> step_execution_current_timer_infos = 1;
}
message GetScheduledGreedyTimerTimesQueryResponse {
repeated TimerInfo pending_scheduled = 1;
}
message DebugDumpResponse {
FlowConfig config = 1;
ContinueAsNewDump snapshot = 2;
repeated int64 firing_timers_unix_timestamps = 3;
repeated ActiveStepExecutionState active_step_executions = 4;
}
// Sync-update InvokeRPC handler result when response and error are multiplexed.
message InvokeRpcUpdateResult {
InvokeRPCResponse response = 1;
}
message StepExecutionNumbers {
repeated int32 numbers = 1;
}