Recovery UI for discovering and operating EVM ZeroDev Kernel loan wallets if satsterminal ceases to exist or the hosted service is unavailable.
Scope: EVM loans only. Solana loans are not supported.
This app is frontend-only:
- No backend signer
- No database
- No paymaster abstraction
- All signatures happen in your connected wallet
- Derives deterministic ZeroDev Kernel v3.3 smart account addresses from your EOA + wallet index.
- Scans index ranges across chains to find deployed loan wallets.
- Reads balances + loan data from Aave and Morpho.
- Submits rescue actions through ERC-4337 UserOperations (EntryPoint v0.7):
- Repay debt
- Withdraw collateral
- Transfer out collateral token balance
- Smart account: ZeroDev Kernel v3.3
- Chains: Ethereum (
1), Base (8453), Arbitrum (42161), BNB Chain (56) - Aave V3:
- Reads + rescue actions on supported chains
- Morpho Blue:
- Reads + rescue actions
- Market ID:
0x9103c3b4e834476c9a62ea009ba2c884ee42e94e6e314a26f04d312434191836
- Node.js
>=20 - npm
- Browser wallet with EIP-1193 support (MetaMask, Rabby, etc.)
- Optional WalletConnect Project ID (only needed if you want WalletConnect in UI)
npm install
cp .env.example .envRecommended .env values:
NEXT_PUBLIC_THIRDWEB_CLIENT_ID=your_thirdweb_client_id
NEXT_PUBLIC_ALCHEMY_API_KEY=your_alchemy_api_key
NEXT_PUBLIC_WALLETCONNECT_PROJECT_ID=your_walletconnect_project_idIf you do not set the WalletConnect value, injected wallets still work.
The thirdweb client ID is optional but preferred. When set, the wallet page uses thirdweb as the default chain RPC and only reveals the manual RPC field if that endpoint stops responding.
If thirdweb is unavailable, the UI tells the user to paste an Alchemy HTTPS endpoint as the fallback. If neither thirdweb nor Alchemy is configured in .env, the wallet page shows an Alchemy API key field immediately and does not fall back to public RPCs.
Use a public thirdweb client ID here, not a secret key. You still only need a ZeroDev project/bundler value when you want to submit rescue UserOperations.
npm run devOpen: http://localhost:3000
npm run lint
npm run build- You must export your private key from the Sats Terminal dashboard first.
- Import that private key into MetaMask/Rabby (or another EIP-1193 wallet), then connect that imported wallet to this recovery UI.
- Open the app.
- Connect that same imported EOA from the top-right wallet button.
- Do not connect a different wallet, or the derived wallet IDs/Kernel addresses will not match your loan.
- Never paste private keys into this recovery UI. Private keys should only be imported in your wallet application.
- Go to
/scan. - Set:
Start indexEnd index- Chain checkboxes to scan
- Click Start scan.
- The app will request chain switches while scanning each chain.
- Click any result row to open
/wallet/<index>.
Notes:
- Max scan size per run is
2,000indices. - Use Show only deployed wallets to filter noise.
You can skip scanning if you already know the wallet ID (index).
Open /wallet/<wallet-id> directly to access that exact loan wallet.
Example: /wallet/12
You receive this wallet ID in the loan activation email sent to your email address when your loan is completed/activated.
- The page derives and displays the Kernel loan wallet address.
- Use Copy address and fund this smart wallet with:
- Native gas token (required for all rescue actions)
- Repay token (required for repay actions)
- Select chain in the chain dropdown if needed.
- Click Load positions to fetch:
- Wallet balances
- Aave loan details
- Morpho loan details (Base market above)
- How to get your ZeroDev Project ID:
- Open https://dashboard.zerodev.app/projects/general and sign in.
- Open your project (or create one if none exists).
- Copy the Project ID shown in the top-right of the project page.
- In ZeroDev Project ID or RPC URL, paste either:
- A ZeroDev project ID, or
- A full bundler URL (example:
https://rpc.zerodev.app/api/v3/<project-id>/chain/<chain-id>)
- Rescue action buttons stay disabled until this input is valid.
- The chain RPC field is normally hidden. It appears only if the default RPC for the selected chain is not responding, or if you already entered a custom override.
- If neither thirdweb nor Alchemy is configured in
.env, the wallet page shows an Alchemy API Key field immediately. - Default RPC priority is: thirdweb client ID from
.env-> Alchemy key from.env-> pasted Alchemy API key in the wallet UI. No public RPC fallback.
- Choose action: Withdraw collateral or Repay debt
- Choose full amount toggle or custom amount
- Click Execute Aave action via Kernel
- If using Repay all, keep a little extra loan token (for example USDC/USDT) in the loan/kernel wallet, because interest accrues in real time and debt can increase slightly before execution.
Behavior:
- Repay sends 2 UserOps:
- Approve repay token to pool
- Repay
- Withdraw sends 1 UserOp.
- Choose action: Withdraw collateral or Repay debt
- Choose full amount toggle or custom amount
- Click Execute Morpho action via Kernel
- If using Repay all, keep a little extra loan token (for example USDC/USDT) in the loan/kernel wallet, because interest accrues in real time and debt can increase slightly before execution.
- In wallet balances section, click Transfer all to connected wallet for the collateral token card.
- Each action surfaces status text and a UserOp hash.
- Verify token balances and debt/collateral changes by clicking Load positions again.
Before executing actions:
- Connected wallet is on the intended chain.
- Loan wallet has enough native gas token.
- Repay token is funded to the loan wallet for repay flows.
- Bundler input is set correctly.
- Amount + action are correct (especially full-withdraw/full-repay toggles).
-
Switch your wallet to <chain>:- Use chain selector and approve wallet switch prompt.
-
Action button disabled:
- Missing/invalid bundler input, missing/invalid Alchemy API key or custom RPC override, invalid amount, or an action is already submitting.
-
No gaswarning:- Send native gas token to the loan wallet address shown on the page.
-
Morpho USD fields show
—:- Click Load positions again.
- Check browser console for
Morpho summary fetch failedto see exact read-path failure details. - Current logic tries:
- Configured RPC read (backend-style)
- Wallet provider read fallback
- Raw onchain contract read fallback
-
Scan is slow:
- Reduce range size and/or number of selected chains.
app/: Next.js routes and UIlib/kernel/: deterministic Kernel address derivationlib/accountAbstraction/: UserOperation construction and submissionlib/protocols/: Aave, Morpho, ERC-20, Kernel calldata helperslib/chains.ts,lib/assets.ts: chain and token configuration
npm run dev
npm run build
npm run start
npm run lint- Never paste or type private keys into this app.
- Always validate addresses, chain, and amounts before signing.
- You are fully responsible for transaction execution and operational safety.
This software is provided as-is, without warranties. You are responsible for validating transactions and operational safety before signing.
MIT
