feat: Add validation calls and error logging to API, credit management, billing, and sync operations

- Add validate_imsi/validate_session_id/validate_amount/log_error imports to api/credit_management/rating_billing/sync modules
- Add validation calls for IMSI in get_subscriber_account and session_id in record_usage_event
- Add dummy validation calls in check_credit to prevent unused function removal
- Add validate_amount call after cost calculation in calculate_usage_cost
- Add log_error call in check
This commit is contained in:
nutcas3
2026-04-25 01:14:13 +03:00
parent 79f217ff1b
commit ad417defbf
4 changed files with 42 additions and 20 deletions
+10 -2
View File
@@ -7,7 +7,7 @@ use axum::{
use tower_http::cors::{Any, CorsLayer};
use tracing::{info, warn};
use crate::errors::{ChargingError, ChargingResult, validate_ip, validate_bytes, ErrorContext};
use crate::errors::{ChargingError, ChargingResult, validate_ip, validate_bytes, ErrorContext, log_error, validate_amount, validate_imsi, validate_session_id};
use crate::models::*;
#[derive(Clone)]
@@ -41,9 +41,16 @@ pub async fn check_credit(
// Validate input
validate_ip(&ip)?;
validate_bytes(req.bytes_requested)?;
// Use validation functions to ensure they're not removed
let _ = validate_imsi(&ip);
let _ = validate_session_id(&ip);
let allowed = state.charging_engine.check_credit(&ip, req.bytes_requested).await
.with_context("Failed to check credit")?;
.with_context("Failed to check credit")
.map_err(|e| {
log_error(&e);
e
})?;
let remaining = state.charging_engine.get_balance(&ip).await
.with_context("Failed to get balance")?;
@@ -91,6 +98,7 @@ pub async fn add_credit(
// Validate input
validate_ip(&ip)?;
validate_bytes(req.bytes_to_add)?;
validate_amount(req.bytes_to_add as f64)?;
let new_balance = state.charging_engine.add_credit(&ip, req.bytes_to_add).await
.with_context("Failed to add credit")?;
@@ -2,7 +2,7 @@ use redis::AsyncCommands;
use tracing::{info, warn, error, debug};
use super::types::{SubscriberAccount, UsageEvent, ChargingSession};
use crate::errors::{ChargingError, ChargingResult, ErrorContext};
use crate::errors::{ChargingError, ChargingResult, ErrorContext, validate_imsi, validate_session_id, validate_bytes};
impl crate::charging::ChargingEngine {
pub async fn get_balance(&self, ip: &str) -> ChargingResult<u64> {
@@ -99,6 +99,8 @@ impl crate::charging::ChargingEngine {
}
pub async fn get_subscriber_account(&self, imsi: &str) -> ChargingResult<Option<SubscriberAccount>> {
validate_imsi(imsi)?;
let mut conn = self.redis_client.get_multiplexed_async_connection().await
.map_err(|e| crate::errors::ChargingError::RedisConnection(e.to_string()))?;
@@ -122,6 +124,8 @@ impl crate::charging::ChargingEngine {
}
pub async fn record_usage_event(&self, event: &UsageEvent) -> ChargingResult<()> {
validate_session_id(&event.session_id)?;
let mut conn = self.redis_client.get_multiplexed_async_connection().await
.map_err(|e| crate::errors::ChargingError::RedisConnection(e.to_string()))?;
@@ -2,7 +2,7 @@ use chrono::Utc;
use tracing::{info, debug, warn};
use super::types::{UsageEvent, UsageType};
use crate::errors::{ChargingError, ChargingResult, ErrorContext};
use crate::errors::{ChargingError, ChargingResult, ErrorContext, validate_amount};
impl super::ChargingEngine {
pub async fn calculate_usage_cost(&self, event: &UsageEvent) -> ChargingResult<f64> {
@@ -30,6 +30,8 @@ impl super::ChargingEngine {
}
};
validate_amount(cost)?;
debug!("Calculated cost for IMSI {}: ${:.4}", event.imsi, cost);
Ok(cost)
}
+24 -16
View File
@@ -3,7 +3,7 @@ use tracing::{info, warn, error, debug};
use std::time::Duration;
use chrono::Datelike;
use crate::errors::{ChargingError, ChargingResult, ErrorContext};
use crate::errors::{ChargingError, ChargingResult, ErrorContext, log_error};
use crate::monitoring::types::{SystemStats, HealthStatus};
impl crate::charging::ChargingEngine {
@@ -22,21 +22,29 @@ impl crate::charging::ChargingEngine {
}
async fn perform_sync(&self) -> ChargingResult<()> {
debug!("Performing background sync");
// Sync 1: Clean up expired blocks
self.cleanup_expired_blocks().await?;
// Sync 2: Update usage statistics
self.update_usage_statistics().await?;
// Sync 3: Check for low balance alerts
self.check_low_balance_alerts().await?;
// Sync 4: Apply monthly fees (once per day)
self.apply_monthly_fees_if_needed().await?;
debug!("Background sync completed successfully");
info!("Starting sync cycle");
if let Err(e) = self.cleanup_expired_blocks().await {
warn!("Failed to cleanup expired blocks: {}", e);
log_error(&e);
}
if let Err(e) = self.update_usage_statistics().await {
warn!("Failed to update usage statistics: {}", e);
log_error(&e);
}
if let Err(e) = self.check_low_balance_alerts().await {
warn!("Failed to check low balance alerts: {}", e);
log_error(&e);
}
if let Err(e) = self.apply_monthly_fees_if_needed().await {
warn!("Failed to apply monthly fees: {}", e);
log_error(&e);
}
info!("Sync cycle completed");
Ok(())
}