mod action;
#[cfg(test)]
mod test;
pub use action::*;
use crate::{
config::get_configuration,
error::{InquireError, InquireResult},
formatter::{BoolFormatter, DEFAULT_BOOL_FORMATTER},
parser::{BoolParser, DEFAULT_BOOL_PARSER},
terminal::get_default_terminal,
ui::{Backend, CustomTypeBackend, RenderConfig},
CustomType,
};
#[derive(Clone)]
pub struct Confirm<'a> {
pub message: &'a str,
pub starting_input: Option<&'a str>,
pub default: Option<bool>,
pub placeholder: Option<&'a str>,
pub help_message: Option<&'a str>,
pub formatter: BoolFormatter<'a>,
pub parser: BoolParser<'a>,
pub default_value_formatter: BoolFormatter<'a>,
pub error_message: String,
pub render_config: RenderConfig<'a>,
}
impl<'a> Confirm<'a> {
pub const DEFAULT_FORMATTER: BoolFormatter<'a> = DEFAULT_BOOL_FORMATTER;
pub const DEFAULT_PARSER: BoolParser<'a> = DEFAULT_BOOL_PARSER;
pub const DEFAULT_DEFAULT_VALUE_FORMATTER: BoolFormatter<'a> = &|ans| match ans {
true => String::from("Y/n"),
false => String::from("y/N"),
};
pub const DEFAULT_ERROR_MESSAGE: &'a str =
"Invalid answer, try typing 'y' for yes or 'n' for no";
pub fn new(message: &'a str) -> Self {
Self {
message,
starting_input: None,
default: None,
placeholder: None,
help_message: None,
formatter: Self::DEFAULT_FORMATTER,
parser: Self::DEFAULT_PARSER,
default_value_formatter: Self::DEFAULT_DEFAULT_VALUE_FORMATTER,
error_message: String::from(Self::DEFAULT_ERROR_MESSAGE),
render_config: get_configuration(),
}
}
pub fn with_starting_input(mut self, message: &'a str) -> Self {
self.starting_input = Some(message);
self
}
pub fn with_default(mut self, default: bool) -> Self {
self.default = Some(default);
self
}
pub fn with_placeholder(mut self, placeholder: &'a str) -> Self {
self.placeholder = Some(placeholder);
self
}
pub fn with_help_message(mut self, message: &'a str) -> Self {
self.help_message = Some(message);
self
}
pub fn with_formatter(mut self, formatter: BoolFormatter<'a>) -> Self {
self.formatter = formatter;
self
}
pub fn with_parser(mut self, parser: BoolParser<'a>) -> Self {
self.parser = parser;
self
}
pub fn with_error_message(mut self, error_message: &'a str) -> Self {
self.error_message = String::from(error_message);
self
}
pub fn with_default_value_formatter(mut self, formatter: BoolFormatter<'a>) -> Self {
self.default_value_formatter = formatter;
self
}
pub fn with_render_config(mut self, render_config: RenderConfig<'a>) -> Self {
self.render_config = render_config;
self
}
pub fn prompt_skippable(self) -> InquireResult<Option<bool>> {
match self.prompt() {
Ok(answer) => Ok(Some(answer)),
Err(InquireError::OperationCanceled) => Ok(None),
Err(err) => Err(err),
}
}
pub fn prompt(self) -> InquireResult<bool> {
let (input_reader, terminal) = get_default_terminal()?;
let mut backend = Backend::new(input_reader, terminal, self.render_config)?;
self.prompt_with_backend(&mut backend)
}
pub(crate) fn prompt_with_backend<B: CustomTypeBackend>(
self,
backend: &mut B,
) -> InquireResult<bool> {
CustomType::from(self).prompt_with_backend(backend)
}
}
impl<'a> From<&'a str> for Confirm<'a> {
fn from(val: &'a str) -> Self {
Confirm::new(val)
}
}
impl<'a> From<Confirm<'a>> for CustomType<'a, bool> {
fn from(co: Confirm<'a>) -> Self {
Self {
message: co.message,
starting_input: co.starting_input,
default: co.default,
default_value_formatter: co.default_value_formatter,
placeholder: co.placeholder,
help_message: co.help_message,
formatter: co.formatter,
parser: co.parser,
validators: vec![],
error_message: co.error_message,
render_config: co.render_config,
}
}
}