Démarrage rapide
Quickstart : créer une facture en Rust
Pas de SDK officiel — utiliser reqwest + serde_json
Pas de SDK Rust officiel pour Scell.io. Le combo standard est `reqwest` (HTTP client async/blocking) + `serde` + `serde_json`. Compatible avec Tokio et async-std. Pour des intégrations production, ajouter `reqwest-middleware` + `reqwest-retry` (retries exponentiels). La sérialisation JSON snake_case se fait nativement avec `#[derive(Serialize, Deserialize)]`. Idéal pour services microservices, Tauri (desktop), ou serverless (Cloudflare Workers via `worker-rs`). Cible : Rust stable (édition 2021+).
À retenir
- Prérequis : Rust stable 1.75+, Cargo
- Pas de SDK officiel : `reqwest` + `serde_json`
- Variable d'env : `std::env::var("SCELL_API_KEY")`
- HTTP : `reqwest` 0.12+ (avec feature `json`)
- Output attendu : `serde_json::Value` ou struct typée
- Codes erreur : `response.error_for_status()` + `Result<T, reqwest::Error>`
Exemple de code
// Cargo.toml: reqwest = { version = "0.12", features = ["json"] }
// tokio = { version = "1", features = ["full"] }
// serde_json = "1"
// uuid = { version = "1", features = ["v4"] }
use serde_json::{json, Value};
use uuid::Uuid;
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
let key = std::env::var("SCELL_API_KEY")?;
let http = reqwest::Client::new();
let call = |path: &'static str, body: Value| {
let http = http.clone();
let key = key.clone();
async move {
let r = http.post(format!("https://api.scell.io/api/v1{}", path))
.header("X-API-Key", &key)
.header("Idempotency-Key", Uuid::new_v4().to_string())
.json(&body).send().await?.error_for_status()?
.json::<Value>().await?;
Ok::<Value, reqwest::Error>(r)
}
};
let seller = json!({
"siret": "12345678901234", "name": "Ma SAS", "vat_number": "FR12345678901",
"address": {"street": "1 rue Test", "city": "Paris", "postal_code": "75001", "country": "FR"}
});
let b2b = call("/invoices", json!({
"format": "factur-x", "profile": "EN16931", "currency": "EUR", "seller": seller,
"buyer": {"siret": "98765432109876", "name": "Client SARL",
"address": {"street": "2 avenue Demo", "city": "Lyon", "postal_code": "69001", "country": "FR"}},
"lines": [{"description": "Prestation conseil", "quantity": 1, "unit_price": 1000.0, "vat_rate": 20.0}]
})).await?;
println!("B2B: {} ({})", b2b["id"], b2b["status"]);
let b2c = call("/invoices", json!({
"format": "factur-x", "profile": "EN16931", "currency": "EUR", "seller": seller,
"buyer": {"buyer_is_individual": true, "name": "Jean Dupont", "email": "jean@example.com",
"address": {"street": "3 bd Client", "city": "Marseille", "postal_code": "13001", "country": "FR"}},
"lines": [{"description": "Abonnement", "quantity": 1, "unit_price": 49.90, "vat_rate": 20.0}]
})).await?;
println!("B2C: {} ({})", b2c["id"], b2c["status"]);
let sig = call("/signatures", json!({
"document_url": "https://example.com/contrat.pdf",
"signers": [{"name": "Jean Dupont", "email": "jean@example.com", "phone": "+33612345678"}],
"signature_options": {"signature_mode": "drawn", "timezone": "Europe/Paris"}
})).await?;
println!("Signature: {} -> {}", sig["id"], sig["signing_url"]);
Ok(())
}