credit-facility-rs 0.1.0

A rust library for modeling credit facilities with time-aware calculations
Documentation
use thiserror::Error;
use uuid::Uuid;

use crate::decimal::{Money, Rate};
use crate::types::FacilityStatus;

#[derive(Error, Debug)]
pub enum FacilityError {
    #[error("insufficient funds: available {available}, requested {requested}")]
    InsufficientFunds {
        available: Money,
        requested: Money,
    },
    
    #[error("ltv breach: {ltv} exceeds threshold {threshold}")]
    LtvBreach {
        ltv: Rate,
        threshold: Rate,
    },
    
    #[error("invalid payment amount: {amount}")]
    InvalidPaymentAmount {
        amount: Money,
    },
    
    #[error("facility not active: current status is {status:?}")]
    FacilityNotActive {
        status: FacilityStatus,
    },
    
    #[error("overdraft limit exceeded: limit {limit}, requested {requested}")]
    OverdraftLimitExceeded {
        limit: Money,
        requested: Money,
    },
    
    #[error("credit limit exceeded: limit {limit}, requested {requested}")]
    CreditLimitExceeded {
        limit: Money,
        requested: Money,
    },
    
    #[error("milestone not found: {id}")]
    MilestoneNotFound {
        id: Uuid,
    },
    
    #[error("milestone not approved for disbursement: {name}")]
    MilestoneNotApproved {
        name: String,
    },
    
    #[error("invalid configuration: {message}")]
    InvalidConfiguration {
        message: String,
    },
    
    #[error("liquidation in progress")]
    LiquidationInProgress,
    
    #[error("payment schedule not applicable for facility type")]
    PaymentScheduleNotApplicable,
    
    #[error("collateral required for this operation")]
    CollateralRequired,
    
    #[error("no collateral associated with facility")]
    NoCollateral,
    
    #[error("invalid date: {message}")]
    InvalidDate {
        message: String,
    },
    
    #[error("calculation error: {message}")]
    CalculationError {
        message: String,
    },
    
    #[error("facility already settled")]
    FacilityAlreadySettled,
    
    #[error("facility already charged off")]
    FacilityChargedOff,
    
    #[error("invalid interest rate: {rate}")]
    InvalidInterestRate {
        rate: Rate,
    },
    
    #[error("payment less than minimum: minimum {minimum}, provided {provided}")]
    PaymentBelowMinimum {
        minimum: Money,
        provided: Money,
    },
    
    #[error("operation not supported for facility type")]
    OperationNotSupported,
    
    #[error("draw period has ended")]
    DrawPeriodEnded,
    
    #[error("invalid draw amount: {amount}")]
    InvalidDrawAmount {
        amount: Money,
    },
    
    #[error("below minimum drawdown: minimum {minimum}, requested {requested}")]
    BelowMinimumDrawdown {
        minimum: Money,
        requested: Money,
    },
    
    #[error("exceeds credit limit: available {available}, requested {requested}")]
    ExceedsCreditLimit {
        available: Money,
        requested: Money,
    },
    
    #[error("invalid collateral: {message}")]
    InvalidCollateral {
        message: String,
    },
    
    #[error("insufficient collateral: available {available}, required {required}")]
    InsufficientCollateral {
        available: rust_decimal::Decimal,
        required: rust_decimal::Decimal,
    },
    
    #[error("margin call expired: deadline {deadline}, current time {current_time}")]
    MarginCallExpired {
        deadline: chrono::DateTime<chrono::Utc>,
        current_time: chrono::DateTime<chrono::Utc>,
    },
    
    #[error("invalid state: current {current}, expected {expected}")]
    InvalidState {
        current: String,
        expected: String,
    },
}

pub type Result<T> = std::result::Result<T, FacilityError>;