Skip to main content

cbilling/
lib.rs

1// Copyright 2025 OpenObserve Inc.
2// SPDX-License-Identifier: AGPL-3.0
3
4//! # Cloud Billing SDK
5//!
6//! A comprehensive Rust library for managing multi-cloud billing and account management.
7//!
8//! ## Supported Cloud Providers
9//!
10//! Each provider is behind a feature flag for modular compilation:
11//!
12//! - **Aliyun (Alibaba Cloud)** - feature: `aliyun` - Full support
13//! - **Tencent Cloud** - feature: `tencentcloud` - Full support
14//! - **AWS** - feature: `aws` - Full support via Cost Explorer API
15//! - **Volcengine (火山云)** - feature: `volcengine` - Full support
16//! - **UCloud** - feature: `ucloud` - Partial support
17//! - **Azure** - feature: `azure` - Planned
18//!
19//! ## Feature Flags
20//!
21//! ### Cloud Providers (modular)
22//! - `aliyun` - Alibaba Cloud billing support
23//! - `tencentcloud` - Tencent Cloud billing support
24//! - `aws` - AWS Cost Explorer support
25//! - `volcengine` - Volcengine billing support
26//! - `ucloud` - UCloud billing support
27//! - `all-providers` - Enable all cloud providers
28//!
29//! ### Database Support (optional)
30//! - `db-postgres` - PostgreSQL database support
31//! - `db-sqlite` - SQLite database support
32//!
33//! ### Convenience Features
34//! - `full` - All providers + PostgreSQL
35//! - `full-sqlite` - All providers + SQLite
36//!
37//! ### Default Features
38//! By default, all cloud providers are enabled but no database backend.
39//!
40//! ## Core Features
41//!
42//! - πŸ”„ Direct cloud provider API integration
43//! - πŸ‘₯ Multi-account support per provider
44//! - πŸ“Š Bill aggregation and analysis
45//! - πŸ“ˆ Cost trending and comparison
46//! - πŸ’Ύ Optional database persistence (PostgreSQL or SQLite)
47//! - πŸ” Query billing data by cycle, provider, and account
48//!
49//! ## Quick Start
50//!
51//! ### Basic Usage (without database)
52//!
53//! ```toml
54//! [dependencies]
55//! cbilling = { version = "0.1", features = ["aliyun"] }
56//! ```
57//!
58//! ```rust,no_run
59//! # #[cfg(feature = "aliyun")]
60//! use cbilling::providers::aliyun::AliyunBillingClient;
61//! use cbilling::error::Result;
62//!
63//! #[tokio::main]
64//! async fn main() -> Result<()> {
65//! #   #[cfg(feature = "aliyun")]
66//! #   {
67//!     // Create Aliyun billing client
68//!     let client = AliyunBillingClient::new(
69//!         "your_access_key_id".to_string(),
70//!         "your_access_key_secret".to_string(),
71//!     );
72//!
73//!     // Query billing data for a specific month
74//!     let billing_cycle = "2025-03";
75//!     let response = client.query_instance_bill(billing_cycle, None, None, None).await?;
76//!     
77//!     println!("Billing data: {:?}", response);
78//! #   }
79//!     Ok(())
80//! }
81//! ```
82//!
83//! ### With Database Support
84//!
85//! ```toml
86//! [dependencies]
87//! # PostgreSQL
88//! cbilling = { version = "0.1", features = ["aliyun", "db-postgres"] }
89//! # Or SQLite
90//! cbilling = { version = "0.1", features = ["aliyun", "db-sqlite"] }
91//! # Or all providers with PostgreSQL
92//! cbilling = { version = "0.1", features = ["full"] }
93//! ```
94
95// Temporarily allow missing docs during development
96#![allow(missing_docs)]
97#![warn(clippy::all)]
98
99// Core modules
100pub mod error;
101pub mod models;
102pub mod providers;
103pub mod service;
104
105// Re-exports for convenience
106pub use error::{BillingError, Result};
107pub use models::{Account, Bill, Provider, ProviderConfig};
108
109/// Library version
110pub const VERSION: &str = env!("CARGO_PKG_VERSION");
111
112/// Initialize the billing library
113///
114/// This function should be called once at the start of your application.
115/// It initializes the cloud provider registry and sets up logging.
116pub async fn init() -> Result<()> {
117    tracing::info!("Initializing cbilling library v{}", VERSION);
118
119    // Initialize providers registry
120    providers::registry::init().await?;
121
122    tracing::info!("Cloud-billing library initialized successfully");
123    Ok(())
124}
125
126#[cfg(test)]
127mod tests {
128    use super::*;
129
130    #[test]
131    fn test_version() {
132        assert!(!VERSION.is_empty());
133    }
134
135    #[tokio::test]
136    async fn test_init() {
137        let result = init().await;
138        // Initialization might fail if credentials are not configured,
139        // which is expected in tests
140        assert!(result.is_ok() || result.is_err());
141    }
142}