1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
//! # better-bucket
//!
//! A genuinely better token bucket for Rust. The hot path — `try_acquire` — is
//! designed to be **lock-free**, **allocation-free**, and **cache-aligned**: a
//! single compare-and-swap over a packed `(tokens, last_refill_tick)` word.
//! Refill is **lazy**, computed from a monotonic clock the instant you ask, so
//! an idle bucket costs nothing — no background timer thread, no per-tick
//! wakeups. The defining correctness property is that the bucket **never
//! over-grants**: across any concurrent interleaving, the total tokens handed
//! out never exceed capacity plus accrued refill.
//!
//! The crate is a single-purpose primitive. It owns token-bucket accounting and
//! nothing else, so it can sit at the bottom of a dependency tree (its first
//! consumer is the `rate-net` rate limiter) without dragging in an async
//! runtime or a keyed-state store.
//!
//! ## Guarantees
//!
//! The safety contract holds under any concurrent interleaving, adversarial
//! input, and extreme uptime: **no panic, no wrap, no over-grant, and tokens
//! always within `[0, capacity]`.** It is defended by `loom` model checking, a
//! multi-thread stress test, an allocation audit, an adversarial/edge suite, and
//! `proptest`. `try_acquire` is a single `compare_exchange_weak` on a packed
//! atomic word — allocation-free, cache-line aligned, with a division-free
//! fixed-point refill. The bucket's own accounting measures a few nanoseconds;
//! end-to-end `try_acquire` is bounded by the monotonic clock read (see
//! `docs/BENCHMARKS.md`).
//!
//! Token bucket is the crate's sole algorithm by design — leaky-bucket and
//! sliding-window limiting live in the downstream `rate-net` crate.
//!
//! ```
//! # #[cfg(feature = "clock")] {
//! use better_bucket::Bucket;
//!
//! // 100 tokens per second, capacity 100.
//! let bucket = Bucket::per_second(100);
//!
//! if bucket.try_acquire(1) {
//! // allowed — do the work
//! } else {
//! // denied — shed load / return 429 / back off
//! }
//! # }
//! ```
//!
//! The bucket reads time from [`clock-lib`](https://crates.io/crates/clock-lib);
//! the `clock` feature (on by default) provides it and implies `std`. The
//! lock-free accounting core needs only `core`, but the shipped `Bucket`
//! constructors read the clock, so a bare `no_std` build
//! (`default-features = false`) exposes only [`VERSION`].
//!
//! ## Design goals
//!
//! - **Lock-free acquire.** One `compare_exchange_weak` on a packed atomic
//! word; no `Mutex`, no parking on the hot path.
//! - **Allocation-free steady state.** A bucket is a small, cache-line-aligned
//! value with no heap tail; acquiring never allocates.
//! - **Lazy refill.** Tokens accrue from elapsed monotonic time on access — no
//! timer thread, no wakeups, no watts burned while idle.
//! - **Overflow-safe.** Every refill and capacity computation is checked or
//! saturating; a hostile request count or a multi-day idle gap can neither
//! wrap the counter nor over-fill the bucket.
//! - **`no_std`-capable.** The core runs without the standard library; the
//! caller drives time when `std` is disabled.
//!
//! ## Feature flags
//!
//! | Feature | Default | Description |
//! |---------|---------|-------------|
//! | `std` | yes | Standard library. Off → `no_std`, caller drives time. |
//! | `clock` | yes | Pluggable [`clock-lib`](https://crates.io/crates/clock-lib) time source plus a mockable clock for deterministic tests. |
// `no_std` for the library build when `std` is off, but always link `std` under
// `test` so the unit-test harness (and dev-dependencies) have what they need.
// The token-bucket surface requires a clock to read time and a `Mutex` for the
// simple implementation; both are gated on `clock` (which implies `std`). The
// no_std, caller-driven core arrives with the lock-free rewrite in 0.3.
pub use crate;
pub use crateBucketBuilder;
pub use crateBucketConfig;
pub use crateDecision;
pub use crateBucketError;
/// The version of this crate, taken from `Cargo.toml` at compile time.
///
/// Exposed so a consumer can report the exact `better-bucket` build it links
/// against — useful in diagnostics and version-skew checks across a dependency
/// tree.
///
/// # Examples
///
/// ```
/// // Reports the crate version as a `major.minor.patch` string.
/// let version = better_bucket::VERSION;
/// assert!(version.starts_with("1."));
/// assert_eq!(version.split('.').count(), 3);
/// ```
pub const VERSION: &str = env!;