fix(u16_wrappers): Improve error handling and validation for CustomerListLimit conversions

This commit is contained in:
Venu Madhav
2025-10-27 16:40:07 +05:30
parent e8de4270f5
commit babb698b98
3 changed files with 24 additions and 19 deletions

View File

@ -15,13 +15,13 @@ pub const MAX_DISPUTE_POLLING_INTERVAL_IN_HOURS: i32 = 24;
pub const DEFAULT_DISPUTE_POLLING_INTERVAL_IN_HOURS: i32 = 24;
/// Customer List Lower Limit
pub const CUSTOMER_LIST_LOWER_LIMIT: u16 = 1;
pub const CUSTOMER_LIST_LOWER_LIMIT: i16 = 1;
/// Customer List Upper Limit
pub const CUSTOMER_LIST_UPPER_LIMIT: u16 = 100;
pub const CUSTOMER_LIST_UPPER_LIMIT: i16 = 100;
/// Customer List Default Limit
pub const CUSTOMER_LIST_DEFAULT_LIMIT: u16 = 20;
pub const CUSTOMER_LIST_DEFAULT_LIMIT: i16 = 20;
/// Default payment intent statuses that trigger a webhook
pub const DEFAULT_PAYMENT_WEBHOOK_TRIGGER_STATUSES: &[common_enums::IntentStatus] = &[

View File

@ -463,7 +463,7 @@ mod u16_wrappers {
where
D: serde::Deserializer<'de>,
{
let val = u16::deserialize(deserializer)?;
let val = i16::deserialize(deserializer)?;
if val < CUSTOMER_LIST_LOWER_LIMIT {
Err(D::Error::custom(format!(
"CustomerListLimit cannot be less than {}",
@ -475,7 +475,7 @@ mod u16_wrappers {
CUSTOMER_LIST_UPPER_LIMIT
)))
} else {
Ok(Self(val as i16))
Ok(Self(val))
}
}
}
@ -502,37 +502,40 @@ mod u16_wrappers {
impl Default for CustomerListLimit {
/// Default for `CustomerListLimit` is `20`
fn default() -> Self {
Self(CUSTOMER_LIST_DEFAULT_LIMIT as i16)
}
}
impl From<u16> for CustomerListLimit {
fn from(value: u16) -> Self {
Self(value.clamp(CUSTOMER_LIST_LOWER_LIMIT, CUSTOMER_LIST_UPPER_LIMIT) as i16)
Self(CUSTOMER_LIST_DEFAULT_LIMIT)
}
}
impl CustomerListLimit {
/// Creates a new CustomerListLimit with validation
pub fn new(value: u16) -> Result<Self, String> {
if value < CUSTOMER_LIST_LOWER_LIMIT {
// Convert constants to u16 for comparison - these should always succeed
let lower_u16 = u16::try_from(CUSTOMER_LIST_LOWER_LIMIT)
.map_err(|_| "Invalid lower limit constant".to_string())?;
let upper_u16 = u16::try_from(CUSTOMER_LIST_UPPER_LIMIT)
.map_err(|_| "Invalid upper limit constant".to_string())?;
if value < lower_u16 {
Err(format!(
"CustomerListLimit cannot be less than {}",
CUSTOMER_LIST_LOWER_LIMIT
))
} else if value > CUSTOMER_LIST_UPPER_LIMIT {
} else if value > upper_u16 {
Err(format!(
"CustomerListLimit exceeds the maximum allowed value of {}",
CUSTOMER_LIST_UPPER_LIMIT
))
} else {
Ok(Self(value as i16))
let inner = i16::try_from(value)
.map_err(|_| "Value too large for internal representation".to_string())?;
Ok(Self(inner))
}
}
/// Returns the inner u16 value
pub fn get_value(&self) -> u16 {
self.0 as u16
/// Returns the limit as u16 for external compatibility
pub fn get_value(&self) -> Result<u16, String> {
u16::try_from(self.0)
.map_err(|_| "Internal value cannot be converted to u16".to_string())
}
}
}

View File

@ -637,7 +637,9 @@ pub async fn list_customers_with_count(
})?;
let customer_list_constraints = crate::db::customers::CustomerListConstraints {
limit: request.limit.unwrap_or_else(|| limit.get_value()),
limit: request
.limit
.unwrap_or_else(|| limit.get_value().unwrap_or(20)),
offset: request.offset,
customer_id: request.customer_id,
time_range: request.time_range,