Files
nick-doc/08 - Operations/Handoff - Telegram Mini App Debug - 2026-05-24.md
Siavash Sameni 940ad0c655 Add full system audit reports and Telegram Mini App debug handoff
- Three-stream audit (security / logic / performance) with 35+ findings
  derived from actual source code, each with file:line and remediation
- Audit Index cross-references criticals across streams into prioritized
  fix tiers: immediately / before soft launch / before public launch
- Telegram Mini App debug handoff documenting what was implemented and
  all remaining work items with exact file lists and test commands
- Updated architecture, data model, auth API, and registration flow docs
  to reflect Telegram auth, TON wallet, and email verification additions

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-24 17:20:08 +04:00

17 KiB

Handoff - Telegram Mini App Debug - 2026-05-24

Scope

This handoff covers the work done after bringing the app up under the consolidated https://amn.gg URL and debugging the Telegram Mini App flow.

Primary user-reported issues:

  • The red N badge in the Telegram webview was interpreted as backend/socket failure.
  • Telegram-created users without an existing Amanat account were blocked by the link/sign-in screen instead of being treated as buyer users.
  • Wallet connect did not support Telegram Wallet / TON.
  • Profile email updates for Telegram-created users did not persist and did not send confirmation email.
  • The page needed visible debug statistics to identify which subsystem is working.

Repositories Touched

Backend:

  • backend/src/models/User.ts
  • backend/src/services/user/userController.ts
  • backend/src/services/user/userControllerRoutes.ts
  • backend/src/services/user/userRoutes.ts

Frontend:

  • frontend/next.config.ts
  • frontend/package.json
  • frontend/yarn.lock
  • frontend/public/tonconnect-manifest.json
  • frontend/src/actions/account.ts
  • frontend/src/app/layout.tsx
  • frontend/src/auth/context/jwt/auth-provider.tsx
  • frontend/src/auth/types.ts
  • frontend/src/components/debug/telegram-debug-panel.tsx
  • frontend/src/lib/axios.ts
  • frontend/src/sections/account/account-general.tsx
  • frontend/src/sections/account/account-wallet-connection.tsx
  • frontend/src/types/user.ts
  • frontend/src/web3/tonconnect-provider.tsx

Vault:

  • This file.

Implemented

Debug Statistics

Added TelegramDebugPanel to account/profile and wallet pages.

It reports:

  • API URL
  • Socket URL
  • socket connected/disconnected state and socket id
  • auth state
  • user id, role, email, email verification state
  • Telegram Mini App detection, platform, version, and initData presence
  • saved wallet type/address
  • last frontend account/wallet action and result

Visibility:

  • Always visible in development.
  • Visible inside Telegram Mini App.
  • Visible in production browser with ?debug=1 or localStorage.setItem('amn-debug', '1').

Red N Badge

The red N indicator is the Next.js development indicator, not the backend/socket status.

Change:

  • frontend/next.config.ts now sets devIndicators: false.

The actual socket status should be read from the debug panel or the app socket status component.

Telegram User / Buyer Flow

Frontend auth mapping was changed so users without an email are not treated as email-unverified blockers:

  • isEmailVerified is treated as true when the user has no email.
  • If an email exists, normal verification state applies.

This supports Telegram-created buyer accounts without forcing immediate email collection.

Profile Email Update And Verification

Backend profile update now accepts email and handles verification:

  • Normalizes email to lowercase.
  • Rejects duplicate email.
  • Stores a six-digit verification code on the user.
  • Sets isEmailVerified=false when email changes.
  • Attempts to send a confirmation email.
  • Returns verificationEmailQueued.

New authenticated endpoints:

  • POST /api/user/profile/email/resend-verification
  • POST /api/user/profile/email/verify

Frontend:

  • updateUserProfile now unwraps the backend { user, verificationEmailQueued } response correctly.
  • Profile page shows a verification code input and resend/verify controls when a user has an unverified email.
  • Debug events are emitted for profile update/resend/verify actions.

Telegram Wallet / TON Support

Frontend:

  • Added @tonconnect/ui-react and @ton/core.
  • Added TonWalletProvider in the root layout.
  • Added public/tonconnect-manifest.json.
  • Wallet connection page now offers Telegram Wallet / TON connection inside Telegram Mini App.
  • Connected TON wallet can be saved as walletType: "ton" with provider metadata.

