dex-protocol 0.2.3

Generated Dex protobuf and gRPC protocol
Documentation
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
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
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
1001
1002
1003
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282
1283
1284
1285
1286
1287
1288
1289
1290
1291
1292
1293
1294
1295
1296
1297
1298
1299
1300
1301
1302
1303
1304
1305
1306
1307
1308
1309
1310
1311
1312
1313
1314
1315
1316
1317
1318
1319
1320
1321
1322
1323
1324
1325
1326
1327
1328
1329
1330
1331
1332
1333
1334
1335
1336
1337
1338
1339
1340
1341
1342
1343
1344
1345
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365
1366
// 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 or Stream Store backend unavailable;
//                       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.
//   WriteStream / ReadStream — independent of Flow existence and lifecycle.
//     Redis failures affect only Stream RPCs. Read timeout → 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 WriteStream(WriteStreamRequest) returns (google.protobuf.Empty);
  rpc ReadStream(ReadStreamRequest) returns (ReadStreamResponse);
  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 Server-configured stores.
  optional AttributeStoreNames attribute_store_names = 6;
}

message AttributeStoreNames {
  repeated string names = 1;
}

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;
}

message WriteStreamRequest {
  string flow_id = 1;
  string flow_type = 2;
  string stream_name = 3;
  int64 stream_capacity_bytes = 4;
  Value value = 5;
  // Client keys must not contain "#"; Step SDKs use `<runID>#<stepExecutionID>`.
  string idempotency_key = 6;
}

message ReadStreamRequest {
  string flow_id = 1;
  string flow_type = 2;
  string stream_name = 3;
  string resume_token = 4;
  int32 wait_time_seconds = 5;
}

message ReadStreamResponse {
  StreamMessage message = 1;
}

message StreamMessage {
  Value value = 1;
  string resume_token = 2;
  google.protobuf.Timestamp created_time = 3;
  string idempotency_key = 4;
}

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;
}