1/*
2 * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
3 * SPDX-License-Identifier: Apache-2.0
4 */
56use super::Throughput;
7use aws_smithy_runtime_api::client::stalled_stream_protection::{
8 StalledStreamProtectionConfig, DEFAULT_GRACE_PERIOD,
9};
10use std::time::Duration;
1112/// A collection of options for configuring a [`MinimumThroughputBody`](super::MinimumThroughputDownloadBody).
13#[derive(Debug, Clone)]
14pub struct MinimumThroughputBodyOptions {
15/// The minimum throughput that is acceptable.
16minimum_throughput: Throughput,
1718/// The 'grace period' after which the minimum throughput will be enforced.
19 ///
20 /// If this is set to 0, the minimum throughput will be enforced immediately.
21 ///
22 /// If this is set to a positive value, whenever throughput is below the minimum throughput,
23 /// a timer is started. If the timer expires before throughput rises above the minimum,
24 /// an error is emitted.
25 ///
26 /// It is recommended to set this to a small value (e.g. 200ms) to avoid issues during
27 /// stream-startup.
28grace_period: Duration,
2930/// The period of time to consider when computing the throughput
31 ///
32 /// This SHOULD be longer than the check interval, or stuck-streams may evade detection.
33check_window: Duration,
34}
3536impl MinimumThroughputBodyOptions {
37/// Create a new builder.
38pub fn builder() -> MinimumThroughputBodyOptionsBuilder {
39 Default::default()
40 }
4142/// Convert this struct into a builder.
43pub fn to_builder(self) -> MinimumThroughputBodyOptionsBuilder {
44 MinimumThroughputBodyOptionsBuilder::new()
45 .minimum_throughput(self.minimum_throughput)
46 .grace_period(self.grace_period)
47 }
4849/// The throughput check grace period.
50 ///
51 /// If throughput is below the minimum for longer than this period, an error is emitted.
52 ///
53 /// If this is set to 0, the minimum throughput will be enforced immediately.
54pub fn grace_period(&self) -> Duration {
55self.grace_period
56 }
5758/// The minimum acceptable throughput
59pub fn minimum_throughput(&self) -> Throughput {
60self.minimum_throughput
61 }
6263pub(crate) fn check_window(&self) -> Duration {
64self.check_window
65 }
6667/// Not used. Always returns `Duration::from_millis(500)`.
68#[deprecated(note = "No longer used. Always returns Duration::from_millis(500)")]
69pub fn check_interval(&self) -> Duration {
70 Duration::from_millis(500)
71 }
72}
7374const DEFAULT_MINIMUM_THROUGHPUT: Throughput = Throughput {
75 bytes_read: 1,
76 per_time_elapsed: Duration::from_secs(1),
77};
7879const DEFAULT_CHECK_WINDOW: Duration = Duration::from_secs(1);
8081impl Default for MinimumThroughputBodyOptions {
82fn default() -> Self {
83Self {
84 minimum_throughput: DEFAULT_MINIMUM_THROUGHPUT,
85 grace_period: DEFAULT_GRACE_PERIOD,
86 check_window: DEFAULT_CHECK_WINDOW,
87 }
88 }
89}
9091/// A builder for [`MinimumThroughputBodyOptions`]
92#[derive(Debug, Default, Clone)]
93pub struct MinimumThroughputBodyOptionsBuilder {
94 minimum_throughput: Option<Throughput>,
95 check_window: Option<Duration>,
96 grace_period: Option<Duration>,
97}
9899impl MinimumThroughputBodyOptionsBuilder {
100/// Create a new `MinimumThroughputBodyOptionsBuilder`.
101pub fn new() -> Self {
102 Default::default()
103 }
104105/// Set the amount of time that throughput my fall below minimum before an error is emitted.
106 ///
107 /// If throughput rises above the minimum, the timer is reset.
108pub fn grace_period(mut self, grace_period: Duration) -> Self {
109self.set_grace_period(Some(grace_period));
110self
111}
112113/// Set the amount of time that throughput my fall below minimum before an error is emitted.
114 ///
115 /// If throughput rises above the minimum, the timer is reset.
116pub fn set_grace_period(&mut self, grace_period: Option<Duration>) -> &mut Self {
117self.grace_period = grace_period;
118self
119}
120121/// Set the minimum allowable throughput.
122pub fn minimum_throughput(mut self, minimum_throughput: Throughput) -> Self {
123self.set_minimum_throughput(Some(minimum_throughput));
124self
125}
126127/// Set the minimum allowable throughput.
128pub fn set_minimum_throughput(&mut self, minimum_throughput: Option<Throughput>) -> &mut Self {
129self.minimum_throughput = minimum_throughput;
130self
131}
132133/// No longer used. The check interval is now based on the check window (not currently configurable).
134#[deprecated(
135 note = "No longer used. The check interval is now based on the check window (not currently configurable). Open an issue if you need to configure the check window."
136)]
137pub fn check_interval(self, _check_interval: Duration) -> Self {
138self
139}
140141/// No longer used. The check interval is now based on the check window (not currently configurable).
142#[deprecated(
143 note = "No longer used. The check interval is now based on the check window (not currently configurable). Open an issue if you need to configure the check window."
144)]
145pub fn set_check_interval(&mut self, _check_interval: Option<Duration>) -> &mut Self {
146self
147}
148149#[allow(unused)]
150pub(crate) fn check_window(mut self, check_window: Duration) -> Self {
151self.set_check_window(Some(check_window));
152self
153}
154#[allow(unused)]
155pub(crate) fn set_check_window(&mut self, check_window: Option<Duration>) -> &mut Self {
156self.check_window = check_window;
157self
158}
159160/// Build this builder, producing a [`MinimumThroughputBodyOptions`].
161 ///
162 /// Unset fields will be set with defaults.
163pub fn build(self) -> MinimumThroughputBodyOptions {
164 MinimumThroughputBodyOptions {
165 grace_period: self.grace_period.unwrap_or(DEFAULT_GRACE_PERIOD),
166 minimum_throughput: self
167.minimum_throughput
168 .unwrap_or(DEFAULT_MINIMUM_THROUGHPUT),
169 check_window: self.check_window.unwrap_or(DEFAULT_CHECK_WINDOW),
170 }
171 }
172}
173174impl From<StalledStreamProtectionConfig> for MinimumThroughputBodyOptions {
175fn from(value: StalledStreamProtectionConfig) -> Self {
176 MinimumThroughputBodyOptions {
177 grace_period: value.grace_period(),
178 minimum_throughput: DEFAULT_MINIMUM_THROUGHPUT,
179 check_window: DEFAULT_CHECK_WINDOW,
180 }
181 }
182}