--- id: TASK-120 title: Universal Profiles × EncryptID integration status: In Progress assignee: [] created_date: '' updated_date: '2026-04-10 23:25' labels: [] dependencies: [] priority: high --- ## Description Give every EncryptID user a LUKSO Universal Profile (LSP0 + LSP6) on Base, controlled by their passkey-derived secp256k1 key. ## Phase 1: Core (DONE) - [x] EVM key derivation (`encryptid-sdk/src/client/evm-key.ts`) — HKDF secp256k1 from PRF - [x] UP deployment service (`encryptid-up-service/`) — Hono API with CREATE2, LSP6 permissions, LSP25 relay - [x] SDK types — `eid.up` in JWT claims, `LSP6Permission` enum, UP request/response types - [x] Session UP helpers — `getUPAddress()`, `hasUniversalProfile()`, `setUniversalProfile()` - [x] Recovery hooks — `onUPRecovery()` for on-chain controller rotation - [x] Schema migration — UP columns on users table - [x] Server endpoints — `GET/POST /api/profile/:id/up`, UP info in JWT claims ## Phase 2: UP-Aware Sessions - [x] Map EncryptID AuthLevel → LSP6 BitArray permissions (scaffolding — `lsp6.ts` mapper) - [ ] Guardian → LSP6 controller mapping with ADDPERMISSIONS - [ ] On-chain permission write (requires LSP factory deployment) ## Phase 3: Payment-Infra Migration - [x] WalletAdapter abstraction (UP + Safe + EOA) — `wallet-adapter.ts` - [ ] New users → UP by default ## Phase 4: NLA Oracle Integration - [x] `getEncryptIDWallet()` for CLI — `wallet-helper.ts` - [ ] Escrow parties identified by UP address ## Notes - encryptid-up-service repo: https://gitea.jeffemmett.com/jeffemmett/encryptid-up-service - Chain: Base Sepolia (84532) for dev, Base mainnet for prod - LSP contracts are EVM-compatible, deployed on Base ## Implementation Notes **2026-04-10 Architecture Decision — Chain-Parameterized WalletAdapter:** Phase 3 WalletAdapter MUST be built with `chainId` parameter from day one, not Base-hardcoded. This enables adding Linea (59144/59141) or any EVM L2 as: add chain config → deploy LSP factory → done. Add Linea to CHAIN_MAP alongside the adapter work. CREATE2 determinism should work on Linea's zkEVM but LSP factory contracts need deployment there. Current state: wallet module reads 13+ chains but UP write operations are Base-only. ## Phases 2-4 Implementation (2026-04-10) - **Linea chain support**: Added Linea mainnet (59144) + Linea Sepolia (59141) to all 6 chain maps in rwallet/mod.ts, price-feed, defi-positions, wallet-viewer, and encryptid server CHAIN_PREFIXES. Popular tokens: USDC, WETH, USDT on Linea. - **WalletAdapter** (`src/encryptid/wallet-adapter.ts`): Chain-parameterized abstraction over Safe/EOA/UP with `fromSafe()`, `fromEOA()`, `fromUP()` factories, immutable `withUniversalProfile()`, `getInfo()`, `toJSON()`. - **LSP6 Permission Mapper** (`encryptid-sdk/src/types/lsp6.ts`): 23-bit `LSP6Permission` enum, `buildBitmap()`, `hasPermission()`, `mergePermissions()`, `AUTH_LEVEL_PERMISSIONS` mapping BASIC→CRITICAL, `GUARDIAN_PERMISSIONS`, `getPermissionsForAuthLevel()`. Removed duplicate inline enum from types/index.ts. - **getEncryptIDWallet()** (`encryptid-sdk/src/client/wallet-helper.ts`): SDK helper returns read-only `EncryptIDWalletInfo` snapshot (EOA, DID, username, UP, auth level, compressed pubkey) for CLI/oracle. Never exposes private keys. - **SDK exports**: All new types/functions re-exported from types/index.ts, client/index.ts, src/index.ts. - Deployed to production. rspace.online returns 200.