1 unstable release
Uses new Rust 2024
0.1.0 | May 17, 2025 |
---|
#703 in Web programming
118 downloads per month
36KB
182 lines
supplier_kit
A modular toolkit for managing and grouping dynamic data suppliers.
supplier_kit
helps you build robust and extensible architectures that rely
on multiple external or internal data providers — known as suppliers. It is ideal
for use cases such as federated API calls, service orchestration, or data aggregation
(e.g., e-commerce platforms).
✨ Features
Supplier
trait: defines a common interface for all data providersSupplierRegistry
: a container for registering and accessing suppliers by nameSupplierGroup
: abstraction to query multiple suppliers in a batchSupplierGroupResult
: returns per-supplier successes and failuresregister_suppliers!
macro: for easy supplier registration- Utility helpers like
add_supplier_from_registry
andadd_suppliers_from_registry
as an option
🔧 Use Cases
- Aggregating product listings from multiple platforms
- Wrapping multiple internal microservices behind unified access
- Resilient systems that gracefully handle partial failure
🚀 Quick Start
Example: Registering and Querying Multiple Suppliers
This example demonstrates how to use SupplierRegistry
and BasicSupplierGroup
to register multiple suppliers, group them, and execute a Search
operation.
It includes:
- Using the
register_suppliers!
macro - Handling partial failures using
add_suppliers_from_registry
- Group querying with
SupplierGroup
trait
use supplier_kit::models::{SupplierRequest, SupplierResponse, SupplierOperation};
use supplier_kit::supplier::{Supplier, SupplierRegistry};
use supplier_kit::supplier_group::{SupplierGroup, BasicSupplierGroup, SupplierGroupResult};
use supplier_kit::errors::SupplierError;
use supplier_kit::register_suppliers;
use serde_json::json;
use supplier_kit::utils::add_suppliers_from_registry;
struct MockSupplier {
name: String,
should_fail: bool,
}
impl MockSupplier {
fn new(name: &str, should_fail: bool) -> Self {
Self {
name: name.to_string(),
should_fail,
}
}
}
impl Supplier for MockSupplier {
fn name(&self) -> &str {
&self.name
}
fn query(&self, request: SupplierRequest) -> Result<SupplierResponse, SupplierError> {
if self.should_fail {
Err(SupplierError::Internal(format!("{} failed", self.name)))
} else {
Ok(SupplierResponse {
data: json!({
"supplier": self.name,
"params": request.params
}),
})
}
}
}
fn main() -> Result<(), SupplierError> {
let mut registry = SupplierRegistry::new();
register_suppliers!(
registry,
"s1" => MockSupplier::new("s1", false),
"s2" => MockSupplier::new("s2", true),
"s3" => MockSupplier::new("s3", false),
);
let mut group = BasicSupplierGroup::new("example_group");
let failures = add_suppliers_from_registry(&mut group, ®istry, &["s1", "s2", "s4"]);
if !failures.is_empty() {
for (name, err) in failures {
println!("Failed to add '{}': {}", name, err);
}
}
let request = SupplierRequest {
operation: SupplierOperation::Search,
params: json!({ "keyword": "laptop" }),
};
let result: SupplierGroupResult = group.query(request);
println!("Successes:");
for (name, response) in result.successes {
println!("- [{}] Response: {}", name, response.data);
}
println!("Failures:");
for (name, error) in result.failures {
println!("- [{}] Error: {}", name, error);
}
Ok(())
}
📄 License
Licensed under the Apache-2.0 license
👨 Author
Jerry Maheswara jerrymaheswara@gmail.com
❤️ Built with Love in Rust
This project is built with ❤️ using Rust — a systems programming language that is safe, fast, and concurrent.
Rust is the perfect choice for building reliable and efficient applications.
🤝 Contributing
Pull requests, issues, and feedback are welcome!
If you find this crate useful, give it a ⭐ and share it with others in the Rustacean community.
Dependencies
~0.6–1.5MB
~33K SLoC