Backend:

  • User profile schema now supports:
    • profile.walletType: "evm" | "ton"
    • profile.walletProvider
  • Current /user/wallet-address controller supports TON address validation.
  • Legacy /users/wallet-address route also accepts TON.
  • EVM still requires signature verification.
  • TON currently validates address format only and skips EVM signature.

Verification Completed

Backend:

cd backend
npm run typecheck --if-present

Result: passed.

Frontend focused tests:

cd frontend
npm test -- __tests__/account-test/account-actions.test.ts __tests__/auth/telegram-auth-action.test.ts __tests__/sections/telegram/telegram-mini-app-shell.test.tsx --runInBand

Result:

  • 3 suites passed
  • 38 tests passed

Diff hygiene:

git diff --check

Result: passed in backend and frontend after whitespace cleanup.

Public smoke checks completed during the session:

  • https://amn.gg/ returned HTTP 200.
  • https://amn.gg/tonconnect-manifest.json returned HTTP 200 with JSON.
  • https://amn.gg/socket.io/?EIO=4&transport=polling returned HTTP 200 polling handshake.
  • https://amn.gg/dashboard/account/wallet/ returned HTTP 200 after compilation.

Known Issues Left

Frontend Typecheck Still Has Existing Failures

frontend npx tsc --noEmit -p tsconfig.json still fails in pre-existing areas not introduced by this Telegram/debug pass:

  • src/components/payment/shkeeper-payment-widget.tsx
  • src/sections/address/address-form.tsx
  • src/sections/address/address-new-form.tsx
  • src/sections/request-template/request-template-checkout-payment.tsx
  • src/sections/request-template/request-template-new-edit-form.tsx
  • src/web3/components/provider-payment.tsx

Representative issues:

  • Missing sellerId in IPaymentIntentPayload.
  • React Hook Form resolver typing mismatches.
  • Invalid icon name solar:wallet-money-bold.

Next agent should decide whether to clean these before treating global frontend typecheck as a release gate.

Backend Broad Test Pattern Is Noisy

A broad backend Jest pattern for user|auth|telegram pulled in unrelated payment/shkeeper/basic suites and failed with pre-existing app/test setup problems such as supertest app undefined and expected status mismatch.

Focused backend typecheck passed. The next agent should add targeted backend tests for:

  • PUT /api/user/profile email update.
  • duplicate email rejection.
  • resend profile email verification.
  • verify profile email code.
  • TON wallet save.
  • EVM wallet signature requirement still enforced.

TON Wallet Signature Model Is Not Final

TON wallet save currently validates address shape only.

This is acceptable as a first Telegram Wallet integration smoke path, but not sufficient as final wallet ownership proof.

Next steps:

  • Use TonConnect proof payload/signature validation server-side.
  • Store wallet proof timestamp/provider.
  • Decide whether Telegram Wallet should be required for payments or only optional profile wallet metadata.

Email Delivery Needs Runtime Confirmation

Backend is wired to call emailService.sendVerificationCodeEmail, and Resend support was configured earlier in the session, but the live flow should still be verified end-to-end:

  • Add an email from the Telegram-created profile.
  • Confirm the API returns verificationEmailQueued: true.
  • Confirm the message arrives from the configured @amn.gg sender.
  • Submit code and confirm isEmailVerified=true.

Do not put API keys or bot tokens in docs or commits.

Package Manager State

The frontend project declares Yarn 1 as package manager and yarn.lock was updated for TON dependencies.

package-lock.json was intentionally restored to avoid unrelated massive lockfile churn.

Next agent should continue using Yarn for dependency changes unless the project standard changes.

Dev Runtime Note

During dependency installation, the mounted node_modules was temporarily broken by an Alpine/Yarn install attempt involving native packages. It was repaired on the host with dependency install and the public app recovered.

If the container shows stale Next errors in logs, check for a later successful startup before treating them as current.

Current Git State At Handoff

Backend and frontend contain uncommitted changes for this Telegram/debug/email/wallet pass. They have not been committed yet.

Backend current modified files:

  • src/models/User.ts
  • src/services/user/userController.ts
  • src/services/user/userControllerRoutes.ts
  • src/services/user/userRoutes.ts

