Files
metamask-integration/chain138-snap/TESTING_INSTRUCTIONS.md
2026-03-02 12:14:14 -08:00

394 lines
14 KiB
Markdown

# Chain 138 Snap Testing Instructions
**Date:** 2026-01-30
**Status:** Built and ready for testing
**Thorough pre-publish testing:** For a complete pass before every npm publish (including **all logos/images**, every RPC method, companion site, Send page, production-like test, and recommendations), use **[docs/PRE_PUBLISH_TESTING.md](docs/PRE_PUBLISH_TESTING.md)**.
---
## Prerequisites
1. **MetaMask Flask** (development version of MetaMask)
- Download: https://metamask.io/flask/
- Install as separate browser extension (won't conflict with regular MetaMask)
2. **Snap Development Server Running**
```bash
pnpm run start
```
(From the repo root.)
(Or use **yarn start** if you prefer Yarn; see [PACKAGE_MANAGER.md](PACKAGE_MANAGER.md).)
- Server will start on http://localhost:8000
- Keep this terminal open
3. **For full E2E (API-dependent features):** Token-aggregation service and companion site env. See [E2E Preparation](E2E_PREPARATION.md).
---
## E2E Preparation
For full end-to-end success (market data, bridge routes, swap quotes), complete these before running the checklist:
1. **Start token-aggregation** (local or use a deployed URL).
- See [E2E_PREPARATION.md](E2E_PREPARATION.md) for steps (database, env, `npm run dev` or Docker).
- Note the API base URL (e.g. `http://localhost:3000` for local).
2. **Configure companion site env.**
- In `packages/site`, copy `.env.production.dist` to `.env` or `.env.production`.
- Set `GATSBY_SNAP_API_BASE_URL` to the token-aggregation base URL (e.g. `http://localhost:3000`).
- Restart the site if it is already running so the variable is picked up.
3. **Run Snap + site:** From repo root, `pnpm run start` (serves site and Snap on http://localhost:8000).
4. **Install MetaMask Flask** and use the checklist in [E2E testing checklist (MetaMask Flask)](#e2e-testing-checklist-metamask-flask) below.
**Automated E2E (optional):** Run `pnpm run test:e2e` to start the dev server (if needed) and run Playwright tests against the companion site. See [E2E_PREPARATION.md](E2E_PREPARATION.md#5-optional-automated-e2e-playwright). This does not drive MetaMask Flask.
---
## Testing Steps
### 1. Install the Snap
1. Open browser with MetaMask Flask installed
2. Navigate to **http://localhost:8000**
3. You should see the Snap installation page
4. Click **"Connect"** to install the Snap
5. MetaMask Flask will prompt for permissions - approve them
### 2. Test RPC Methods
Once installed, you can test the Snap's RPC methods:
#### Test `get_networks`
Pass `apiBaseUrl` (your token-aggregation service URL). Open browser console:
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'get_networks',
params: { apiBaseUrl: 'https://your-token-aggregation-api.com' },
},
},
});
```
**Expected response:** `{ version, networks: [ ... ] }` with full EIP-3085 params for Chain 138, Ethereum Mainnet, and ALL Mainnet.
**Optional:** You can pass `networksUrl` instead of (or without) `apiBaseUrl` to fetch networks from a JSON URL (e.g. GitHub raw):
```javascript
params: {
networksUrl: 'https://raw.githubusercontent.com/org/repo/main/networks.json';
}
```
#### Test `get_chain138_config`
Requires `apiBaseUrl`. Returns Chain 138 config from the API:
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'get_chain138_config',
params: { apiBaseUrl: 'https://your-token-aggregation-api.com' },
},
},
});
```
**Expected response:** Chain 138 params (chainId, chainName, rpcUrls, nativeCurrency, blockExplorerUrls, oracles).
**Optional:** Pass `networksUrl` instead of `apiBaseUrl` to use a remote networks JSON.
#### Test `get_chain138_market_chains`
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'get_chain138_market_chains',
params: {
apiBaseUrl: 'https://your-token-aggregation-api.com', // When deployed
},
},
},
});
```
**Expected response:**
```json
[
{
"chainId": 138,
"name": "DeFi Oracle Meta Mainnet",
"nativeToken": { "symbol": "ETH", "decimals": 18 },
"rpcUrl": "https://rpc-http-pub.d-bis.org",
"explorerUrl": "https://explorer.d-bis.org"
}
]
```
#### Test `get_market_summary`
Requires `apiBaseUrl` (token-aggregation service URL). Fetches tokens with optional market data (price, volume) for a chain. Optional `chainId` (default 138).
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'get_market_summary',
params: {
apiBaseUrl: 'https://your-token-aggregation-api.com',
chainId: 138, // optional, default 138
},
},
},
});
```
**Expected response:** `{ tokens: [ { symbol, name, address, market?: { priceUsd, volume24h } } ] }` or `{ error, tokens: [] }` on failure.
#### Test `show_market_data`
Requires `apiBaseUrl`. Opens a Snap dialog listing token symbols and USD prices from the token-aggregation API.
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'show_market_data',
params: {
apiBaseUrl: 'https://your-token-aggregation-api.com',
chainId: 138, // optional
},
},
},
});
```
**Expected:** A MetaMask dialog showing "Market data (Chain 138)" and token lines with prices. Without `apiBaseUrl`, the Snap shows an alert asking to pass it.
#### Test `get_token_list` and `get_token_list_url`
With `apiBaseUrl`: same pattern as above; the Snap calls `${apiBaseUrl}/api/v1/report/token-list` (optional `chainId` in params).
**Optional:** Pass `tokenListUrl` to fetch the token list from a JSON URL (e.g. GitHub raw):
```javascript
params: { tokenListUrl: 'https://raw.githubusercontent.com/org/repo/main/token-list.json', chainId: 138 }
```
#### Test `get_bridge_routes`
Requires `apiBaseUrl` or `bridgeListUrl`. Returns bridge routes: CCIP (WETH9/WETH10) and, when configured, Trustless (Lockbox on 138) and Chain 138 bridge addresses.
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'get_bridge_routes',
params: { apiBaseUrl: 'https://your-token-aggregation-api.com' },
},
},
});
```
**Expected response:** `{ routes: { weth9: {...}, weth10: {...} }, chain138Bridges: { weth9, weth10 } }`.
**Optional:** Pass `bridgeListUrl` instead of `apiBaseUrl` to fetch bridge list from a JSON URL.
#### Test `show_bridge_routes`
Requires `apiBaseUrl` or `bridgeListUrl`. Opens a Snap dialog with bridge route summary: CCIP (WETH9/WETH10) and Trustless (Lockbox) → Ethereum Mainnet.
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'show_bridge_routes',
params: { apiBaseUrl: 'https://your-token-aggregation-api.com' },
},
},
});
```
#### Test `get_swap_quote`
Requires `apiBaseUrl`, `tokenIn`, `tokenOut`, `amountIn` (raw amount string). Optional `chainId` (default 138).
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'get_swap_quote',
params: {
apiBaseUrl: 'https://your-token-aggregation-api.com',
chainId: 138,
tokenIn: '0x...',
tokenOut: '0x...',
amountIn: '1000000000000000000',
},
},
},
});
```
**Expected response:** `{ amountOut: string | undefined, error?: string, poolAddress?: string }`.
#### Test `show_swap_quote`
Same params as `get_swap_quote`. Opens a Snap dialog with the quote (In/Out raw amounts).
#### Test `hello` (basic test)
```javascript
await ethereum.request({
method: 'wallet_invokeSnap',
params: {
snapId: 'local:http://localhost:8000',
request: {
method: 'hello',
},
},
});
```
**Expected response:**
```json
"Hello from Chain 138 Snap!"
```
---
## E2E testing checklist (MetaMask Flask)
Use this checklist for full manual E2E testing:
1. **Environment**
- [ ] MetaMask Flask installed
- [ ] Snap dev server running: `pnpm run start` (or `yarn start`) in the repo root
- [ ] For API-dependent tests: token-aggregation service reachable. Set `apiBaseUrl` to your deployment (e.g. `https://your-token-aggregation-api.com`) or a local/staging URL (e.g. `http://localhost:3000` if running token-aggregation locally).
2. **Install Snap**
- [ ] Open http://localhost:8000 in the browser
- [ ] Click **Connect** and approve Snap installation in MetaMask Flask
3. **RPC methods (apiBaseUrl or optional networksUrl / tokenListUrl / bridgeListUrl)**
- [ ] `hello`
- [ ] `get_networks` (apiBaseUrl or networksUrl)
- [ ] `get_chain138_config` (apiBaseUrl or networksUrl)
- [ ] `get_chain138_market_chains` (apiBaseUrl)
- [ ] `get_token_list`, `get_token_list_url` (apiBaseUrl or tokenListUrl; optional chainId)
- [ ] `get_oracles` (apiBaseUrl), `show_dynamic_info` (apiBaseUrl or networksUrl/tokenListUrl)
- [ ] `get_market_summary`, `show_market_data` (apiBaseUrl; optional chainId)
- [ ] `get_bridge_routes`, `show_bridge_routes` (apiBaseUrl or bridgeListUrl)
- [ ] `get_swap_quote`, `show_swap_quote` (apiBaseUrl, tokenIn, tokenOut, amountIn; optional chainId)
4. **Companion site cards**
- [ ] Set `GATSBY_SNAP_API_BASE_URL` in `.env` (copy from `.env.production.dist` and fill) so the site passes apiBaseUrl to the Snap.
- [ ] **Market data:** "Show market data" opens Snap dialog; "Fetch market summary" displays tokens/prices below.
- [ ] **Bridge:** "Show bridge routes" opens Snap dialog with CCIP and Trustless routes.
- [ ] **Swap quote:** Enter token In/Out addresses and amount (raw), then "Get quote" shows amountOut; "Show quote in Snap" opens dialog.
---
## Troubleshooting
### Snap not appearing in MetaMask Flask
- Ensure dev server is running on port 8000
- Check browser console for errors
- Try refreshing the page
### Permission errors
- Snap needs `endowment:network-access` for API calls
- Check `snap.manifest.json` has correct permissions
### API calls failing
- Ensure `apiBaseUrl` is provided for methods that need it, or use the optional URL params: `networksUrl`, `tokenListUrl`, `bridgeListUrl` (see RPC method sections above).
- On the companion site, set `GATSBY_SNAP_API_BASE_URL` in `.env` or `.env.production` (see `packages/site/.env.production.dist`) so Market data and other API-dependent cards work.
- Check CORS settings on the token-aggregation API server (it uses `cors()` by default).
- Verify API endpoint is accessible (e.g. token-aggregation and, for full testing, bridge/quote endpoints).
---
## Next Steps
### After Testing
1. **Fix any bugs** found during testing
2. **Submit to Snap directory** when ready (see Publishing below)
### Publishing
**Checklist before publishing:**
- [ ] **Thorough test:** Complete [docs/PRE_PUBLISH_TESTING.md](docs/PRE_PUBLISH_TESTING.md) (build, logos/images, all RPC methods, companion site, Send page, production-like, final sign-off).
- [ ] All manual E2E checklist items above completed and passing.
- [ ] Token-aggregation (or your API) deployed and stable; production `apiBaseUrl` known.
- [ ] Snap built with no errors; `prepublishOnly` has run (updates manifest shasum).
- [ ] `packages/snap/package.json`: `name` and `publishConfig` (e.g. `"access": "public"`) correct for npm.
- [ ] Integrator docs updated: dApps/site must pass `apiBaseUrl` (or optional `networksUrl` / `tokenListUrl` / `bridgeListUrl`) for market data, bridge, and swap quote.
**Snap directory submission checklist:**
- [ ] All manual E2E checklist items in this doc completed and passing.
- [ ] Snap built with `pnpm run build`; `prepublishOnly` has run (manifest shasum updated).
- [ ] `packages/snap/package.json`: `name`, `version`, `publishConfig` (e.g. `"access": "public"`) correct for npm.
- [ ] `snap.manifest.json`: `description`, `proposedName`, `initialPermissions` match what the Snap uses; `source.location.npm` will be valid after publish.
- [ ] Snap package published to npm so the manifest npm source is resolvable.
- [ ] [MetaMask Snap publishing guide](https://docs.metamask.io/snaps/how-to/publish-a-snap/) followed: register Snap (package name or bundle URL), description, category, permissions.
- [ ] Integrator docs: dApps/site must pass `apiBaseUrl` (or optional `networksUrl` / `tokenListUrl` / `bridgeListUrl`) for market data, bridge, swap quote.
**Steps to publish to MetaMask Snap directory:**
1. **Build:** Run `pnpm run build` (or **yarn build**; see [PACKAGE_MANAGER.md](PACKAGE_MANAGER.md)). The `prepublishOnly` script updates the manifest shasum.
2. **Publish package:** Publish the Snap package to npm (e.g. from `packages/snap`) so `source.location.npm` in `snap.manifest.json` is valid.
3. **Snap directory:** Follow the [MetaMask Snap publishing guide](https://docs.metamask.io/snaps/how-to/publish-a-snap/) to register the Snap (package name or bundle URL, description, category, permissions).
**Production use:** After the Snap is published, the production Snap ID is **`npm:chain138-snap`**. For market data, swap quote, and bridge routes to work, dApps (and the companion site) must pass `apiBaseUrl` (your token-aggregation service URL) or the optional URLs (`networksUrl`, `tokenListUrl`, `bridgeListUrl`) when invoking the Snap. See "Integrators" in the repo README and "API calls failing" in Troubleshooting.
---
## Snap Capabilities
### Current Features
- ✅ Get Chain 138 configuration (`get_chain138_config`, `get_networks`)
- ✅ Token list and token list URL (`get_token_list`, `get_token_list_url`)
- ✅ Market data: `get_market_summary` (tokens with prices), `show_market_data` (dialog)
- ✅ Oracles config (`get_oracles`), dynamic info dialog (`show_dynamic_info`)
- ✅ Bridge routes (`get_bridge_routes`, `show_bridge_routes`) — CCIP and Trustless — when bridge API is available
- ✅ Swap quote (`get_swap_quote`, `show_swap_quote`) when quote API is available
---
**Last updated:** 2026-02-11
**Status:** Ready for manual testing in MetaMask Flask; Playwright E2E available via `pnpm run test:e2e`