Skip to main content

hive_console_sdk/expressions/values/
duration.rs

1use crate::expressions::FromVrlValue;
2use humantime::{parse_duration, DurationError};
3use std::{str::Utf8Error, time::Duration};
4use vrl::core::Value as VrlValue;
5
6#[derive(Debug, thiserror::Error, Clone)]
7pub enum DurationParseErrorSource {
8    #[error("Invalid UTF-8 encoding in duration string: {0}")]
9    Utf8(#[from] Utf8Error),
10    #[error("Invalid duration format: {0}")]
11    Humantime(#[from] DurationError),
12}
13
14#[derive(Debug, thiserror::Error, Clone)]
15pub enum DurationConversionError {
16    #[error("Duration cannot be negative")]
17    NegativeValue,
18
19    #[error("Invalid duration type: {type_name}. Expected a non-negative integer (milliseconds) or a duration string (e.g., '30s', '5m', '1h')")]
20    UnexpectedType { type_name: String },
21
22    #[error(transparent)]
23    ParseError(#[from] DurationParseErrorSource),
24}
25
26impl From<Utf8Error> for DurationConversionError {
27    fn from(err: Utf8Error) -> Self {
28        DurationConversionError::ParseError(DurationParseErrorSource::Utf8(err))
29    }
30}
31
32impl From<DurationError> for DurationConversionError {
33    fn from(err: DurationError) -> Self {
34        DurationConversionError::ParseError(DurationParseErrorSource::Humantime(err))
35    }
36}
37
38impl FromVrlValue for Duration {
39    type Error = DurationConversionError;
40
41    #[inline]
42    fn from_vrl_value(value: VrlValue) -> Result<Self, Self::Error> {
43        match value {
44            VrlValue::Integer(i) => {
45                if i < 0 {
46                    return Err(DurationConversionError::NegativeValue);
47                }
48                Ok(Duration::from_millis(i as u64))
49            }
50            VrlValue::Bytes(b) => {
51                let s = std::str::from_utf8(&b)?;
52                Ok(parse_duration(s)?)
53            }
54            other => Err(DurationConversionError::UnexpectedType {
55                type_name: other.kind().to_string(),
56            }),
57        }
58    }
59}