8.8 KiB
8.8 KiB
Edut Secret System - Wallet-First Designation + Membership Spec
Overview
The Edut onboarding flow is deterministic and wallet-first:
- Visitor requests designation intent from
edut.ai. - Server issues one-time typed-data payload (
nonce,deadline,price,currency). - Visitor signs intent with wallet (identity proof, no value transfer).
- Server verifies signature and creates/updates designation record.
- Visitor mints paid EDUT membership on-chain (intent proof).
- Server confirms transaction and marks membership active.
- Visitor downloads the EDUT platform app from post-mint success links.
This flow is the pre-launch identity and commerce envelope. It is not a throwaway waitlist.
User Experience Sequence (Continue Flow)
- Initial page state: orb, identity text, footer links.
- First click anywhere: globe spin intensifies,
continueappears. - Click
continue: wallet explainer appears. - User selects
I have a walletorI need a wallet. I need a walletshows install guidance and remains in-page.I have a wallettriggers wallet connection request.- Page calls
POST /secret/wallet/intent. - Wallet signs EIP-712 typed intent.
- Page calls
POST /secret/wallet/verify. - Page requests membership quote via
POST /secret/membership/quote. - Wallet submits membership mint transaction on Base.
- Page confirms via
POST /secret/membership/confirmand/or status poll. - UI shows
acknowledged · {token}when membership is active. - Post-mint success state presents
download your platformlinks (Desktop/iOS/Android). - Download endpoints perform wallet membership status checks before channel authorization messaging.
- Member opens the app, signs in with the same wallet, and receives platform updates through app notifications.
Privacy and Terms links bypass flow and navigate normally.
Architecture
Landing page -> POST /secret/wallet/intent
Wallet signs typed intent (EIP-712)
Landing page -> POST /secret/wallet/verify
Landing page -> POST /secret/membership/quote
Wallet sends paid mint tx on Base
Landing page -> POST /secret/membership/confirm
Membership active -> acknowledged state
Post-mint success -> app download links (Desktop/iOS/Android)
Core Commerce Rule
- Membership is required to purchase marketplace offers.
- Membership is not a product/module license.
- Offer-specific licenses/entitlements are purchased separately.
- Membership purchase delivers initial platform access (download entry point) immediately after activation.
Infrastructure
| Service | Domain / Endpoint | Purpose |
|---|---|---|
| Landing UI | edut.ai, edut.dev |
Continue flow + wallet intent/signature + membership mint UX |
| API | api.edut.ai/secret/wallet/intent |
Create one-time designation intent |
| API | api.edut.ai/secret/wallet/verify |
Verify signature and bind wallet identity |
| API | api.edut.ai/secret/membership/quote |
Return current payable membership quote |
| API | api.edut.ai/secret/membership/confirm |
Confirm membership tx and activation state |
| Chain | Base | Membership mint settlement and evidence |
| Database | /var/lib/edut/secrets.db |
Durable designation + membership state |
Deterministic State Machine
pending_signature -> signature_verified -> pending_membership_mint -> membership_active
Additional side states:
intent_expiredquote_expiredtx_unconfirmedrejected(invalid signature, wrong chain, mismatched wallet)rate_limited
Rules:
- No backwards transition except administrative recovery event with audit entry.
membership_activerequires successful on-chain payment confirmation.- Signature and quote nonces are single-use; replay attempts are rejected.
- Acknowledged UI state requires
membership_active.
API Contracts
1) Wallet Intent
POST /secret/wallet/intent
Request JSON:
{
"address": "0xabc123...",
"origin": "https://edut.ai",
"locale": "en",
"chain_id": 8453
}
Behavior:
- Normalize and validate wallet address format.
- Validate
originagainst allowlist. - Enforce rate limits (IP + address + rolling windows).
- Generate designation
code,auth_token, nonce, and intent TTL. - Persist
pending_signaturestate. - Return typed-data envelope fields required for signing.
Response:
{
"intent_id": "wi_...",
"designation_code": "0217073045482",
"display_token": "0217-0730-4548-2",
"nonce": "f2e9...",
"issued_at": "2026-02-17T07:30:45Z",
"expires_at": "2026-02-17T07:40:45Z",
"domain_name": "EDUT Designation",
"chain_id": 8453,
"verifying_contract": "0x0000000000000000000000000000000000000000"
}
2) Wallet Verify
POST /secret/wallet/verify
Request JSON:
{
"intent_id": "wi_...",
"address": "0xabc123...",
"chain_id": 8453,
"signature": "0x..."
}
Behavior:
- Load pending intent by
intent_id. - Verify not expired and not consumed.
- Reconstruct typed payload exactly as issued.
- Recover signer and compare to declared address.
- Validate chain allowlist and origin.
- Transition to
signature_verifiedandpending_membership_mint.
Response:
{
"status": "signature_verified",
"designation_code": "0217073045482",
"display_token": "0217-0730-4548-2",
"verified_at": "2026-02-17T07:31:12Z"
}
3) Membership Quote
POST /secret/membership/quote
Request JSON:
{
"designation_code": "0217073045482",
"address": "0xabc123...",
"chain_id": 8453
}
Behavior:
- Verify
signature_verifiedstatus for designation/address pair. - Fetch current policy (
currency,amount,deadline,contract). - Return quote payload for client-side transaction submission.
Response:
{
"quote_id": "mq_...",
"chain_id": 8453,
"currency": "USDC",
"amount": "5.00",
"amount_atomic": "5000000",
"deadline": "2026-02-17T07:36:12Z",
"contract_address": "0x...",
"method": "mintMembership",
"calldata": "0x..."
}
4) Membership Confirm
POST /secret/membership/confirm
Request JSON:
{
"designation_code": "0217073045482",
"quote_id": "mq_...",
"tx_hash": "0x...",
"address": "0xabc123...",
"chain_id": 8453
}
Behavior:
- Validate quote ownership and expiry.
- Verify tx inclusion and success on allowed chain.
- Validate minted membership recipient and amount policy.
- Transition to
membership_active. - Emit activation evidence receipt.
Response:
{
"status": "membership_active",
"designation_code": "0217073045482",
"display_token": "0217-0730-4548-2",
"tx_hash": "0x...",
"activated_at": "2026-02-17T07:33:09Z"
}
Security Controls
- Intent TTL and one-time nonce consumption.
- Quote TTL with explicit
deadline. - Strict origin allowlist for intent and verify endpoints.
- Chain allowlist enforcement.
- Signature and quote replay prevention.
- IP + address rate limits on all public endpoints.
- Deterministic audit trail for signature and payment confirmation.
- No private key handling server-side.
Data Model (SQLite)
File: /var/lib/edut/secrets.db
CREATE TABLE IF NOT EXISTS designations (
id INTEGER PRIMARY KEY AUTOINCREMENT,
code TEXT NOT NULL UNIQUE,
auth_token TEXT NOT NULL,
status TEXT NOT NULL DEFAULT 'pending_signature',
wallet_address TEXT,
chain_id INTEGER,
intent_id TEXT UNIQUE,
intent_nonce TEXT,
intent_issued_at DATETIME,
intent_expires_at DATETIME,
signature TEXT,
signature_verified_at DATETIME,
membership_quote_id TEXT,
membership_currency TEXT,
membership_amount_atomic TEXT,
membership_quote_expires_at DATETIME,
membership_tx_hash TEXT,
membership_activated_at DATETIME,
origin TEXT,
locale TEXT,
created_at DATETIME DEFAULT (datetime('now'))
);
CREATE INDEX idx_designations_code ON designations(code);
CREATE INDEX idx_designations_wallet ON designations(wallet_address);
CREATE INDEX idx_designations_status ON designations(status);
CREATE INDEX idx_designations_intent ON designations(intent_id);
CREATE INDEX idx_designations_quote ON designations(membership_quote_id);
CREATE INDEX idx_designations_created ON designations(created_at);
Launch-Day Activation Messaging
At launch, membership_active records are eligible for access-level updates and marketplace onboarding.
NGINX Routing (Example)
location /secret/wallet/intent {
proxy_pass http://127.0.0.1:9091;
}
location /secret/wallet/verify {
proxy_pass http://127.0.0.1:9091;
}
location /secret/membership/quote {
proxy_pass http://127.0.0.1:9091;
}
location /secret/membership/confirm {
proxy_pass http://127.0.0.1:9091;
}
Summary
The wallet-first designation plus paid membership flow creates a deterministic two-factor identity and commitment chain:
- signature proves wallet control,
- paid mint proves intent,
- membership gates all future marketplace purchases.