واجهة برمجية غير متزامنة مبنية على Tokio. تتصل بخادم واحد، وتحجز مفتاحًا ثم تعيده فورًا.
use std::time::Duration;
use ticketing::TicketBroker;
let broker = TicketBroker::connect(["127.0.0.1:5225"]);
broker.wait_ready(Duration::from_secs(5)).await;
let wait = Duration::from_secs(5);
let lease = Duration::from_secs(30);
let ticket = broker.acquire("key", wait, lease).await.unwrap();
ticket.release().await.unwrap();
println!("pass");مثال يتحقق من أن عدة مهام (tasks) تُجري إيداعات وسحوبات متكررة عبر قفل خاص بكل حساب دون تعارض، وأن الرصيد يعود دائمًا إلى قيمته الأولية. يمكن استنساخ (Clone) TicketBroker لمشاركته بين عدة مهام.
async fn transaction(broker: &TicketBroker, account: usize, delta: i64) {
let key = format!("account-{account}");
let _ticket = match broker.acquire(&key, WAIT, LEASE).await {
Ok(ticket) => Some(ticket),
Err(e) => {
tracing::error!("account {account} acquire failed: {e}");
return;
}
};
// منطقة حرجة آمنة فقط أثناء الاحتفاظ بالقفل
let before = balances[account];
tokio::task::yield_now().await;
balances[account] = before + delta;
// عند إسقاط ticket، يتم إرجاعه تلقائيًا في الخلفية (يمكن حذفه إذا لم تكن هناك حاجة للإرجاع الفوري)
let (action, sign) = if delta < 0 { ("withdraw", '-') } else { ("deposit", '+') };
tracing::info!("account {account} {action} {sign}${AMOUNT} -> ${}", balances[account]);
}راجع الأمثلة الكاملة في tests/example_simple.rs, tests/example_bank.rs, tests/bench_test.rs.