Skip to main content

dex_sdk/
time_travel_options.rs

1// Copyright (c) 2026 Super Durable, Inc.
2//
3// Licensed under the Super Durable Source License 1.0.
4// You may not use this file except in compliance with the License.
5// See the LICENSE file in the repository root.
6//
7// SPDX-License-Identifier: LicenseRef-Super-Durable-1.0
8
9use std::time::SystemTime;
10
11use crate::{Step, StepExecutionId};
12
13#[derive(Clone, Debug)]
14/// Selects a historical point from which [`crate::Client::time_travel`] creates a new run.
15///
16/// Constructors identify exactly one time travel point. Builder methods add an audit reason and control
17/// whether writes are reapplied. Write reapplication defaults to enabled.
18pub struct TimeTravelOptions {
19    pub(crate) point: TimeTravelPoint,
20    pub(crate) reason: Option<String>,
21    pub(crate) skip_writes_reapply: bool,
22}
23
24#[derive(Clone, Debug)]
25pub(crate) enum TimeTravelPoint {
26    Beginning,
27    HistoryEventTime(SystemTime),
28    StepType(&'static str),
29    StepExecution(StepExecutionId, TimeTravelStepMethod),
30}
31
32#[derive(Clone, Copy, Debug)]
33/// Selects the Step method used as a Step execution time travel boundary.
34pub enum TimeTravelStepMethod {
35    /// Reruns WaitFor and everything after it.
36    WaitFor,
37    /// Keeps the WaitFor result and reruns Execute and everything after it.
38    Execute,
39}
40
41impl TimeTravelOptions {
42    /// Resumes before the first workflow-history event.
43    pub fn from_beginning() -> Self {
44        Self::new(TimeTravelPoint::Beginning)
45    }
46
47    /// Resumes at the last eligible history event at or before `event_time`.
48    pub fn from_history_event_time(event_time: SystemTime) -> Self {
49        Self::new(TimeTravelPoint::HistoryEventTime(event_time))
50    }
51
52    /// Resumes before the first execution of the selected Step type.
53    pub fn from_step<SomeStep: Step>(step: &SomeStep) -> Self {
54        Self::new(TimeTravelPoint::StepType(step.step_type()))
55    }
56
57    /// Resumes before one method of the exact Step execution identified by `step_execution`.
58    pub fn from_step_execution(
59        step_execution: StepExecutionId,
60        method: TimeTravelStepMethod,
61    ) -> Self {
62        Self::new(TimeTravelPoint::StepExecution(step_execution, method))
63    }
64
65    /// Adds an operator-facing reason recorded with time travel.
66    pub fn reason(mut self, reason: impl Into<String>) -> Self {
67        self.reason = Some(reason.into());
68        self
69    }
70
71    /// Controls whether later RPCs, Channel publications, and Attribute writes are skipped.
72    pub fn skip_writes_reapply(mut self, skip: bool) -> Self {
73        self.skip_writes_reapply = skip;
74        self
75    }
76
77    fn new(point: TimeTravelPoint) -> Self {
78        Self {
79            point,
80            reason: None,
81            skip_writes_reapply: false,
82        }
83    }
84}