mirror of
https://github.com/Orange-OpenSource/hurl.git
synced 2024-12-01 20:02:19 +03:00
Unify Retry and Repeat types with Count.
This commit is contained in:
parent
25d6716145
commit
1cdc491867
@ -31,7 +31,7 @@ error: Invalid variable type
|
|||||||
| GET http://localhost:8000/unused
|
| GET http://localhost:8000/unused
|
||||||
| ...
|
| ...
|
||||||
29 | repeat: {{count}}
|
29 | repeat: {{count}}
|
||||||
| ^^^^^ expecting integer, actual value is integer <-2>
|
| ^^^^^ expecting integer >= -1, actual value is integer <-2>
|
||||||
|
|
|
|
||||||
|
|
||||||
error: Invalid variable type
|
error: Invalid variable type
|
||||||
@ -58,6 +58,6 @@ error: Invalid variable type
|
|||||||
| GET http://localhost:8000/unused
|
| GET http://localhost:8000/unused
|
||||||
| ...
|
| ...
|
||||||
50 | retry: {{count}}
|
50 | retry: {{count}}
|
||||||
| ^^^^^ expecting integer, actual value is foo
|
| ^^^^^ expecting integer, actual value is string <foo>
|
||||||
|
|
|
|
||||||
|
|
||||||
|
@ -24,7 +24,7 @@ use std::{env, fs, io};
|
|||||||
|
|
||||||
use clap::ArgMatches;
|
use clap::ArgMatches;
|
||||||
use hurl::runner::{Input, Value};
|
use hurl::runner::{Input, Value};
|
||||||
use hurl_core::typing::{Repeat, Retry};
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
use super::variables::{parse as parse_variable, parse_value};
|
use super::variables::{parse as parse_variable, parse_value};
|
||||||
use super::CliOptionsError;
|
use super::CliOptionsError;
|
||||||
@ -366,10 +366,10 @@ pub fn proxy(arg_matches: &ArgMatches) -> Option<String> {
|
|||||||
get::<String>(arg_matches, "proxy")
|
get::<String>(arg_matches, "proxy")
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn repeat(arg_matches: &ArgMatches) -> Option<Repeat> {
|
pub fn repeat(arg_matches: &ArgMatches) -> Option<Count> {
|
||||||
match get::<i32>(arg_matches, "repeat") {
|
match get::<i32>(arg_matches, "repeat") {
|
||||||
Some(-1) => Some(Repeat::Forever),
|
Some(-1) => Some(Count::Infinite),
|
||||||
Some(n) => Some(Repeat::Count(n as usize)),
|
Some(n) => Some(Count::Finite(n as usize)),
|
||||||
None => None,
|
None => None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -378,10 +378,10 @@ pub fn resolves(arg_matches: &ArgMatches) -> Vec<String> {
|
|||||||
get_strings(arg_matches, "resolve").unwrap_or_default()
|
get_strings(arg_matches, "resolve").unwrap_or_default()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn retry(arg_matches: &ArgMatches) -> Option<Retry> {
|
pub fn retry(arg_matches: &ArgMatches) -> Option<Count> {
|
||||||
match get::<i32>(arg_matches, "retry") {
|
match get::<i32>(arg_matches, "retry") {
|
||||||
Some(-1) => Some(Retry::Infinite),
|
Some(-1) => Some(Count::Infinite),
|
||||||
Some(r) => Some(Retry::Finite(r as usize)),
|
Some(r) => Some(Count::Finite(r as usize)),
|
||||||
None => None,
|
None => None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -36,7 +36,7 @@ use hurl_core::ast::Entry;
|
|||||||
use crate::cli;
|
use crate::cli;
|
||||||
use crate::runner::{RunnerOptions, RunnerOptionsBuilder, Value};
|
use crate::runner::{RunnerOptions, RunnerOptionsBuilder, Value};
|
||||||
pub use error::CliOptionsError;
|
pub use error::CliOptionsError;
|
||||||
use hurl_core::typing::{Repeat, Retry};
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
/// Represents the list of all options that can be used in Hurl command line.
|
/// Represents the list of all options that can be used in Hurl command line.
|
||||||
#[derive(Clone, Debug, PartialEq, Eq)]
|
#[derive(Clone, Debug, PartialEq, Eq)]
|
||||||
@ -81,9 +81,9 @@ pub struct CliOptions {
|
|||||||
pub path_as_is: bool,
|
pub path_as_is: bool,
|
||||||
pub progress_bar: bool,
|
pub progress_bar: bool,
|
||||||
pub proxy: Option<String>,
|
pub proxy: Option<String>,
|
||||||
pub repeat: Option<Repeat>,
|
pub repeat: Option<Count>,
|
||||||
pub resolves: Vec<String>,
|
pub resolves: Vec<String>,
|
||||||
pub retry: Option<Retry>,
|
pub retry: Option<Count>,
|
||||||
pub retry_interval: Duration,
|
pub retry_interval: Duration,
|
||||||
pub ssl_no_revoke: bool,
|
pub ssl_no_revoke: bool,
|
||||||
pub tap_file: Option<PathBuf>,
|
pub tap_file: Option<PathBuf>,
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
use hurl_core::typing::Repeat;
|
use hurl_core::typing::Count;
|
||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
|
|
||||||
use crate::runner::{HurlResult, Input, RunnerOptions, Value};
|
use crate::runner::{HurlResult, Input, RunnerOptions, Value};
|
||||||
@ -87,14 +87,14 @@ pub struct JobQueue<'job> {
|
|||||||
/// Current index of the job, referencing the input job list.
|
/// Current index of the job, referencing the input job list.
|
||||||
index: usize,
|
index: usize,
|
||||||
/// Repeat mode of this queue (finite or infinite).
|
/// Repeat mode of this queue (finite or infinite).
|
||||||
repeat: Repeat,
|
repeat: Count,
|
||||||
/// Current index of the repeat.
|
/// Current index of the repeat.
|
||||||
repeat_index: usize,
|
repeat_index: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'job> JobQueue<'job> {
|
impl<'job> JobQueue<'job> {
|
||||||
/// Create a new queue, with a list of `jobs` and a `repeat` mode.
|
/// Create a new queue, with a list of `jobs` and a `repeat` mode.
|
||||||
pub fn new(jobs: &'job [Job], repeat: Repeat) -> Self {
|
pub fn new(jobs: &'job [Job], repeat: Count) -> Self {
|
||||||
JobQueue {
|
JobQueue {
|
||||||
jobs,
|
jobs,
|
||||||
index: 0,
|
index: 0,
|
||||||
@ -108,8 +108,8 @@ impl<'job> JobQueue<'job> {
|
|||||||
/// If queue is created in loop forever mode ([`Repeat::Forever`]), returns `None`.
|
/// If queue is created in loop forever mode ([`Repeat::Forever`]), returns `None`.
|
||||||
pub fn jobs_count(&self) -> Option<usize> {
|
pub fn jobs_count(&self) -> Option<usize> {
|
||||||
match self.repeat {
|
match self.repeat {
|
||||||
Repeat::Count(n) => Some(self.jobs.len() * n),
|
Count::Finite(n) => Some(self.jobs.len() * n),
|
||||||
Repeat::Forever => None,
|
Count::Infinite => None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -130,7 +130,7 @@ impl Iterator for JobQueue<'_> {
|
|||||||
if self.index >= self.jobs.len() {
|
if self.index >= self.jobs.len() {
|
||||||
self.repeat_index = self.repeat_index.checked_add(1).unwrap_or(0);
|
self.repeat_index = self.repeat_index.checked_add(1).unwrap_or(0);
|
||||||
match self.repeat {
|
match self.repeat {
|
||||||
Repeat::Count(n) => {
|
Count::Finite(n) => {
|
||||||
if self.repeat_index >= n {
|
if self.repeat_index >= n {
|
||||||
None
|
None
|
||||||
} else {
|
} else {
|
||||||
@ -138,7 +138,7 @@ impl Iterator for JobQueue<'_> {
|
|||||||
Some(self.job_at(0))
|
Some(self.job_at(0))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Repeat::Forever => {
|
Count::Infinite => {
|
||||||
self.index = 1;
|
self.index = 1;
|
||||||
Some(self.job_at(0))
|
Some(self.job_at(0))
|
||||||
}
|
}
|
||||||
@ -155,7 +155,7 @@ mod tests {
|
|||||||
use crate::parallel::job::{Job, JobQueue};
|
use crate::parallel::job::{Job, JobQueue};
|
||||||
use crate::runner::{Input, RunnerOptionsBuilder};
|
use crate::runner::{Input, RunnerOptionsBuilder};
|
||||||
use crate::util::logger::LoggerOptionsBuilder;
|
use crate::util::logger::LoggerOptionsBuilder;
|
||||||
use hurl_core::typing::Repeat;
|
use hurl_core::typing::Count;
|
||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
|
|
||||||
fn new_job(file: &str, index: usize) -> Job {
|
fn new_job(file: &str, index: usize) -> Job {
|
||||||
@ -179,7 +179,7 @@ mod tests {
|
|||||||
new_job("c.hurl", 2),
|
new_job("c.hurl", 2),
|
||||||
];
|
];
|
||||||
|
|
||||||
let mut queue = JobQueue::new(&jobs, Repeat::Count(2));
|
let mut queue = JobQueue::new(&jobs, Count::Finite(2));
|
||||||
|
|
||||||
assert_eq!(queue.next(), Some(new_job("a.hurl", 0)));
|
assert_eq!(queue.next(), Some(new_job("a.hurl", 0)));
|
||||||
assert_eq!(queue.next(), Some(new_job("b.hurl", 1)));
|
assert_eq!(queue.next(), Some(new_job("b.hurl", 1)));
|
||||||
@ -196,7 +196,7 @@ mod tests {
|
|||||||
fn input_queue_is_infinite() {
|
fn input_queue_is_infinite() {
|
||||||
let jobs = [new_job("foo.hurl", 0)];
|
let jobs = [new_job("foo.hurl", 0)];
|
||||||
|
|
||||||
let mut queue = JobQueue::new(&jobs, Repeat::Forever);
|
let mut queue = JobQueue::new(&jobs, Count::Infinite);
|
||||||
assert_eq!(queue.next(), Some(new_job("foo.hurl", 0)));
|
assert_eq!(queue.next(), Some(new_job("foo.hurl", 0)));
|
||||||
assert_eq!(queue.next(), Some(new_job("foo.hurl", 1)));
|
assert_eq!(queue.next(), Some(new_job("foo.hurl", 1)));
|
||||||
assert_eq!(queue.next(), Some(new_job("foo.hurl", 2)));
|
assert_eq!(queue.next(), Some(new_job("foo.hurl", 2)));
|
||||||
|
@ -16,7 +16,7 @@
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
use hurl_core::error::{DisplaySourceError, OutputFormat};
|
use hurl_core::error::{DisplaySourceError, OutputFormat};
|
||||||
use hurl_core::typing::Repeat;
|
use hurl_core::typing::Count;
|
||||||
use std::sync::mpsc::{Receiver, Sender};
|
use std::sync::mpsc::{Receiver, Sender};
|
||||||
use std::sync::{mpsc, Arc, Mutex};
|
use std::sync::{mpsc, Arc, Mutex};
|
||||||
|
|
||||||
@ -53,7 +53,7 @@ pub struct ParallelRunner {
|
|||||||
/// Output type for each completed job on standard output.
|
/// Output type for each completed job on standard output.
|
||||||
output_type: OutputType,
|
output_type: OutputType,
|
||||||
/// Repeat mode for the runner: infinite or finite.
|
/// Repeat mode for the runner: infinite or finite.
|
||||||
repeat: Repeat,
|
repeat: Count,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Represents a worker's state.
|
/// Represents a worker's state.
|
||||||
@ -106,7 +106,7 @@ impl ParallelRunner {
|
|||||||
pub fn new(
|
pub fn new(
|
||||||
workers_count: usize,
|
workers_count: usize,
|
||||||
output_type: OutputType,
|
output_type: OutputType,
|
||||||
repeat: Repeat,
|
repeat: Count,
|
||||||
test: bool,
|
test: bool,
|
||||||
progress_bar: bool,
|
progress_bar: bool,
|
||||||
color: bool,
|
color: bool,
|
||||||
|
@ -28,7 +28,7 @@ use hurl::runner::{HurlResult, Input, Output};
|
|||||||
use hurl::util::term::{Stdout, WriteMode};
|
use hurl::util::term::{Stdout, WriteMode};
|
||||||
use hurl::{output, parallel, runner};
|
use hurl::{output, parallel, runner};
|
||||||
use hurl_core::error::{DisplaySourceError, OutputFormat};
|
use hurl_core::error::{DisplaySourceError, OutputFormat};
|
||||||
use hurl_core::typing::Repeat;
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
/// Runs Hurl `files` sequentially, given a current directory and command-line options (see
|
/// Runs Hurl `files` sequentially, given a current directory and command-line options (see
|
||||||
/// [`crate::cli::options::CliOptions`]). This function returns a list of [`HurlRun`] results or
|
/// [`crate::cli::options::CliOptions`]). This function returns a list of [`HurlRun`] results or
|
||||||
@ -40,7 +40,7 @@ pub fn run_seq(
|
|||||||
) -> Result<Vec<HurlRun>, CliError> {
|
) -> Result<Vec<HurlRun>, CliError> {
|
||||||
let mut runs = vec![];
|
let mut runs = vec![];
|
||||||
|
|
||||||
let repeat = options.repeat.unwrap_or_default();
|
let repeat = options.repeat.unwrap_or(Count::Finite(1));
|
||||||
let queue = InputQueue::new(files, repeat);
|
let queue = InputQueue::new(files, repeat);
|
||||||
|
|
||||||
// When dumped HTTP responses, we truncate existing output file on first save, then append
|
// When dumped HTTP responses, we truncate existing output file on first save, then append
|
||||||
@ -165,8 +165,8 @@ pub fn run_par(
|
|||||||
// We're going to use the right numbers of workers. We don't need to use more workers than there
|
// We're going to use the right numbers of workers. We don't need to use more workers than there
|
||||||
// are input files (repeat option act as if we're dealing with a multiplied number of files)
|
// are input files (repeat option act as if we're dealing with a multiplied number of files)
|
||||||
let workers_count = match options.repeat {
|
let workers_count = match options.repeat {
|
||||||
Some(Repeat::Count(n)) => min(files.len() * n, workers_count),
|
Some(Count::Finite(n)) => min(files.len() * n, workers_count),
|
||||||
Some(Repeat::Forever) => workers_count,
|
Some(Count::Infinite) => workers_count,
|
||||||
None => min(files.len(), workers_count),
|
None => min(files.len(), workers_count),
|
||||||
};
|
};
|
||||||
let variables = &options.variables;
|
let variables = &options.variables;
|
||||||
@ -188,7 +188,7 @@ pub fn run_par(
|
|||||||
let mut runner = ParallelRunner::new(
|
let mut runner = ParallelRunner::new(
|
||||||
workers_count,
|
workers_count,
|
||||||
output_type,
|
output_type,
|
||||||
options.repeat.unwrap_or_default(),
|
options.repeat.unwrap_or(Count::Finite(1)),
|
||||||
options.test,
|
options.test,
|
||||||
options.progress_bar,
|
options.progress_bar,
|
||||||
options.color,
|
options.color,
|
||||||
@ -233,14 +233,14 @@ pub struct InputQueue<'input> {
|
|||||||
/// Current index of the input, referencing the input list.
|
/// Current index of the input, referencing the input list.
|
||||||
index: usize,
|
index: usize,
|
||||||
/// Repeat mode of this queue (finite or infinite).
|
/// Repeat mode of this queue (finite or infinite).
|
||||||
repeat: Repeat,
|
repeat: Count,
|
||||||
/// Current index of the repeat.
|
/// Current index of the repeat.
|
||||||
repeat_index: usize,
|
repeat_index: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'input> InputQueue<'input> {
|
impl<'input> InputQueue<'input> {
|
||||||
/// Create a new queue, with a list of `inputs` and a `repeat` mode.
|
/// Create a new queue, with a list of `inputs` and a `repeat` mode.
|
||||||
pub fn new(inputs: &'input [Input], repeat: Repeat) -> Self {
|
pub fn new(inputs: &'input [Input], repeat: Count) -> Self {
|
||||||
InputQueue {
|
InputQueue {
|
||||||
inputs,
|
inputs,
|
||||||
index: 0,
|
index: 0,
|
||||||
@ -262,7 +262,7 @@ impl Iterator for InputQueue<'_> {
|
|||||||
if self.index >= self.inputs.len() {
|
if self.index >= self.inputs.len() {
|
||||||
self.repeat_index = self.repeat_index.checked_add(1).unwrap_or(0);
|
self.repeat_index = self.repeat_index.checked_add(1).unwrap_or(0);
|
||||||
match self.repeat {
|
match self.repeat {
|
||||||
Repeat::Count(n) => {
|
Count::Finite(n) => {
|
||||||
if self.repeat_index >= n {
|
if self.repeat_index >= n {
|
||||||
None
|
None
|
||||||
} else {
|
} else {
|
||||||
@ -270,7 +270,7 @@ impl Iterator for InputQueue<'_> {
|
|||||||
Some(self.input_at(0))
|
Some(self.input_at(0))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Repeat::Forever => {
|
Count::Infinite => {
|
||||||
self.index = 1;
|
self.index = 1;
|
||||||
Some(self.input_at(0))
|
Some(self.input_at(0))
|
||||||
}
|
}
|
||||||
@ -286,13 +286,13 @@ impl Iterator for InputQueue<'_> {
|
|||||||
mod tests {
|
mod tests {
|
||||||
use crate::run::InputQueue;
|
use crate::run::InputQueue;
|
||||||
use hurl::runner::Input;
|
use hurl::runner::Input;
|
||||||
use hurl_core::typing::Repeat;
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn input_queue_is_finite() {
|
fn input_queue_is_finite() {
|
||||||
let files = [Input::new("a"), Input::new("b"), Input::new("c")];
|
let files = [Input::new("a"), Input::new("b"), Input::new("c")];
|
||||||
|
|
||||||
let mut queue = InputQueue::new(&files, Repeat::Count(4));
|
let mut queue = InputQueue::new(&files, Count::Finite(4));
|
||||||
assert_eq!(queue.next(), Some(Input::new("a")));
|
assert_eq!(queue.next(), Some(Input::new("a")));
|
||||||
assert_eq!(queue.next(), Some(Input::new("b")));
|
assert_eq!(queue.next(), Some(Input::new("b")));
|
||||||
assert_eq!(queue.next(), Some(Input::new("c")));
|
assert_eq!(queue.next(), Some(Input::new("c")));
|
||||||
@ -312,7 +312,7 @@ mod tests {
|
|||||||
fn input_queue_is_infinite() {
|
fn input_queue_is_infinite() {
|
||||||
let files = [Input::new("a")];
|
let files = [Input::new("a")];
|
||||||
|
|
||||||
let mut queue = InputQueue::new(&files, Repeat::Forever);
|
let mut queue = InputQueue::new(&files, Count::Infinite);
|
||||||
assert_eq!(queue.next(), Some(Input::new("a")));
|
assert_eq!(queue.next(), Some(Input::new("a")));
|
||||||
assert_eq!(queue.next(), Some(Input::new("a")));
|
assert_eq!(queue.next(), Some(Input::new("a")));
|
||||||
assert_eq!(queue.next(), Some(Input::new("a")));
|
assert_eq!(queue.next(), Some(Input::new("a")));
|
||||||
|
@ -26,7 +26,7 @@ use hurl_core::ast::{
|
|||||||
};
|
};
|
||||||
use hurl_core::error::DisplaySourceError;
|
use hurl_core::error::DisplaySourceError;
|
||||||
use hurl_core::parser;
|
use hurl_core::parser;
|
||||||
use hurl_core::typing::{Repeat, Retry};
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
use crate::http::{Call, Client};
|
use crate::http::{Call, Client};
|
||||||
use crate::runner::event::EventListener;
|
use crate::runner::event::EventListener;
|
||||||
@ -217,7 +217,7 @@ pub fn run_entries(
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Repeat 0 is equivalent to skip.
|
// Repeat 0 is equivalent to skip.
|
||||||
if options.repeat == Some(Repeat::Count(0)) {
|
if options.repeat == Some(Count::Finite(0)) {
|
||||||
logger.debug("");
|
logger.debug("");
|
||||||
logger.debug_important(&format!("Entry {entry_index} is skipped (repeat 0 times)"));
|
logger.debug_important(&format!("Entry {entry_index} is skipped (repeat 0 times)"));
|
||||||
entry_index += 1;
|
entry_index += 1;
|
||||||
@ -268,7 +268,7 @@ pub fn run_entries(
|
|||||||
repeat_count = 0;
|
repeat_count = 0;
|
||||||
entry_index += 1;
|
entry_index += 1;
|
||||||
}
|
}
|
||||||
Some(Repeat::Count(n)) => {
|
Some(Count::Finite(n)) => {
|
||||||
if repeat_count >= n {
|
if repeat_count >= n {
|
||||||
repeat_count = 0;
|
repeat_count = 0;
|
||||||
entry_index += 1;
|
entry_index += 1;
|
||||||
@ -278,7 +278,7 @@ pub fn run_entries(
|
|||||||
));
|
));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Some(Repeat::Forever) => {
|
Some(Count::Infinite) => {
|
||||||
logger.debug_important(&format!("Repeat entry {entry_index} (x{repeat_count})"));
|
logger.debug_important(&format!("Repeat entry {entry_index} (x{repeat_count})"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -319,7 +319,7 @@ fn run_request(
|
|||||||
let mut has_error = !result.errors.is_empty();
|
let mut has_error = !result.errors.is_empty();
|
||||||
|
|
||||||
// The retry threshold can only be reached with a finite positive number of retries
|
// The retry threshold can only be reached with a finite positive number of retries
|
||||||
let retry_max_reached = if let Some(Retry::Finite(r)) = options.retry {
|
let retry_max_reached = if let Some(Count::Finite(r)) = options.retry {
|
||||||
retry_count > r
|
retry_count > r
|
||||||
} else {
|
} else {
|
||||||
false
|
false
|
||||||
|
@ -19,10 +19,10 @@ use std::collections::HashMap;
|
|||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
use hurl_core::ast::{
|
use hurl_core::ast::{
|
||||||
BooleanOption, Entry, EntryOption, Float, NaturalOption, Number as AstNumber, OptionKind,
|
BooleanOption, CountOption, Entry, EntryOption, Float, NaturalOption, Number as AstNumber,
|
||||||
RepeatOption, RetryOption, SectionValue, VariableDefinition, VariableValue,
|
OptionKind, SectionValue, VariableDefinition, VariableValue,
|
||||||
};
|
};
|
||||||
use hurl_core::typing::{Repeat, Retry};
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
use crate::http::{IpResolve, RequestedHttpVersion};
|
use crate::http::{IpResolve, RequestedHttpVersion};
|
||||||
use crate::runner::template::{eval_expression, eval_template};
|
use crate::runner::template::{eval_expression, eval_template};
|
||||||
@ -200,7 +200,7 @@ pub fn get_entry_options(
|
|||||||
entry_options.proxy = Some(value);
|
entry_options.proxy = Some(value);
|
||||||
}
|
}
|
||||||
OptionKind::Repeat(value) => {
|
OptionKind::Repeat(value) => {
|
||||||
let value = eval_repeat_option(value, variables)?;
|
let value = eval_count_option(value, variables)?;
|
||||||
entry_options.repeat = Some(value);
|
entry_options.repeat = Some(value);
|
||||||
}
|
}
|
||||||
OptionKind::Resolve(value) => {
|
OptionKind::Resolve(value) => {
|
||||||
@ -208,7 +208,7 @@ pub fn get_entry_options(
|
|||||||
entry_options.resolves.push(value);
|
entry_options.resolves.push(value);
|
||||||
}
|
}
|
||||||
OptionKind::Retry(value) => {
|
OptionKind::Retry(value) => {
|
||||||
let value = eval_retry_option(value, variables)?;
|
let value = eval_count_option(value, variables)?;
|
||||||
entry_options.retry = Some(value);
|
entry_options.retry = Some(value);
|
||||||
}
|
}
|
||||||
OptionKind::RetryInterval(value) => {
|
OptionKind::RetryInterval(value) => {
|
||||||
@ -320,7 +320,6 @@ fn eval_boolean_option(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Evals a natural option value (>=0), given a set of `variables`.
|
|
||||||
fn eval_natural_option(
|
fn eval_natural_option(
|
||||||
natural_value: &NaturalOption,
|
natural_value: &NaturalOption,
|
||||||
variables: &HashMap<String, Value>,
|
variables: &HashMap<String, Value>,
|
||||||
@ -352,53 +351,18 @@ fn eval_natural_option(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Render an AST repeat option with a `variables` set.
|
fn eval_count_option(
|
||||||
fn eval_repeat_option(
|
count_value: &CountOption,
|
||||||
repeat_option_value: &RepeatOption,
|
|
||||||
variables: &HashMap<String, Value>,
|
variables: &HashMap<String, Value>,
|
||||||
) -> Result<Repeat, RunnerError> {
|
) -> Result<Count, RunnerError> {
|
||||||
match repeat_option_value {
|
match count_value {
|
||||||
RepeatOption::Literal(repeat) => Ok(*repeat),
|
CountOption::Literal(repeat) => Ok(*repeat),
|
||||||
RepeatOption::Expression(expr) => match eval_expression(expr, variables)? {
|
CountOption::Expression(expr) => match eval_expression(expr, variables)? {
|
||||||
Value::Number(Number::Integer(value)) => {
|
Value::Number(Number::Integer(value)) => {
|
||||||
if value == -1 {
|
if value == -1 {
|
||||||
Ok(Repeat::Forever)
|
Ok(Count::Infinite)
|
||||||
} else if value >= 0 {
|
} else if value >= 0 {
|
||||||
Ok(Repeat::Count(value as usize))
|
Ok(Count::Finite(value as usize))
|
||||||
} else {
|
|
||||||
let kind = RunnerErrorKind::TemplateVariableInvalidType {
|
|
||||||
name: expr.variable.name.clone(),
|
|
||||||
value: format!("integer <{value}>"),
|
|
||||||
expecting: "integer".to_string(),
|
|
||||||
};
|
|
||||||
Err(RunnerError::new(expr.variable.source_info, kind, false))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
v => {
|
|
||||||
let kind = RunnerErrorKind::TemplateVariableInvalidType {
|
|
||||||
name: expr.variable.name.clone(),
|
|
||||||
value: v.format(),
|
|
||||||
expecting: "integer".to_string(),
|
|
||||||
};
|
|
||||||
Err(RunnerError::new(expr.variable.source_info, kind, false))
|
|
||||||
}
|
|
||||||
},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Render an AST retry option with a `variables` set.
|
|
||||||
fn eval_retry_option(
|
|
||||||
retry_option_value: &RetryOption,
|
|
||||||
variables: &HashMap<String, Value>,
|
|
||||||
) -> Result<Retry, RunnerError> {
|
|
||||||
match retry_option_value {
|
|
||||||
RetryOption::Literal(retry) => Ok(*retry),
|
|
||||||
RetryOption::Expression(expr) => match eval_expression(expr, variables)? {
|
|
||||||
Value::Number(Number::Integer(value)) => {
|
|
||||||
if value == -1 {
|
|
||||||
Ok(Retry::Infinite)
|
|
||||||
} else if value >= 0 {
|
|
||||||
Ok(Retry::Finite(value as usize))
|
|
||||||
} else {
|
} else {
|
||||||
let kind = RunnerErrorKind::TemplateVariableInvalidType {
|
let kind = RunnerErrorKind::TemplateVariableInvalidType {
|
||||||
name: expr.variable.name.clone(),
|
name: expr.variable.name.clone(),
|
||||||
@ -411,7 +375,7 @@ fn eval_retry_option(
|
|||||||
v => {
|
v => {
|
||||||
let kind = RunnerErrorKind::TemplateVariableInvalidType {
|
let kind = RunnerErrorKind::TemplateVariableInvalidType {
|
||||||
name: expr.variable.name.clone(),
|
name: expr.variable.name.clone(),
|
||||||
value: v.to_string(),
|
value: v.format(),
|
||||||
expecting: "integer".to_string(),
|
expecting: "integer".to_string(),
|
||||||
};
|
};
|
||||||
Err(RunnerError::new(expr.variable.source_info, kind, false))
|
Err(RunnerError::new(expr.variable.source_info, kind, false))
|
||||||
|
@ -18,7 +18,7 @@
|
|||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
use hurl_core::ast::Entry;
|
use hurl_core::ast::Entry;
|
||||||
use hurl_core::typing::{Repeat, Retry};
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
use crate::http::{IpResolve, RequestedHttpVersion};
|
use crate::http::{IpResolve, RequestedHttpVersion};
|
||||||
use crate::runner::Output;
|
use crate::runner::Output;
|
||||||
@ -54,9 +54,9 @@ pub struct RunnerOptionsBuilder {
|
|||||||
post_entry: Option<fn() -> bool>,
|
post_entry: Option<fn() -> bool>,
|
||||||
pre_entry: Option<fn(Entry) -> bool>,
|
pre_entry: Option<fn(Entry) -> bool>,
|
||||||
proxy: Option<String>,
|
proxy: Option<String>,
|
||||||
repeat: Option<Repeat>,
|
repeat: Option<Count>,
|
||||||
resolves: Vec<String>,
|
resolves: Vec<String>,
|
||||||
retry: Option<Retry>,
|
retry: Option<Count>,
|
||||||
retry_interval: Duration,
|
retry_interval: Duration,
|
||||||
skip: bool,
|
skip: bool,
|
||||||
ssl_no_revoke: bool,
|
ssl_no_revoke: bool,
|
||||||
@ -322,7 +322,7 @@ impl RunnerOptionsBuilder {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Set the number of repetition for a given entry.
|
/// Set the number of repetition for a given entry.
|
||||||
pub fn repeat(&mut self, repeat: Option<Repeat>) -> &mut Self {
|
pub fn repeat(&mut self, repeat: Option<Count>) -> &mut Self {
|
||||||
self.repeat = repeat;
|
self.repeat = repeat;
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
@ -336,7 +336,7 @@ impl RunnerOptionsBuilder {
|
|||||||
/// Sets maximum number of retries.
|
/// Sets maximum number of retries.
|
||||||
///
|
///
|
||||||
/// Default is 0.
|
/// Default is 0.
|
||||||
pub fn retry(&mut self, retry: Option<Retry>) -> &mut Self {
|
pub fn retry(&mut self, retry: Option<Count>) -> &mut Self {
|
||||||
self.retry = retry;
|
self.retry = retry;
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
@ -470,9 +470,9 @@ pub struct RunnerOptions {
|
|||||||
pub(crate) post_entry: Option<fn() -> bool>,
|
pub(crate) post_entry: Option<fn() -> bool>,
|
||||||
pub(crate) pre_entry: Option<fn(Entry) -> bool>,
|
pub(crate) pre_entry: Option<fn(Entry) -> bool>,
|
||||||
pub(crate) proxy: Option<String>,
|
pub(crate) proxy: Option<String>,
|
||||||
pub(crate) repeat: Option<Repeat>,
|
pub(crate) repeat: Option<Count>,
|
||||||
pub(crate) resolves: Vec<String>,
|
pub(crate) resolves: Vec<String>,
|
||||||
pub(crate) retry: Option<Retry>,
|
pub(crate) retry: Option<Count>,
|
||||||
pub(crate) retry_interval: Duration,
|
pub(crate) retry_interval: Duration,
|
||||||
pub(crate) skip: bool,
|
pub(crate) skip: bool,
|
||||||
pub(crate) ssl_no_revoke: bool,
|
pub(crate) ssl_no_revoke: bool,
|
||||||
|
@ -17,7 +17,7 @@
|
|||||||
*/
|
*/
|
||||||
use crate::ast::json;
|
use crate::ast::json;
|
||||||
use crate::reader::Pos;
|
use crate::reader::Pos;
|
||||||
use crate::typing::{Repeat, Retry};
|
use crate::typing::Count;
|
||||||
|
|
||||||
///
|
///
|
||||||
/// Hurl AST
|
/// Hurl AST
|
||||||
@ -726,9 +726,9 @@ pub enum OptionKind {
|
|||||||
Output(Template),
|
Output(Template),
|
||||||
PathAsIs(BooleanOption),
|
PathAsIs(BooleanOption),
|
||||||
Proxy(Template),
|
Proxy(Template),
|
||||||
Repeat(RepeatOption),
|
Repeat(CountOption),
|
||||||
Resolve(Template),
|
Resolve(Template),
|
||||||
Retry(RetryOption),
|
Retry(CountOption),
|
||||||
RetryInterval(NaturalOption),
|
RetryInterval(NaturalOption),
|
||||||
Skip(BooleanOption),
|
Skip(BooleanOption),
|
||||||
UnixSocket(Template),
|
UnixSocket(Template),
|
||||||
@ -831,14 +831,8 @@ pub enum NaturalOption {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, PartialEq, Eq)]
|
#[derive(Clone, Debug, PartialEq, Eq)]
|
||||||
pub enum RepeatOption {
|
pub enum CountOption {
|
||||||
Literal(Repeat),
|
Literal(Count),
|
||||||
Expression(Expr),
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Clone, Debug, PartialEq, Eq)]
|
|
||||||
pub enum RetryOption {
|
|
||||||
Literal(Retry),
|
|
||||||
Expression(Expr),
|
Expression(Expr),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -187,20 +187,11 @@ impl fmt::Display for NaturalOption {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl fmt::Display for RepeatOption {
|
impl fmt::Display for CountOption {
|
||||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||||
match self {
|
match self {
|
||||||
RepeatOption::Literal(v) => write!(f, "{}", v),
|
CountOption::Literal(v) => write!(f, "{}", v),
|
||||||
RepeatOption::Expression(v) => write!(f, "{}", v),
|
CountOption::Expression(v) => write!(f, "{}", v),
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl fmt::Display for RetryOption {
|
|
||||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
|
||||||
match self {
|
|
||||||
RetryOption::Literal(v) => write!(f, "{}", v),
|
|
||||||
RetryOption::Expression(v) => write!(f, "{}", v),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -18,7 +18,7 @@
|
|||||||
use std::fmt::Display;
|
use std::fmt::Display;
|
||||||
|
|
||||||
use crate::ast::*;
|
use crate::ast::*;
|
||||||
use crate::typing::{Repeat, Retry};
|
use crate::typing::Count;
|
||||||
|
|
||||||
/// Returns an HTML string of the Hurl file `hurl_file`.
|
/// Returns an HTML string of the Hurl file `hurl_file`.
|
||||||
///
|
///
|
||||||
@ -238,9 +238,9 @@ impl HtmlFormatter {
|
|||||||
OptionKind::Output(filename) => self.fmt_filename(filename),
|
OptionKind::Output(filename) => self.fmt_filename(filename),
|
||||||
OptionKind::PathAsIs(value) => self.fmt_bool_option(value),
|
OptionKind::PathAsIs(value) => self.fmt_bool_option(value),
|
||||||
OptionKind::Proxy(value) => self.fmt_template(value),
|
OptionKind::Proxy(value) => self.fmt_template(value),
|
||||||
OptionKind::Repeat(value) => self.fmt_repeat_option(value),
|
OptionKind::Repeat(value) => self.fmt_count_option(value),
|
||||||
OptionKind::Resolve(value) => self.fmt_template(value),
|
OptionKind::Resolve(value) => self.fmt_template(value),
|
||||||
OptionKind::Retry(value) => self.fmt_retry_option(value),
|
OptionKind::Retry(value) => self.fmt_count_option(value),
|
||||||
OptionKind::RetryInterval(value) => self.fmt_natural_option(value),
|
OptionKind::RetryInterval(value) => self.fmt_natural_option(value),
|
||||||
OptionKind::Skip(value) => self.fmt_bool_option(value),
|
OptionKind::Skip(value) => self.fmt_bool_option(value),
|
||||||
OptionKind::UnixSocket(value) => self.fmt_template(value),
|
OptionKind::UnixSocket(value) => self.fmt_template(value),
|
||||||
@ -253,31 +253,17 @@ impl HtmlFormatter {
|
|||||||
self.fmt_lt(&option.line_terminator0);
|
self.fmt_lt(&option.line_terminator0);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fmt_repeat_option(&mut self, repeat_option: &RepeatOption) {
|
fn fmt_count_option(&mut self, count_option: &CountOption) {
|
||||||
match repeat_option {
|
match count_option {
|
||||||
RepeatOption::Literal(repeat) => self.fmt_repeat(repeat),
|
CountOption::Literal(repeat) => self.fmt_count(*repeat),
|
||||||
RepeatOption::Expression(expr) => self.fmt_expr(expr),
|
CountOption::Expression(expr) => self.fmt_expr(expr),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fmt_repeat(&mut self, repeat: &Repeat) {
|
fn fmt_count(&mut self, count: Count) {
|
||||||
match repeat {
|
match count {
|
||||||
Repeat::Count(n) => self.fmt_number(n),
|
Count::Finite(n) => self.fmt_number(n),
|
||||||
Repeat::Forever => self.fmt_number(-1),
|
Count::Infinite => self.fmt_number(-1),
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
fn fmt_retry_option(&mut self, retry_option: &RetryOption) {
|
|
||||||
match retry_option {
|
|
||||||
RetryOption::Literal(retry) => self.fmt_retry(retry),
|
|
||||||
RetryOption::Expression(expr) => self.fmt_expr(expr),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
fn fmt_retry(&mut self, retry: &Retry) {
|
|
||||||
match retry {
|
|
||||||
Retry::Finite(n) => self.fmt_number(n),
|
|
||||||
Retry::Infinite => self.fmt_number(-1),
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -23,7 +23,7 @@ use crate::parser::primitives::*;
|
|||||||
use crate::parser::string::*;
|
use crate::parser::string::*;
|
||||||
use crate::parser::{expr, filename, filename_password, ParseResult};
|
use crate::parser::{expr, filename, filename_password, ParseResult};
|
||||||
use crate::reader::Reader;
|
use crate::reader::Reader;
|
||||||
use crate::typing::{Repeat, Retry};
|
use crate::typing::Count;
|
||||||
|
|
||||||
/// Parse an option in an `[Options]` section.
|
/// Parse an option in an `[Options]` section.
|
||||||
pub fn parse(reader: &mut Reader) -> ParseResult<EntryOption> {
|
pub fn parse(reader: &mut Reader) -> ParseResult<EntryOption> {
|
||||||
@ -208,7 +208,7 @@ fn option_proxy(reader: &mut Reader) -> ParseResult<OptionKind> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn option_repeat(reader: &mut Reader) -> ParseResult<OptionKind> {
|
fn option_repeat(reader: &mut Reader) -> ParseResult<OptionKind> {
|
||||||
let value = repeat_option(reader)?;
|
let value = non_recover(count_option, reader)?;
|
||||||
Ok(OptionKind::Repeat(value))
|
Ok(OptionKind::Repeat(value))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -218,7 +218,7 @@ fn option_resolve(reader: &mut Reader) -> ParseResult<OptionKind> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn option_retry(reader: &mut Reader) -> ParseResult<OptionKind> {
|
fn option_retry(reader: &mut Reader) -> ParseResult<OptionKind> {
|
||||||
let value = retry_option(reader)?;
|
let value = non_recover(count_option, reader)?;
|
||||||
Ok(OptionKind::Retry(value))
|
Ok(OptionKind::Retry(value))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -257,31 +257,16 @@ fn option_very_verbose(reader: &mut Reader) -> ParseResult<OptionKind> {
|
|||||||
Ok(OptionKind::VeryVerbose(value))
|
Ok(OptionKind::VeryVerbose(value))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn repeat(reader: &mut Reader) -> ParseResult<Repeat> {
|
fn count(reader: &mut Reader) -> ParseResult<Count> {
|
||||||
let start = reader.cursor();
|
let start = reader.cursor();
|
||||||
let value = non_recover(integer, reader)?;
|
let value = non_recover(integer, reader)?;
|
||||||
if value == -1 {
|
if value == -1 {
|
||||||
Ok(Repeat::Forever)
|
Ok(Count::Infinite)
|
||||||
} else if value >= 0 {
|
} else if value >= 0 {
|
||||||
Ok(Repeat::Count(value as usize))
|
Ok(Count::Finite(value as usize))
|
||||||
} else {
|
} else {
|
||||||
let kind = ParseErrorKind::Expecting {
|
let kind = ParseErrorKind::Expecting {
|
||||||
value: "Expecting a repeat value".to_string(),
|
value: "Expecting a count value".to_string(),
|
||||||
};
|
|
||||||
Err(ParseError::new(start.pos, false, kind))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn retry(reader: &mut Reader) -> ParseResult<Retry> {
|
|
||||||
let start = reader.cursor();
|
|
||||||
let value = non_recover(integer, reader)?;
|
|
||||||
if value == -1 {
|
|
||||||
Ok(Retry::Infinite)
|
|
||||||
} else if value >= 0 {
|
|
||||||
Ok(Retry::Finite(value as usize))
|
|
||||||
} else {
|
|
||||||
let kind = ParseErrorKind::Expecting {
|
|
||||||
value: "Expecting a retry value".to_string(),
|
|
||||||
};
|
};
|
||||||
Err(ParseError::new(start.pos, false, kind))
|
Err(ParseError::new(start.pos, false, kind))
|
||||||
}
|
}
|
||||||
@ -321,27 +306,10 @@ fn natural_option(reader: &mut Reader) -> ParseResult<NaturalOption> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn repeat_option(reader: &mut Reader) -> ParseResult<RepeatOption> {
|
fn count_option(reader: &mut Reader) -> ParseResult<CountOption> {
|
||||||
let start = reader.cursor();
|
let start = reader.cursor();
|
||||||
match repeat(reader) {
|
match count(reader) {
|
||||||
Ok(v) => Ok(RepeatOption::Literal(v)),
|
Ok(v) => Ok(CountOption::Literal(v)),
|
||||||
Err(_) => {
|
|
||||||
reader.seek(start);
|
|
||||||
let exp = expr::parse(reader).map_err(|e| {
|
|
||||||
let kind = ParseErrorKind::Expecting {
|
|
||||||
value: "integer".to_string(),
|
|
||||||
};
|
|
||||||
ParseError::new(e.pos, false, kind)
|
|
||||||
})?;
|
|
||||||
Ok(RepeatOption::Expression(exp))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn retry_option(reader: &mut Reader) -> ParseResult<RetryOption> {
|
|
||||||
let start = reader.cursor();
|
|
||||||
match retry(reader) {
|
|
||||||
Ok(v) => Ok(RetryOption::Literal(v)),
|
|
||||||
Err(_) => {
|
Err(_) => {
|
||||||
reader.seek(start);
|
reader.seek(start);
|
||||||
let exp = expr::parse(reader).map_err(|e| {
|
let exp = expr::parse(reader).map_err(|e| {
|
||||||
@ -350,7 +318,7 @@ fn retry_option(reader: &mut Reader) -> ParseResult<RetryOption> {
|
|||||||
};
|
};
|
||||||
ParseError::new(e.pos, false, kind)
|
ParseError::new(e.pos, false, kind)
|
||||||
})?;
|
})?;
|
||||||
Ok(RetryOption::Expression(exp))
|
Ok(CountOption::Expression(exp))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -18,43 +18,22 @@
|
|||||||
//! Hurl common types.
|
//! Hurl common types.
|
||||||
use core::fmt;
|
use core::fmt;
|
||||||
|
|
||||||
/// Represents a repeat operation, either finite or infinite.
|
/// Represents a count operation, either finite or infinite.
|
||||||
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
|
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
|
||||||
pub enum Repeat {
|
pub enum Count {
|
||||||
Count(usize),
|
|
||||||
Forever,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Default for Repeat {
|
|
||||||
fn default() -> Self {
|
|
||||||
Repeat::Count(1)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl fmt::Display for Repeat {
|
|
||||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
|
||||||
let value = match self {
|
|
||||||
Repeat::Count(n) => *n as i64,
|
|
||||||
Repeat::Forever => -1,
|
|
||||||
};
|
|
||||||
write!(f, "{}", value)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/// Represents a retry operation (when an operation has failed), either finite or infinite.
|
|
||||||
/// Contrary to [`Repeat`], [`Retry`] has a notion of retry only on operation failure, while
|
|
||||||
/// [`Repeat`] is unconditional.
|
|
||||||
#[derive(Clone, Debug, PartialEq, Eq, Copy)]
|
|
||||||
pub enum Retry {
|
|
||||||
Finite(usize),
|
Finite(usize),
|
||||||
Infinite,
|
Infinite,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl fmt::Display for Retry {
|
impl fmt::Display for Count {
|
||||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||||
let value = match self {
|
match self {
|
||||||
Retry::Finite(n) => *n as i64,
|
Count::Finite(n) => {
|
||||||
Retry::Infinite => -1,
|
write!(f, "{n}")
|
||||||
};
|
}
|
||||||
write!(f, "{}", value)
|
Count::Infinite => {
|
||||||
|
write!(f, "-1")
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -18,7 +18,7 @@
|
|||||||
use base64::engine::general_purpose;
|
use base64::engine::general_purpose;
|
||||||
use base64::Engine;
|
use base64::Engine;
|
||||||
use hurl_core::ast::*;
|
use hurl_core::ast::*;
|
||||||
use hurl_core::typing::{Repeat, Retry};
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
use super::serialize_json::*;
|
use super::serialize_json::*;
|
||||||
|
|
||||||
@ -353,38 +353,20 @@ impl ToJson for NaturalOption {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ToJson for RepeatOption {
|
impl ToJson for CountOption {
|
||||||
fn to_json(&self) -> JValue {
|
fn to_json(&self) -> JValue {
|
||||||
match self {
|
match self {
|
||||||
RepeatOption::Literal(value) => value.to_json(),
|
CountOption::Literal(value) => value.to_json(),
|
||||||
RepeatOption::Expression(expr) => expr.to_json(),
|
CountOption::Expression(expr) => expr.to_json(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ToJson for Repeat {
|
impl ToJson for Count {
|
||||||
fn to_json(&self) -> JValue {
|
fn to_json(&self) -> JValue {
|
||||||
match self {
|
match self {
|
||||||
Repeat::Count(n) => JValue::Number(n.to_string()),
|
Count::Finite(n) => JValue::Number(n.to_string()),
|
||||||
Repeat::Forever => JValue::Number("-1".to_string()),
|
Count::Infinite => JValue::Number("-1".to_string()),
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ToJson for RetryOption {
|
|
||||||
fn to_json(&self) -> JValue {
|
|
||||||
match self {
|
|
||||||
RetryOption::Literal(value) => value.to_json(),
|
|
||||||
RetryOption::Expression(expr) => expr.to_json(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ToJson for Retry {
|
|
||||||
fn to_json(&self) -> JValue {
|
|
||||||
match self {
|
|
||||||
Retry::Finite(n) => JValue::Number(n.to_string()),
|
|
||||||
Retry::Infinite => JValue::Number("-1".to_string()),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -16,7 +16,7 @@
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
use hurl_core::ast::*;
|
use hurl_core::ast::*;
|
||||||
use hurl_core::typing::{Repeat, Retry};
|
use hurl_core::typing::Count;
|
||||||
|
|
||||||
#[derive(Clone, Debug, PartialEq, Eq)]
|
#[derive(Clone, Debug, PartialEq, Eq)]
|
||||||
pub enum Token {
|
pub enum Token {
|
||||||
@ -935,38 +935,20 @@ impl Tokenizable for NaturalOption {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Tokenizable for RepeatOption {
|
impl Tokenizable for CountOption {
|
||||||
fn tokenize(&self) -> Vec<Token> {
|
fn tokenize(&self) -> Vec<Token> {
|
||||||
match self {
|
match self {
|
||||||
RepeatOption::Literal(retry) => retry.tokenize(),
|
CountOption::Literal(retry) => retry.tokenize(),
|
||||||
RepeatOption::Expression(expr) => expr.tokenize(),
|
CountOption::Expression(expr) => expr.tokenize(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Tokenizable for Repeat {
|
impl Tokenizable for Count {
|
||||||
fn tokenize(&self) -> Vec<Token> {
|
fn tokenize(&self) -> Vec<Token> {
|
||||||
match self {
|
match self {
|
||||||
Repeat::Count(n) => vec![Token::Number(n.to_string())],
|
Count::Finite(n) => vec![Token::Number(n.to_string())],
|
||||||
Repeat::Forever => vec![Token::Number("-1".to_string())],
|
Count::Infinite => vec![Token::Number("-1".to_string())],
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Tokenizable for RetryOption {
|
|
||||||
fn tokenize(&self) -> Vec<Token> {
|
|
||||||
match self {
|
|
||||||
RetryOption::Literal(retry) => retry.tokenize(),
|
|
||||||
RetryOption::Expression(expr) => expr.tokenize(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Tokenizable for Retry {
|
|
||||||
fn tokenize(&self) -> Vec<Token> {
|
|
||||||
match self {
|
|
||||||
Retry::Finite(n) => vec![Token::Number(n.to_string())],
|
|
||||||
Retry::Infinite => vec![Token::Number("-1".to_string())],
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user