Frontend current modified/untracked files:

  • next.config.ts
  • package.json
  • yarn.lock
  • public/tonconnect-manifest.json
  • src/actions/account.ts
  • src/app/layout.tsx
  • src/auth/context/jwt/auth-provider.tsx
  • src/auth/types.ts
  • src/components/debug/telegram-debug-panel.tsx
  • src/lib/axios.ts
  • src/sections/account/account-general.tsx
  • src/sections/account/account-wallet-connection.tsx
  • src/types/user.ts
  • src/web3/tonconnect-provider.tsx

Vault also has older uncommitted audit/doc updates from prior task work, plus this handoff file.

Vault current modified/untracked files at handoff:

  • 00 - Overview/System Overview.md
  • 00 - Overview/Tech Stack.md
  • 01 - Architecture/Backend Architecture.md
  • 01 - Architecture/Security Architecture.md
  • 02 - Data Models/Data Model Overview.md
  • 03 - API Reference/Authentication API.md
  • 04 - Flows/Registration Flow.md
  • 08 - Operations/Handoff - Telegram Mini App Debug - 2026-05-24.md
  • 09 - Audits/Audit Index - 2026-05-24.md
  • 09 - Audits/Logic Audit - 2026-05-24.md
  • 09 - Audits/Performance Audit - 2026-05-24.md
  • 09 - Audits/Security Audit - 2026-05-24.md

Recommended commit split:

  1. Backend commit:

    • user profile email verification endpoints
    • wallet type/provider model fields
    • TON wallet address support
  2. Frontend commit:

    • debug stats panel
    • TonConnect provider and manifest
    • Telegram Wallet connect/save UI
    • profile email verification UI/actions
    • disabled Next dev indicator
  3. Vault commit:

    • existing task/audit docs
    • this handoff document

Before committing, rerun:

cd /Users/manwe/CascadeProjects/escrow/backend
git diff --check
npm run typecheck --if-present

cd /Users/manwe/CascadeProjects/escrow/frontend
git diff --check
npm test -- __tests__/account-test/account-actions.test.ts __tests__/auth/telegram-auth-action.test.ts __tests__/sections/telegram/telegram-mini-app-shell.test.tsx --runInBand

Then commit only the relevant files for each repository. Do not include secrets, local .env files, or regenerated package-lock.json churn.

Suggested Next Steps

  1. Run the app in Telegram and open profile with ?debug=1 if needed.
  2. Confirm debug panel socket state matches https://amn.gg/socket.io/?EIO=4&transport=polling.
  3. Test Telegram-created user account creation as buyer without email.
  4. Add profile email, verify confirmation email delivery, and submit the code.
  5. Connect Telegram Wallet and confirm backend stores profile.walletType="ton".
  6. Add targeted backend Jest tests for the new endpoints.
  7. Fix existing frontend typecheck blockers or document them as accepted debt.
  8. Commit backend, frontend, and vault changes separately.

Detailed Remaining Work

1. Confirm Telegram Bot Web App URL

Make sure the Telegram bot opens the consolidated production URL:

  • Target URL: https://amn.gg
  • Bot username seen in the app: @amnescrow_Bot
  • Mini App return URL configured for TonConnect: https://t.me/amnescrow_Bot/escrow

If the Telegram button still opens an old frontend URL, update the bot menu/button/web app URL through BotFather or the bot startup/config code, depending on how this bot is registered.

2. Recheck Pangolin/Newt Routing

The desired public shape is one URL:

  • Browser and Telegram app: https://amn.gg
  • Backend proxied by path under the same host.

