You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
The cross-contract integration primitive. Returns `true` when the wallet's score is **strictly below**`gate_threshold` (safe to proceed), and `false` when the score is `>= gate_threshold`**or no score exists**. It is **infallible** (returns `bool`, never an error), **never panics**, and is **side-effect free** — designed to be called directly from inside another protocol's guard clause. See [Composability](#composability) and [`docs/interface-spec.md`](docs/interface-spec.md).
Runtime capability detection for the composability interface. Returns `true` for the registered capabilities `score`, `history`, `batch`, `gate`, and `aggr`, letting integrators feature-detect instead of hardcoding contract version numbers.
90
+
85
91
### `RiskScore` Structure
86
92
87
93
```rust
@@ -91,6 +97,7 @@ pub struct RiskScore {
91
97
pubml_flag:bool, // True if ML classifier flagged
92
98
pubtimestamp:u64, // Ledger timestamp of last update
93
99
pubconfidence:u32, // Model confidence 0-100
100
+
pubmodel_version:u32, // Detection-pipeline model version
94
101
}
95
102
```
96
103
@@ -143,6 +150,48 @@ A wallet scoring 60-70 on three pairs individually might not breach the per-pair
143
150
144
151
`get_aggregate_score` iterates the wallet's full pair list, so its cost is O(N) in the number of distinct pairs the wallet has scores for. The contract is designed around a practical maximum of `MAX_WALLET_PAIRS` (20) pairs per wallet; this is documented as a constant but not enforced on-chain.
145
152
153
+
## Composability
154
+
155
+
LedgerLens is only useful if other protocols can actually *act* on its scores. A risk score that lives in isolation is a dashboard widget; a risk score that an AMM, a lending market, or a DEX aggregator can read mid-transaction is a shared fraud-prevention layer for the entire Stellar DeFi ecosystem.
156
+
157
+
The problem with composing on a raw getter is fragility. If every integrator reverse-engineers `get_score` and decodes the `RiskScore` struct by hand, then the day we add a field or change an error code, every downstream protocol breaks silently. So LedgerLens exposes a **stable, versioned composability interface** — `ILedgerLensScore` — as the canonical integration point. It is fully specified in [`docs/interface-spec.md`](docs/interface-spec.md); the headline function is `query_risk_gate`.
158
+
159
+
### Why a dedicated gate function?
160
+
161
+
A guard clause inside someone else's contract has hard requirements that a normal getter doesn't meet:
162
+
163
+
-**It must never panic.** A panic in a cross-contract call traps the *caller's* transaction. If LedgerLens could panic, an attacker could craft inputs that disable the AMM's risk guard — or simply burn its gas. So `query_risk_gate` returns a plain `bool` and is engineered to be infallible.
164
+
-**It must fail closed.** Because the answer is a single `bool`, the "we have no score for this wallet" case has to collapse to one value — and that value is `false`. Unknown wallets are treated as *potentially risky*, not waved through.
165
+
-**It must be cheap and side-effect free.** It is a pure read that doesn't even extend storage TTL, so calling it from a hot path is safe.
166
+
167
+
### The AMM pattern
168
+
169
+
Here is the entire integration — drop `query_risk_gate` into your swap guard and refuse risky wallets:
A complete, compiling reference contract lives in [`examples/amm_gate.rs`](examples/amm_gate.rs) (build it with `cargo build --example amm_gate -p ledgerlens-score`). For versioning, error-code stability, threshold selection, and caching guidance, read the full [interface specification](docs/interface-spec.md).
194
+
146
195
## Security Features
147
196
148
197
1.**Authorization Checks**: Only the authorised LedgerLens service account can submit scores
0 commit comments