use std::time::Duration;
use inquire::error::InquireResult;
use inquire::validator::Validation;
use inquire::Text;
use crate::actions::h3::Action;
use crate::actions::h3::StreamEvent;
use crate::actions::h3::StreamEventType;
use crate::actions::h3::WaitType;
use super::prompt_stream_id;
use super::squish_suggester;
use super::validate_wait_period;
use super::SuggestionResult;
const DURATION: &str = "duration";
const HEADERS: &str = "headers";
const DATA: &str = "data";
const FINISHED: &str = "stream finished";
pub fn prompt_wait() -> InquireResult<Action> {
let wait_type = Text::new("wait type:")
.with_autocomplete(&wait_type_suggestor)
.with_validator(wait_type_validator)
.prompt()?;
let actual = match wait_type.as_str() {
DURATION => Some(prompt_wait_period()),
t @ (HEADERS | DATA | FINISHED) => Some(prompt_stream_wait(t)),
_ => None,
};
let action = Action::Wait {
wait_type: actual.unwrap()?,
};
Ok(action)
}
fn wait_type_suggestor(val: &str) -> SuggestionResult<Vec<String>> {
let suggestions = [DURATION, HEADERS, DATA, FINISHED];
squish_suggester(&suggestions, val)
}
fn wait_type_validator(wait_type: &str) -> SuggestionResult<Validation> {
match wait_type {
DURATION | HEADERS | DATA | FINISHED => Ok(Validation::Valid),
_ => Ok(Validation::Invalid(
inquire::validator::ErrorMessage::Default,
)),
}
}
fn prompt_stream_wait(stream_wait_type: &str) -> InquireResult<WaitType> {
let stream_id = prompt_stream_id()?;
let event_type = if let HEADERS = stream_wait_type {
Some(StreamEventType::Headers)
} else if let DATA = stream_wait_type {
Some(StreamEventType::Data)
} else if let FINISHED = stream_wait_type {
Some(StreamEventType::Finished)
} else {
None
}
.unwrap();
Ok(WaitType::StreamEvent(StreamEvent {
stream_id,
event_type,
}))
}
pub fn prompt_wait_period() -> InquireResult<WaitType> {
let period = Text::new("wait period (ms):")
.with_validator(validate_wait_period)
.prompt()?;
let period = Duration::from_millis(period.parse::<u64>().unwrap());
Ok(WaitType::WaitDuration(period))
}