Expected route intent:

  • /* -> frontend container/service
  • /api/* -> backend container/service
  • /socket.io/* -> backend container/service with WebSocket support
  • /uploads/* -> backend container/service
  • /health -> backend container/service

If Telegram shows network errors:

  1. Open https://amn.gg/?debug=1.
  2. Check API, Socket URL, and Socket fields in the debug panel.
  3. Hit https://amn.gg/socket.io/?EIO=4&transport=polling directly and confirm HTTP 200 with a Socket.IO polling handshake.
  4. Check newt target health in Pangolin.

3. Finish Email Verification Test Coverage

The code path exists but targeted backend tests still need to be written.

Recommended backend tests:

  • Profile email update stores normalized email and sets isEmailVerified=false.
  • Profile email update rejects duplicate email.
  • Profile email update queues an email verification code and calls email service.
  • Resend verification fails when user has no email.
  • Resend verification fails when email is already verified.
  • Resend verification refreshes code/expires and sends email.
  • Verify email rejects malformed code.
  • Verify email rejects expired/wrong code.
  • Verify email sets isEmailVerified=true and clears code fields.

Mock emailService.sendVerificationCodeEmail in these tests so Resend is not called.

4. Finish Wallet Test Coverage

Recommended backend tests:

  • PATCH /api/user/wallet-address with walletType="ton" accepts a valid friendly TON address.
  • TON wallet save stores profile.walletAddress, profile.walletType, and profile.walletProvider.
  • TON wallet save rejects malformed TON addresses.
  • EVM wallet save still rejects missing signature/message.
  • EVM wallet save still rejects a signature that does not recover the submitted address.
  • Legacy /api/users/wallet-address behavior remains compatible.

Recommended frontend tests:

  • updateWalletAddress sends legacy EVM payload unchanged when no options are passed.
  • updateWalletAddress sends TON payload without signature when { walletType: "ton" } is passed.
  • TelegramDebugPanel renders socket/auth/TG fields when debug is enabled.
  • Account profile page renders email verification controls for an unverified email.

5. Upgrade TON Ownership Proof

Current TON wallet support is intentionally minimal: it validates address format and stores the address.

Before using TON wallet as strong proof of ownership, implement TonConnect proof verification:

  • Generate a backend nonce/payload for wallet proof.
  • Pass the proof request into TonConnect.
  • Verify the returned proof server-side using TON address public key/proof data.
  • Store proof metadata, timestamp, wallet provider, and verified status.
  • Expire or rotate proof when needed.

Until this is done, treat saved TON wallet as user-supplied wallet metadata, not a cryptographic ownership guarantee.

6. Check Profile Update UX

The backend now supports email changes and confirmation codes, but the profile UI should be manually checked in Telegram:

  • Start with a Telegram-created buyer without email.
  • Add email in profile.
  • Confirm the page does not discard the email.
  • Confirm warning/verification controls appear.
  • Confirm Resend works.
  • Enter verification code.
  • Confirm user session refresh shows verified state.

If the UI toast says success but no email arrives, inspect backend email logs and Resend domain/sender configuration.

7. Resolve Existing Typecheck Debt

Do not assume the global frontend typecheck failure is caused by this pass. It was already failing in other modules.

Known blockers to resolve or explicitly defer:

  • shkeeper-payment-widget.tsx: payload type expects sellerId.
  • address form files: React Hook Form resolver type mismatches.
  • request template form files: resolver/data typing issues.
  • provider-payment.tsx: invalid icon id solar:wallet-money-bold.

After resolving these, make npx tsc --noEmit -p tsconfig.json part of the normal frontend verification gate.

8. Deployment/Container Follow-Up

Because dependencies changed in frontend/package.json and yarn.lock, the deployed frontend image/container should be rebuilt from a clean dependency install.

Recommended sequence:

cd /Users/manwe/CascadeProjects/escrow/frontend
yarn install --frozen-lockfile
yarn test __tests__/account-test/account-actions.test.ts __tests__/auth/telegram-auth-action.test.ts __tests__/sections/telegram/telegram-mini-app-shell.test.tsx --runInBand

cd /Users/manwe/CascadeProjects/escrow
docker compose build frontend backend
docker compose up -d frontend backend

If the existing compose setup relies on mounted node_modules, verify the mounted dependencies include @tonconnect/ui-react and @ton/core.

9. Spark Agent Status

The user asked to use codex-spark agents. Earlier in this session, existing subagents were already active and a fresh spark verifier could not be spawned because the agent thread limit was reached.

Next agent can continue with spark workers once capacity is available. Good isolated assignments:

  • Worker A: backend tests for profile email verification.
  • Worker B: backend tests for wallet address EVM/TON behavior.
  • Worker C: frontend tests for debug panel and TON wallet action payload.
  • Worker D: manual Telegram/Pangolin runtime verification report.

10. Safety Notes

  • Do not commit Telegram bot token, Resend API key, Pangolin/Newt secret, or any .env file.
  • Do not revert unrelated vault audit files; they predate this handoff and should be reviewed as separate documentation work.
  • Do not regenerate package locks casually. The frontend project declares Yarn 1 and yarn.lock is the relevant lockfile for this change.
  • Keep Trezor optional; this pass did not modify Trezor safekeeping behavior.
  • Payment adapter remains optional; this pass did not force SHKeeper or Request Network.