Security model¶
What trusts what, what can go wrong, and how the blast radius is bounded — for the two parties in every Edith integration: your app and your users.
The short version: your users' existing wallets sit outside the trust boundary entirely, your app's spend is prepaid and capped, and the entire smart-contract surface is ~550 lines of immutable, single-purpose code.
Your users: what interacting with Edith exposes¶
A user onboarded through Edith — including through
gasless smart accounts — signs one
message per operation (an EIP-191 personal_sign of the operation's hash).
That is the entire footprint. Concretely:
- No token approvals, no allowances, no delegation. Nothing in the flow grants Edith — or the contracts — any standing permission over the user's wallet. The funds in their existing wallet are unreachable by design, before, during, and after.
- One signature authorizes exactly one operation. The signed hash commits to the chain, the EntryPoint, and the account's nonce — it cannot be replayed, reused, or applied to a different operation.
- The smart account is owner-locked and immutable. Its owner (the user's EOA) and EntryPoint are fixed at deployment — no proxy, no upgrade path, no admin function. Only operations signed by the owner validate, and only the EntryPoint (after that validation) or the owner can execute. Edith cannot move anything the account holds.
- The account address is bound to its owner. Addresses derive from the owner via CREATE2 — nobody can deploy "your" account address with a different owner.
- Gas sponsorship risks Edith's funds, not the user's. The paymaster can only spend its own EntryPoint deposit; by ERC-4337 design it has no path to user assets.
The trust that remains: the operation a user signs is built by Edith's backend, and today it is presented as a hash. A compromised backend could present a hash for a different operation — bounded strictly to the smart account's own assets, never the user's wallet. Human-readable EIP-712 signing (wallets rendering the operation as structured fields) is on the roadmap to close this gap.
Your app: what an API key exposes¶
Your API key is a bearer credential against a prepaid USD balance — so the worst case is bounded by construction:
- Prepaid, never open-ended. An account can only spend what was deposited. There is no credit, no overdraft, no surprise invoice.
- Layered caps below the balance ceiling: an optional
maxUSDper submission, a per-transaction limit, and a daily limit with tracked consumption — each with a distinct error code so breaches are diagnosable. - A failure circuit breaker can halt an account on a streak of failed transactions — a runaway loop stops itself.
- The key belongs on your backend. End users never talk to Edith directly; your server holds the key and your authentication decides which users deserve a sponsored transaction. (This split is inherent to sponsorship — only you know who your users are.)
The contract surface¶
All Edith contracts together — the smart account, its factory, the verifying paymaster, the ERC-4337 library, and the execution/routing contracts — total roughly 550 normalized source lines. Small enough to read in a sitting, with a design bias to match: immutable deployments, single owners, no upgradeability, canonical EntryPoint v0.7 (Edith's off-chain signing and hashing are verified against the real EntryPoint bytecode in CI).
Current status, plainly¶
- Edith runs on testnets today; nothing in the current environment carries monetary value.
- The contracts are not yet audited. An external audit and human-readable (EIP-712) signing are prerequisites we hold ourselves to before any mainnet deployment.
- Per-end-user policy controls (per-wallet quotas, target-contract allowlists) are on the roadmap; today, per-user throttling is the app's responsibility and the account-level caps bound the damage regardless.
Found something? Reach your Edith contact (see Get API access) — security reports get priority.