Skip to content

feat: massalabs network#741

Merged
kvhnuke merged 30 commits intodevop/package-upgrades-2-11from
feat/massalabs-extension
Sep 11, 2025
Merged

feat: massalabs network#741
kvhnuke merged 30 commits intodevop/package-upgrades-2-11from
feat/massalabs-extension

Conversation

@kvhnuke
Copy link
Contributor

@kvhnuke kvhnuke commented Aug 20, 2025

Summary by CodeRabbit

  • New Features

    • Full Massa integration: mainnet & buildnet networks, wallet onboarding, address validation & identicons, balances (MAS & MRC20), activity feed, add-custom Massa token UI, send & verify transaction flows, provider UI/routes, and “Buy MAS” link.
  • Tests

    • Unit tests added for the Massa signer.
  • Chores

    • Added Massa signer package and massa-web3 dependency; broad dependency/tooling/version bumps and CI/Node/Docker version updates.

@github-actions
Copy link

github-actions bot commented Aug 20, 2025

💼 Build Files
chrome: enkrypt-chrome-cea48fd6.zip
firefox: enkrypt-firefox-cea48fd6.zip

💉 Virus total analysis
chrome: cea48fd6
firefox: cea48fd6

@coderabbitai
Copy link

coderabbitai bot commented Aug 20, 2025

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

🗂️ Base branches to auto review (3)
  • main
  • develop
  • devop/vite-migrate

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Walkthrough

Adds end-to-end Massa support: new Massa signer package and massa-web3 dependency, MassaProvider and API, MassaNetwork configs, UI routes/components (send/verify/token management), types, keyring/signers wiring, activity handlers, crypto utilities, tests, and multiple dependency/tooling updates.

Changes

Cohort / File(s) Summary
Manifests & deps
packages/extension/package.json, packages/types/package.json, packages/keyring/package.json, packages/signers/massa/package.json, package.json, packages/*/package.json
Add @massalabs/massa-web3, add new workspace @enkryptcom/signer-massa, and apply numerous dependency/devDependency version bumps across packages.
Background & provider types
packages/extension/src/libs/background/index.ts, packages/extension/src/libs/background/types.ts, packages/extension/src/providers/index.ts
Register ProviderName.massa in tab providers and provider registry; extend provider-type unions to include MassaProvider.
Provider implementation & API
packages/extension/src/providers/massa/index.ts, packages/extension/src/providers/massa/libs/api.ts, packages/extension/src/providers/massa/methods/*
New MassaProvider class, MassaAPI wrapper over massa-web3, and middleware methods (massa_getBalance, massa_getNetwork, massa_setNetwork) for RPC handling and network switching.
Networks & configs
packages/extension/src/providers/massa/networks/*.ts, packages/extension/src/libs/utils/networks.ts
Add MassaNetwork base implementation, mainnet/buildnet configs, networks index; include Massa in providerNetworks, getAllNetworks, POPULAR_NAMES and export DEFAULT_MASSA_* constants.
Tokens & token-state types
packages/extension/src/libs/tokens-state/types.ts, packages/extension/src/libs/tokens-state/index.ts
Add CustomMassaToken type (address AS${string}) and extend addErc20Token to accept massa tokens (MRC20-like).
Activity handlers & mapping
packages/extension/src/providers/massa/libs/activity-handlers/*.ts, packages/extension/src/ui/action/views/network-activity/index.vue
Add MassaActivity handler and map Massa OperationStatus → ActivityStatus in activity update flow.
UI provider, routing & exports
packages/extension/src/providers/massa/ui/index.ts, packages/extension/src/providers/massa/ui/routes/*, packages/extension/src/ui/provider-pages/routes.ts
Register Massa UI export, define Massa routes and names, and include Massa UI routes in global uiRoutes.
Send / Verify UI & components
packages/extension/src/providers/massa/ui/send-transaction/*.vue, packages/extension/src/providers/massa/ui/send-transaction/components/*, packages/extension/src/ui/action/views/send-transaction/index.vue, packages/extension/src/ui/action/views/verify-transaction/index.vue
Add full Massa send and verify flows with subcomponents, signing integration and submission flows.
Custom Massa token UI
packages/extension/src/ui/action/views/network-assets/components/custom-massa-token.vue, packages/extension/src/ui/action/views/network-assets/index.vue
Add modal to add MRC20 tokens and conditional rendering for Massa token UI.
Signer package (new)
packages/signers/massa/src/**, packages/signers/massa/package.json, packages/signers/massa/tsconfig*.json, packages/signers/massa/tests/*
New @enkryptcom/signer-massa: SLIP-0010 ed25519 derivation, key generation/sign/verify, address/keys/signature abstractions, crypto utils (blake3, base58, varint versioner, password sealer, cross-browser crypto), and unit tests.
Keyring & derivation paths
packages/keyring/src/index.ts, packages/keyring/src/utils.ts
Wire Massa signer (SignerType.ed25519mas) into KeyRing signers and add ed25519-mas path handling in pathParser.
Types & enums
packages/types/src/networks.ts, packages/types/src/index.ts, packages/extension/src/types/provider.ts, packages/extension/src/types/base-network.ts, packages/extension/src/types/activity.ts
Add NetworkNames.Massa/MassaBuildnet, CoingeckoPlatform.Massa, SignerType.ed25519mas, ProviderName.massa; include MassaAPI and MassaRawInfo in network/provider/activity typings.
Vitest & tooling
packages/extension/configs/vitest.config.mts
Add resolve.alias customResolver for polyfill paths and compress test include formatting.
UI tweaks & wiring
packages/extension/src/ui/action/App.vue, packages/extension/src/ui/action/views/network-assets/index.vue, packages/extension/src/ui/action/views/send-transaction/index.vue, packages/extension/src/ui/action/views/verify-transaction/index.vue
Add buy link for Massa, preserve selected account when switching networks, and wire Massa send/verify layouts into provider-component maps.
Presentational CSS & minor UI logic
packages/extension/src/providers/common/ui/send-transaction/send-input-amount.vue, packages/extension/src/ui/action/components/app-menu/index.vue
Fiat display truncation CSS and change sort comparator to use long name.
Network registry edits (EVM/Polkadot removals/additions)
packages/extension/src/providers/ethereum/networks/*, packages/extension/src/providers/polkadot/networks/*, packages/types/src/networks.ts
Remove several networks (Form/FormTestnet/CAGA/SkaleChaos/Opal/ZkSyncGoerli), add new mappings (zkSyncSepolia, TAC), and update NetworkNames enum.
CI / Node / Docker updates
.github/workflows/*.yml, .nvmrc, Dockerfile
Update Node versions to 22.18.x, add NODE_OPTIONS memory flag, and update CI images/steps.

Sequence Diagram(s)

sequenceDiagram
  autonumber
  actor User
  participant SendUI as "SendTransaction (Massa UI)"
  participant KeyRing as "KeyRing / MassaSigner"
  participant BG as "Background (MassaProvider)"
  participant API as "MassaAPI"
  participant Node as "Massa Node (RPC)"

  User->>SendUI: confirm transaction
  SendUI->>API: api().getMinimalFee() / getAllTokenInfo()
  SendUI->>KeyRing: request signature (MassaTransactionSigner)
  KeyRing-->>SendUI: signed payload
  SendUI->>BG: background request to submit signed operation
  BG->>API: submit operation (sendOperations / RPC)
  API->>Node: RPC submit
  Node-->>API: operationId / status
  API-->>BG: result
  BG-->>SendUI: response / notification
  SendUI->>User: display operationId / activity
Loading
sequenceDiagram
  autonumber
  participant Dapp as "dApp"
  participant BG as "Background"
  participant Prov as "MassaProvider"
  participant API as "MassaAPI"

  Dapp->>BG: JSON-RPC massa_getBalance(address)
  BG->>Prov: middleware chain -> massa_getBalance
  Prov->>API: api().getBalance(address)
  API-->>Prov: balance
  Prov-->>BG: result
  BG-->>Dapp: balance response

  Dapp->>BG: JSON-RPC massa_setNetwork(target)
  BG->>Prov: middleware chain -> massa_setNetwork
  Prov->>Prov: setRequestProvider(newNetwork)
  Prov-->>BG: { success: true, network }
  BG-->>Dapp: response
Loading

Estimated code review effort

🎯 5 (Critical) | ⏱️ ~120 minutes

Possibly related PRs

Pre-merge checks (3 passed)

✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed The title succinctly identifies the primary change—the addition of the Massalabs network feature—and aligns with the PR’s main purpose without listing implementation details, making it clear and specific to a teammate scanning history.
Docstring Coverage ✅ Passed No functions found in the changes. Docstring coverage check skipped.
✨ Finishing touches
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feat/massalabs-extension

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 21

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
packages/extension/src/types/provider.ts (1)

141-152: Add Massa to Provider type unions and exports

You added enums and MassaRawInfo, but Provider (the union) and the named exports don’t include the Massa injected provider. This will hinder typing for consumers and any cross-network abstractions expecting Provider to cover all supported networks.

Apply these changes (outside the modified lines):

@@
-import type { InjectedProvider as KadenaProvider } from '@/providers/kadena/types';
+import type { InjectedProvider as KadenaProvider } from '@/providers/kadena/types';
 import type { InjectedProvider as SolanaProvider } from '@/providers/solana/types';
+import type { InjectedProvider as MassaProvider } from '@/providers/massa/types';
@@
 export {
   EthereumProvider,
   PolkadotProvider,
   BitcoinProvider,
   KadenaProvider,
   SolanaProvider,
+  MassaProvider,
 };
@@
 export type Provider =
   | EthereumProvider
   | PolkadotProvider
   | BitcoinProvider
   | KadenaProvider
-  | SolanaProvider;
+  | SolanaProvider
+  | MassaProvider;

If Massa currently doesn’t expose an InjectedProvider type, define and export it from '@/providers/massa/types' for consistency with other providers.

packages/extension/src/ui/action/views/network-activity/index.vue (1)

235-238: Unconditional clearInterval can stop polling for still-pending activities (affects Massa, Polkadot, etc.)

If an activity is still pending (e.g., Polkadot subInfo.pending), the interval is cleared anyway. Gate the clear with terminal statuses only.

Apply this diff:

-  // If we're this far in then the transaction has reached a terminal status
-  // No longer need to check this activity
-  clearInterval(timer);
+  // Stop polling only when a terminal status is reached
+  if (
+    activity.status === ActivityStatus.success ||
+    activity.status === ActivityStatus.failed ||
+    activity.status === ActivityStatus.dropped
+  ) {
+    clearInterval(timer);
+  }
🧹 Nitpick comments (43)
packages/signers/massa/tsconfig.json (1)

3-17: Set rootDir to stabilize emit paths and avoid mis-inference

Without rootDir, tsc infers it from all included files. Explicitly setting "rootDir": "src" prevents accidental inclusion of tests or editor folders from affecting emit structure.

Apply this diff:

   "compilerOptions": {
     "lib": ["ESNext", "dom"],
     "moduleResolution": "node",
     "noUnusedLocals": true,
     "noUnusedParameters": true,
     "removeComments": true,
     "sourceMap": true,
     "target": "es2015",
     "module": "commonjs",
     "outDir": "dist",
+    "rootDir": "src",
     "resolveJsonModule": true,
     "esModuleInterop": true,
     "declaration": true,
     "downlevelIteration": true
   },
packages/types/package.json (1)

27-27: Remove unused @massalabs/massa-web3 devDependency from the types package

No imports of @massalabs/massa-web3 were found under packages/types/src, and keeping a caret‐range here duplicates the extension’s pinned version and risks skew down the line.

• packages/types/package.json (lines 26–28):

-  "devDependencies": {
-    "@massalabs/massa-web3": "^5.2.1-dev",
-    "@types/node": "^22.16.5",
+  "devDependencies": {
+    "@types/node": "^22.16.5",
packages/extension/src/libs/tokens-state/types.ts (1)

24-27: Massa token address type is fine; consider runtime validation and clearer token standard naming

The template literal type for AS-prefixed addresses is helpful, but it’s not sufficient for correctness (doesn’t validate base58 length/charset). Ensure add-token flows perform runtime validation for Massa contract addresses using a trusted utility (e.g., from massa-web3) before persisting state.

Additionally, since these are MRC20 contracts, consider introducing TokenType.MRC20 and/or renaming to CustomMrc20Token for clarity. Not blocking, but it will future-proof conditional logic that diverges from ERC20.

I can add a lightweight validator in the add-token path and, if desired, refactor TokenType to include MRC20 while preserving backward compatibility. Want me to draft that patch?

packages/extension/src/types/activity.ts (1)

9-9: Use a type-only import to avoid bundling massa-web3 at runtime

Prevents unnecessary runtime dependency inclusion by the bundler.

-import { OperationStatus } from '@massalabs/massa-web3';
+import type { OperationStatus } from '@massalabs/massa-web3';
packages/extension/src/providers/massa/methods/massa_getNetwork.ts (1)

12-19: Avoid defaulting to mainnet on errors; return the actual error or current network

Defaulting to NetworkNames.Massa can misreport the active network (e.g., Buildnet). Prefer returning the actual current network or surfacing the error.

-  if (payload.method !== 'massa_getNetwork') return next();
-  else {
-    try {
-      res(null, this.network.name);
-    } catch (error) {
-      res(null, NetworkNames.Massa);
-    }
-  }
+  if (payload.method !== 'massa_getNetwork') return next();
+  try {
+    return res(null, this.network.name);
+  } catch (error) {
+    return res(error as any);
+  }
packages/extension/src/providers/massa/libs/activity-handlers/massa.ts (1)

10-21: Local-activity passthrough is fine; consider deterministic ordering

Returning persisted activities is a good first step. Consider sorting by timestamp desc to keep UI stable across loads.

Example:

return activities.sort((a, b) => (b.timestamp ?? 0) - (a.timestamp ?? 0));
packages/extension/src/providers/massa/ui/send-transaction/components/send-token-select.vue (4)

2-2: Prefer button semantics for clickability (accessibility).

Using an anchor purely for click handling is suboptimal for a11y. Use a button or add role and keyboard handlers.

Apply:

-  <a class="send-token-select" @click="emit('update:toggleTokenSelect')">
+  <button type="button" class="send-token-select" @click="emit('update:toggleTokenSelect')">
...
-  </a>
+  </button>

4-5: Guard against undefined token.icon to avoid broken image requests.

When token.icon is undefined, the browser will attempt to load "undefined". Add a conditional and a fallback.

-      <img :src="token.icon" alt="" />
+      <img v-if="token.icon" :src="token.icon" :alt="token.symbol || token.name || 'token icon'" />
+      <div v-else class="send-token-select__image--placeholder" aria-hidden="true"></div>

49-57: Duplicate CSS property.

box-sizing is set twice; remove the duplicate.

   box-sizing: border-box;
-  border: 1px solid @gray02;
-  box-sizing: border-box;
+  border: 1px solid @gray02;

26-28: Event name suggests v-model usage but is used as a plain toggle.

update:toggleTokenSelect reads like a v-model event. Consider renaming to toggle:tokenSelect or toggleTokenSelect for clarity and consistency.

packages/extension/src/providers/massa/types/index.ts (1)

9-15: Make chainId required to avoid non-null assertions downstream.

chainId is used with a non-null assertion in signing (OperationManager.canonicalize). Making it required at the type level prevents runtime surprises.

-export interface MassaNetworkOptions extends BaseNetworkOptions {
-  chainId?: (typeof CHAIN_ID)[keyof typeof CHAIN_ID];
+export interface MassaNetworkOptions extends BaseNetworkOptions {
+  chainId: (typeof CHAIN_ID)[keyof typeof CHAIN_ID];

If some networks legitimately lack chainId, add a guard at the call site instead.

packages/signers/massa/src/libs/ed25519.ts (2)

50-61: Path handling silently hardens all segments; either enforce apostrophes or reflect them.

Ed25519 derivation only supports hardened steps. Your current implementation adds HARDENED_OFFSET to all segments regardless of apostrophes, which can surprise callers. Prefer one of:

  • Enforce that all segments are hardened (contain a trailing apostrophe) and reject otherwise, or
  • Keep current behavior but document it and tighten validation.

Option A (enforce hardened segments):

-const isValidPath = (path: string): boolean => {
-  if (!/^m(\/[0-9]+('?))*$/.test(path)) {
+const isValidPath = (path: string): boolean => {
+  if (!/^m(\/[0-9]+'?)*$/.test(path)) {
     return false;
   }
-  return !path
-    .split("/")
-    .slice(1)
-    .map(replaceDerive)
-    .some(isNaN as any);
+  const segments = path.split("/").slice(1);
+  // Require apostrophes on all segments when present
+  if (segments.length && segments.some(s => !s.endsWith("'"))) return false;
+  return !segments.map(replaceDerive).some(isNaN as any);
 }

Option B (document behavior): add a brief comment to derivePath stating all segments are treated as hardened irrespective of apostrophes.


41-48: Public key derivation is correct; defaulting to a 0x00 prefix is unconventional.

Many consumers expect a 32-byte ed25519 public key. Default withZeroByte = true alters length to 33 bytes. If this is for compatibility with downstream tooling, all good; otherwise consider defaulting to false.

packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue (2)

47-51: Use Clipboard API instead of deprecated execCommand('paste').

document.execCommand('paste') is deprecated and requires special permissions. Prefer navigator.clipboard with fallback.

-const pasteFromClipboard = () => {
-  addressInput.value?.focus();
-  document.execCommand('paste');
-};
+const pasteFromClipboard = async () => {
+  try {
+    addressInput.value?.focus();
+    if (navigator.clipboard?.readText) {
+      const text = await navigator.clipboard.readText();
+      emit('update:inputAddress', text);
+    } else {
+      console.warn('Clipboard API not available');
+    }
+  } catch (e) {
+    console.error('Clipboard read failed:', e);
+  }
+};

27-28: Replace inline color logic with a CSS class for consistency with theming.

Inline styles bypass theme tokens and can hurt readability. Toggle a class instead.

-        :style="{
-          color: massaAddress && !isValidMassaAddress ? 'red' : 'black',
-        }"
+        :class="{ 'send-address-input__address--invalid': massaAddress && !isValidMassaAddress }"

Add style:

.send-address-input__address--invalid {
  color: @error; // or appropriate theme token
}
packages/extension/src/providers/massa/ui/libs/signer.ts (3)

96-107: Harden JSON parsing and result handling from messenger.

If result isn’t JSON or is empty, JSON.parse will throw. Use a safe parse and normalize the signature.

-      const signature = JSON.parse(res.result as string) || '';
+      let signature = '';
+      try {
+        signature = JSON.parse(res.result as string) || '';
+      } catch {
+        signature = (res.result as string) || '';
+      }

17-32: Type network as MassaNetworkOptions to remove casts.

You’re casting network later; make it explicit in the options interface to improve safety.

 export interface MassaTransactionOptions {
   account: EnkryptAccount;
-  network: BaseNetwork;
+  network: BaseNetwork & MassaNetworkOptions;

68-75: Validate hex payload for smart contract calls.

hexToBuffer('') or non-hex strings may throw. Add a simple guard or normalize 0x prefix.

-      parameter: hexToBuffer(payload.data ?? ''),
+      parameter: payload.data ? hexToBuffer(payload.data) : Buffer.alloc(0),
packages/keyring/src/utils.ts (1)

17-19: Add unit tests for ed25519mas path parsing

The new SignerType.ed25519mas branch in pathParser has no existing test coverage—let’s add tests to guard against regressions. For example, verify that given a basePath of "m/44'/632'" and indexes 0, 1, 2, etc., the outputs are:

  • index 0 → "m/44'/632'/0'/0'"
  • index 1 → "m/44'/632'/1'/0'"
  • index 2 → "m/44'/632'/2'/0'"

Please add corresponding unit tests in the packages/keyring/src/utils.test.ts (or similar) targeting:

  • The ed25519mas case in pathParser(basePath, index, type)
  • Edge conditions (e.g., negative indexes, very large indexes) if applicable
packages/extension/src/providers/massa/libs/activity-handlers/index.ts (1)

1-3: Minor: simplify re-export to a one-liner.

Functionally equivalent and a bit tidier.

Apply this diff:

-import MassaActivity from './massa';
-
-export { MassaActivity };
+export { default as MassaActivity } from './massa';
packages/extension/src/providers/massa/methods/index.ts (1)

7-19: Tiny polish: avoid unused param warning and name the placeholder middleware.

  • Rename the unused provider param to _provider to satisfy linters.
  • Give the placeholder middleware a name for easier debugging in stacks.

Apply this diff:

-export default (
-  provider: BackgroundProviderInterface,
-): MiddlewareFunction[] => {
+export default (
+  _provider: BackgroundProviderInterface,
+): MiddlewareFunction[] => {
   return [
     massa_getBalance,
     massa_getNetwork,
     massa_setNetwork,
-    async (request, response, next) => {
-      // Add any additional Massa-specific middleware logic here
-      return next();
-    },
+    async function massaExtraMiddleware(request, response, next) {
+      // Add any additional Massa-specific middleware logic here
+      return next();
+    },
   ];
 };
packages/extension/src/providers/massa/networks/mainnet.ts (1)

5-14: Optional: Set an explicit CoinGecko platform only if supported

getAllTokenInfo in massa-base uses this.coingeckoPlatform for custom token market data. If createMassaNetworkOptions doesn’t set it (or CoinGecko doesn’t recognize Massa as a platform by contract), custom tokens’ market data calls may fail. If unsupported, it's fine to skip; otherwise, consider passing a valid coingeckoPlatform here.

packages/extension/src/ui/action/App.vue (1)

201-226: Add Massa buy link via network options for consistency (optional)

Hardcoding the Massa buy URL works, but other networks pull from network.options.buyLink. Using options keeps this centralized and easier to change.

Apply this diff to prefer a network-provided link while keeping your fallback:

       case NetworkNames.SyscoinNEVMTest:
       case NetworkNames.RolluxTest:
         return (currentNetwork.value as EvmNetwork).options.buyLink;
-      case NetworkNames.Massa:
-        return 'https://www.massa.net/get-mas';
+      case NetworkNames.Massa:
+        return (currentNetwork.value as any).options?.buyLink ?? 'https://www.massa.net/get-mas';
packages/signers/massa/tests/sign.test.ts (2)

28-38: Sign/verify happy path looks solid

Using blake2 for a msg hash is fine for this unit test and validates the signer API.

Add a negative test where the message hash differs (same signature, different msgHash) to ensure verify rejects altered payloads, complementing the “all zeros” signature case.


16-26: Confirmed: SLIP-0044 coin type 632 and “AU” prefix

Both assumptions are correct:

  • SLIP-0044 assigns Massa coin type 632.
  • Externally owned Massa addresses are serialized with the “AU” prefix.

• Optional improvement: add a canonical test vector (mnemonic + derivation path → full expected address) and assert the exact address to catch any future regressions, rather than only checking the prefix.

packages/signers/massa/package.json (3)

8-15: Add an explicit exports map and mark package as side-effect free

Improves Node/bundler interop (Esm/Cjs) and enables tree-shaking. Using publishConfig to override fields on publish is good; extend it to include exports. Also mark as sideEffects: false.

Apply this diff:

   "module": "src/index.ts",
   "publishConfig": {
     "main": "dist/index.cjs",
     "module": "dist/index.js",
-    "types": "dist/index.d.ts"
+    "types": "dist/index.d.ts",
+    "exports": {
+      ".": {
+        "types": "./dist/index.d.ts",
+        "import": "./dist/index.js",
+        "require": "./dist/index.cjs"
+      }
+    }
   },
+  "sideEffects": false,

Also applies to: 24-31


17-20: Ensure artifacts are built before publish

Without a prepublish step, you risk publishing an empty dist. Add prepublishOnly (or prepare) to guarantee builds on publish.

   "scripts": {
     "build": "tsup src/index.ts --format esm,cjs --dts --clean",
     "lint": "prettier --write .",
-    "test": "vitest run"
+    "test": "vitest run",
+    "prepublishOnly": "pnpm run build"
   },

21-23: Modernize Node engine, pin massa-web3 prerelease, remove unused types, and correct repository URL

  • Removed unused @types/hdkey (no references found in packages/signers/massa).
  • Confirmed @massalabs/massa-web3 is imported in src/index.ts; changed from caret-pinned prerelease to an exact 5.2.1-dev.
  • Recommended bumping the Node engine from >=14.15.0 to >=18 for alignment with current LTS and ESM ecosystem (TS 5.8.3/ESLint 9.27.0 support ≥14; please verify no regressions).
  • Updated repository metadata to point at the root Git URL and added the directory field.

Relevant file: packages/signers/massa/package.json

Proposed diff:

  "engines": {
-   "node": ">=14.15.0"
+   "node": ">=18"
  },
  "dependencies": {
-   "@massalabs/massa-web3": "^5.2.1-dev",
+   "@massalabs/massa-web3": "5.2.1-dev",
  },
  "devDependencies": {
-   "@types/hdkey": "^2.1.0",
  },
  "repository": {
    "type": "git",
-   "url": "git+https://github.com/enkryptcom/enKrypt/tree/main/packages/signers/massa"
+   "url": "git+https://github.com/enkryptcom/enKrypt.git",
+   "directory": "packages/signers/massa"
  }
packages/extension/src/providers/massa/methods/massa_getBalance.ts (2)

3-3: Remove unused import

Address is not used in this middleware.

-import { Address } from '@massalabs/massa-web3';

17-21: Stricter input validation for address parameter

Ensure the param is a string before validation to avoid accidental truthy non-strings.

-      const address = payload.params?.[0];
+      const address = payload.params?.[0];
       const network = this.network as MassaNetwork;
-      if (!address || !network.isValidAddress(address)) {
+      if (typeof address !== 'string' || !network.isValidAddress(address)) {
         res(getCustomError('Please enter a valid Massa address'));
         return;
       }
packages/extension/src/providers/massa/methods/massa_setNetwork.ts (1)

16-37: Simplify network lookup and handle case-insensitive names (optional)

You can lookup directly and avoid building a keys array; also optionally accept case-insensitive names.

-      const networkName = payload.params?.[0];
-
-      if (!networkName) {
+      const networkName = payload.params?.[0];
+      if (!networkName || typeof networkName !== 'string') {
         res(getCustomError('Network name is required'));
         return;
       }
-
-      // Check if the network exists
-      const availableNetworks = Object.keys(massaNetworks);
-
-      if (!availableNetworks.includes(networkName)) {
-        res(
-          getCustomError(
-            `Invalid network name. Available networks: ${availableNetworks.join(', ')}`,
-          ),
-        );
-        return;
-      }
-
-      // Get the network object
-      const network = massaNetworks[networkName as keyof typeof massaNetworks];
+      const key = (networkName in massaNetworks)
+        ? (networkName as keyof typeof massaNetworks)
+        : (Object.keys(massaNetworks).find(k => k.toLowerCase() === networkName.toLowerCase()) as keyof typeof massaNetworks | undefined);
+      const network = key ? massaNetworks[key] : undefined;
+      if (!network) {
+        res(getCustomError(`Invalid network name. Available networks: ${Object.keys(massaNetworks).join(', ')}`));
+        return;
+      }
packages/extension/src/ui/action/views/network-assets/index.vue (2)

62-69: Guard against undefined address when opening “Add custom token” modal

The address prop uses a non-null assertion. If the button is triggered before accountInfo is populated, this can pass undefined at runtime. Guard in v-if and drop the non-null assertion.

Apply this diff:

-    <custom-evm-token v-if="showAddCustomTokens && isEvmNetwork" :address="props.accountInfo.selectedAccount?.address!"
+    <custom-evm-token v-if="showAddCustomTokens && isEvmNetwork && !!props.accountInfo.selectedAccount?.address" :address="props.accountInfo.selectedAccount?.address"
       :network="(props.network as EvmNetwork)" @update:token-added="addCustomAsset"
       @update:close="toggleShowAddCustomTokens"></custom-evm-token>
@@
-    <custom-massa-token v-if="showAddCustomTokens && isMassaNetwork" :address="props.accountInfo.selectedAccount?.address!"
-      :network="props.network" @update:token-added="addCustomAsset"
+    <custom-massa-token v-if="showAddCustomTokens && isMassaNetwork && !!props.accountInfo.selectedAccount?.address" :address="props.accountInfo.selectedAccount?.address"
+      :network="props.network" @update:token-added="addCustomAsset"
       @update:close="toggleShowAddCustomTokens"></custom-massa-token>

155-162: Solid, explicit network gating for UI branches

The computed checks for EVM and Massa via ProviderName are straightforward and readable. Consider centralizing provider-type checks in a small helper if you find similar patterns repeated across views, but no change is required here.

packages/extension/src/types/base-network.ts (1)

11-11: Unify import path style for MassaAPI

All other provider APIs use the @ alias. Recommend switching to @/providers/massa/libs/api for consistency.

-import MassaAPI from '../providers/massa/libs/api';
+import MassaAPI from '@/providers/massa/libs/api';
packages/extension/src/providers/massa/libs/api.ts (3)

27-31: Harden balance lookup with error handling

If the node is unreachable or responds unexpectedly, this can throw and bubble up into UI. Consider catching errors and returning '0' (consistent with other getters’ defensive behavior).

   async getBalance(address: string): Promise<string> {
-    const [account] = await this.provider.balanceOf([address], false);
-    if (!account) return '0';
-    return account.balance.toString();
+    try {
+      const [account] = await this.provider.balanceOf([address], false);
+      if (!account) return '0';
+      return account.balance.toString();
+    } catch (_e) {
+      return '0';
+    }
   }

33-37: Wrap token balance lookup to avoid leaking provider errors

Same rationale as native balance; fallback to '0' if the contract call fails or the contract address is invalid.

   async getBalanceMRC20(address: string, contract: string): Promise<string> {
-    const mrc20 = new MRC20(this.provider, contract);
-    const balance = await mrc20.balanceOf(address);
-    return balance.toString();
+    try {
+      const mrc20 = new MRC20(this.provider, contract);
+      const balance = await mrc20.balanceOf(address);
+      return balance.toString();
+    } catch (_e) {
+      return '0';
+    }
   }

39-47: Reasonable default minimal fee on failure

Graceful fallback to a sensible minimal fee is good; consider exposing the fallback as a constant to centralize fee policy later.

packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (2)

15-21: Render error paragraph only when there’s an error

Currently an empty red line shows when there’s no error. Gate it on errorMsg.

-        <p
+        <p
+          v-if="errorMsg"
           class="verify-transaction__description"
           style="color: red"
           :class="{ popup: isPopup }"
         >
           {{ errorMsg }}
         </p>

167-174: Avoid relying on symbol to detect native transfers

Symbols can be user-facing and change; prefer an explicit flag on the token (e.g., isNative) or a branch on provider/network metadata.

packages/extension/src/providers/massa/networks/massa-base.ts (1)

71-79: Unify sparkline encoding across native and token assets (consistency)

Native MAS uses JSON.stringify of the last 25 points; custom tokens use Sparkline.dataValues. Consider standardizing to one format to keep the UI consumer logic simple.

If Sparkline is the standard across the app, you can do:

-              // Convert sparkline data to string format expected by UI
-              sparklineData = JSON.stringify(
-                marketInfo.sparkline_in_24h.price.slice(-25),
-              ); // Last 25 points
+              sparklineData = new Sparkline(
+                marketInfo.sparkline_in_24h.price,
+                25,
+              ).dataValues;
packages/extension/src/ui/action/views/network-assets/components/custom-massa-token.vue (2)

19-24: Avoid marking the field invalid when it’s empty

Currently the field shows invalid state on empty value. Make it invalid only when non-empty and failing validation.

-              :class="{ invalid: !isValidAddress }"
+              :class="{ invalid: contractAddress && !isValidAddress }"

255-257: Debounce contract lookups to reduce RPC chatter (optional)

fetchTokenInfo runs on every keystroke. Debounce to prevent unnecessary RPC calls.

You can replace the watcher with a debounced one (no extra deps):

// outside: let timer: number | undefined;
let timer: number | undefined;

watch(contractAddress, () => {
  if (timer) window.clearTimeout(timer);
  timer = window.setTimeout(fetchTokenInfo, 300);
});
packages/extension/src/providers/massa/index.ts (1)

78-81: More robust error serialization (optional)

Ensure a meaningful message even when e is not a standard Error.

-        return {
-          error: JSON.stringify(e.message),
-        };
+        return {
+          error: JSON.stringify(e?.message || String(e)),
+        };
📜 Review details

Configuration used: .coderabbit.yaml
Review profile: CHILL
Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 9f85baf and 8ed1760.

⛔ Files ignored due to path filters (1)
  • yarn.lock is excluded by !**/yarn.lock, !**/*.lock
📒 Files selected for processing (51)
  • packages/extension/package.json (1 hunks)
  • packages/extension/src/libs/background/index.ts (1 hunks)
  • packages/extension/src/libs/background/types.ts (3 hunks)
  • packages/extension/src/libs/tokens-state/index.ts (2 hunks)
  • packages/extension/src/libs/tokens-state/types.ts (1 hunks)
  • packages/extension/src/libs/utils/initialize-wallet.ts (3 hunks)
  • packages/extension/src/libs/utils/networks.ts (4 hunks)
  • packages/extension/src/providers/index.ts (2 hunks)
  • packages/extension/src/providers/massa/index.ts (1 hunks)
  • packages/extension/src/providers/massa/libs/activity-handlers/index.ts (1 hunks)
  • packages/extension/src/providers/massa/libs/activity-handlers/massa.ts (1 hunks)
  • packages/extension/src/providers/massa/libs/api.ts (1 hunks)
  • packages/extension/src/providers/massa/methods/index.ts (1 hunks)
  • packages/extension/src/providers/massa/methods/massa_getBalance.ts (1 hunks)
  • packages/extension/src/providers/massa/methods/massa_getNetwork.ts (1 hunks)
  • packages/extension/src/providers/massa/methods/massa_setNetwork.ts (1 hunks)
  • packages/extension/src/providers/massa/networks/buildnet.ts (1 hunks)
  • packages/extension/src/providers/massa/networks/index.ts (1 hunks)
  • packages/extension/src/providers/massa/networks/mainnet.ts (1 hunks)
  • packages/extension/src/providers/massa/networks/massa-base.ts (1 hunks)
  • packages/extension/src/providers/massa/types/index.ts (1 hunks)
  • packages/extension/src/providers/massa/ui/index.ts (1 hunks)
  • packages/extension/src/providers/massa/ui/libs/signer.ts (1 hunks)
  • packages/extension/src/providers/massa/ui/routes/index.ts (1 hunks)
  • packages/extension/src/providers/massa/ui/routes/names.ts (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/components/send-token-select.vue (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (1 hunks)
  • packages/extension/src/types/activity.ts (4 hunks)
  • packages/extension/src/types/base-network.ts (3 hunks)
  • packages/extension/src/types/provider.ts (4 hunks)
  • packages/extension/src/ui/action/App.vue (2 hunks)
  • packages/extension/src/ui/action/views/network-activity/index.vue (3 hunks)
  • packages/extension/src/ui/action/views/network-assets/components/custom-massa-token.vue (1 hunks)
  • packages/extension/src/ui/action/views/network-assets/index.vue (3 hunks)
  • packages/extension/src/ui/action/views/send-transaction/index.vue (2 hunks)
  • packages/extension/src/ui/action/views/verify-transaction/index.vue (2 hunks)
  • packages/extension/src/ui/provider-pages/routes.ts (2 hunks)
  • packages/keyring/package.json (1 hunks)
  • packages/keyring/src/index.ts (2 hunks)
  • packages/keyring/src/utils.ts (1 hunks)
  • packages/signers/massa/package.json (1 hunks)
  • packages/signers/massa/src/index.ts (1 hunks)
  • packages/signers/massa/src/libs/ed25519.ts (1 hunks)
  • packages/signers/massa/tests/sign.test.ts (1 hunks)
  • packages/signers/massa/tsconfig.json (1 hunks)
  • packages/signers/massa/tsconfig.paths.json (1 hunks)
  • packages/types/package.json (1 hunks)
  • packages/types/src/index.ts (1 hunks)
  • packages/types/src/networks.ts (2 hunks)
🧰 Additional context used
🧬 Code Graph Analysis (23)
packages/extension/src/providers/massa/methods/index.ts (1)
packages/extension/src/providers/massa/index.ts (1)
  • request (70-83)
packages/extension/src/providers/index.ts (1)
packages/extension/src/providers/massa/index.ts (1)
  • MassaProvider (18-92)
packages/extension/src/providers/massa/methods/massa_getNetwork.ts (2)
packages/extension/src/providers/massa/index.ts (1)
  • MassaProvider (18-92)
packages/extension/src/types/provider.ts (1)
  • ProviderRPCRequest (185-187)
packages/signers/massa/tests/sign.test.ts (2)
packages/utils/src/index.ts (1)
  • bufferToHex (38-38)
packages/signers/massa/src/index.ts (1)
  • MassaSigner (17-65)
packages/extension/src/providers/massa/networks/mainnet.ts (1)
packages/extension/src/providers/massa/networks/massa-base.ts (1)
  • MassaNetwork (26-250)
packages/extension/src/providers/massa/methods/massa_getBalance.ts (5)
packages/extension/src/providers/massa/index.ts (1)
  • MassaProvider (18-92)
packages/extension/src/types/provider.ts (1)
  • ProviderRPCRequest (185-187)
packages/extension/src/providers/massa/networks/massa-base.ts (1)
  • MassaNetwork (26-250)
packages/extension/src/libs/error/index.ts (1)
  • getCustomError (27-33)
packages/extension/src/providers/massa/libs/api.ts (1)
  • api (21-23)
packages/signers/massa/src/libs/ed25519.ts (2)
packages/signers/massa/src/index.ts (1)
  • sign (60-64)
packages/keyring/src/index.ts (1)
  • sign (201-227)
packages/extension/src/types/base-network.ts (1)
packages/extension/src/providers/massa/libs/api.ts (1)
  • MassaAPI (9-60)
packages/extension/src/providers/massa/networks/buildnet.ts (1)
packages/extension/src/providers/massa/networks/massa-base.ts (1)
  • MassaNetwork (26-250)
packages/keyring/src/utils.ts (1)
packages/keyring/src/index.ts (1)
  • basePath (106-111)
packages/extension/src/libs/background/types.ts (1)
packages/extension/src/providers/massa/index.ts (1)
  • MassaProvider (18-92)
packages/extension/src/providers/massa/ui/index.ts (1)
packages/extension/src/types/provider.ts (1)
  • UIExportOptions (189-192)
packages/extension/src/providers/massa/index.ts (2)
packages/types/src/index.ts (1)
  • MiddlewareFunction (194-194)
packages/extension/src/types/provider.ts (1)
  • ProviderRPCRequest (185-187)
packages/extension/src/providers/massa/types/index.ts (1)
packages/extension/src/types/base-network.ts (1)
  • BaseNetworkOptions (17-45)
packages/extension/src/providers/massa/methods/massa_setNetwork.ts (4)
packages/types/src/index.ts (1)
  • MiddlewareFunction (194-194)
packages/extension/src/providers/massa/index.ts (1)
  • MassaProvider (18-92)
packages/extension/src/types/provider.ts (1)
  • ProviderRPCRequest (185-187)
packages/extension/src/libs/error/index.ts (1)
  • getCustomError (27-33)
packages/extension/src/providers/massa/networks/massa-base.ts (3)
packages/extension/src/providers/massa/types/index.ts (1)
  • MassaNetworkOptions (9-15)
packages/extension/src/providers/massa/libs/api.ts (2)
  • api (21-23)
  • MassaAPI (9-60)
packages/extension/src/libs/tokens-state/types.ts (1)
  • CustomMassaToken (24-26)
packages/extension/src/providers/massa/ui/libs/signer.ts (3)
packages/utils/src/index.ts (2)
  • hexToBuffer (39-39)
  • bufferToHex (38-38)
packages/extension/src/providers/massa/types/index.ts (1)
  • MassaNetworkOptions (9-15)
packages/extension/src/libs/backup-state/index.ts (1)
  • msgHash (36-51)
packages/keyring/src/index.ts (1)
packages/signers/massa/src/index.ts (1)
  • MassaSigner (17-65)
packages/extension/src/libs/utils/initialize-wallet.ts (2)
packages/extension/src/libs/utils/accounts.ts (1)
  • getAccountsByNetworkName (14-44)
packages/extension/src/providers/massa/types/index.ts (1)
  • MassaNetworks (7-7)
packages/extension/src/libs/utils/networks.ts (3)
packages/extension/src/providers/bitcoin/types/index.ts (1)
  • BitcoinNetworks (5-9)
packages/extension/src/providers/kadena/types/index.ts (1)
  • KadenaNetworks (4-7)
packages/extension/src/providers/massa/types/index.ts (1)
  • MassaNetworks (7-7)
packages/extension/src/types/provider.ts (1)
packages/extension/src/types/activity.ts (1)
  • MassaRawInfo (150-150)
packages/signers/massa/src/index.ts (3)
packages/types/src/index.ts (3)
  • SignerInterface (187-187)
  • MnemonicWithExtraWord (205-205)
  • KeyPair (191-191)
packages/utils/src/index.ts (2)
  • bufferToHex (38-38)
  • hexToBuffer (39-39)
packages/signers/massa/src/libs/ed25519.ts (1)
  • derivePath (81-81)
packages/extension/src/libs/tokens-state/index.ts (1)
packages/extension/src/libs/tokens-state/types.ts (1)
  • CustomMassaToken (24-26)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
  • GitHub Check: buildAll
  • GitHub Check: test
🔇 Additional comments (61)
packages/signers/massa/tsconfig.paths.json (1)

2-7: LGTM: simple, scoped alias for local sources

The @src/* → src/* mapping is clean and avoids deep relative paths. No issues spotted.

packages/signers/massa/tsconfig.json (1)

1-29: ⚠️ Missing TypeScript Dependency Prevents Local Type-Checking

The tsconfig.json in packages/signers/massa is well-configured, but npx tsc -p packages/signers/massa/tsconfig.json --noEmit failed because the TypeScript compiler isn’t installed. To enable the final type-coverage check:

• In packages/signers/massa/package.json, add TypeScript as a devDependency:

npm install --save-dev typescript

• Re-run the check:

npx tsc -p packages/signers/massa/tsconfig.json --noEmit

Ensure no type errors remain.

packages/keyring/package.json (1)

28-28: LGTM: correct workspace dependency for Massa signer

Adding "@enkryptcom/signer-massa" as a workspace dep is the right move to wire the new signer into keyring.

packages/types/src/index.ts (1)

53-54: ed25519mas coverage verified
All occurrences of the new SignerType.ed25519mas have been wired through the codebase—no unsupported “not supported” paths remain:

• packages/types/src/index.ts – enum entry added
• packages/extension/src/providers/massa/networks/massa-base.ts – network’s signerType mapping
• packages/keyring/src/index.ts – signer dispatch table

No switch-on-SignerType statements (e.g. in PolkadotSigner) need ed25519mas support, and no other mappings omit it.

packages/types/src/networks.ts (2)

115-116: All downstream Massa network mappings verified
All occurrences of NetworkNames.Massa and NetworkNames.MassaBuildnet are present and correctly wired—no missing references.

• providers/massa/networks/index.ts: both Massa and MassaBuildnet entries mapped
• src/libs/utils/networks.ts: DEFAULT_MASSA_NETWORK_NAME and network list include Massa
• initialize-wallet.ts: handles NetworkNames.Massa
• UI (App.vue): case for NetworkNames.Massa with correct buyLink
• providers/index.ts & background types: ProviderName.massa and MassaProvider imported


186-186: Verify CoinGecko platform slug "massa" and add fallback

  • File: packages/types/src/networks.ts, line 186 (Massa = "massa",)
  • Query CoinGecko’s /asset_platforms endpoint (e.g. via pycoingecko or a direct HTTP call) to confirm that "massa" appears in the returned list.
  • In your price-fetcher logic, guard against unrecognized platform slugs and provide a safe fallback (e.g. default network, skip pricing, or surface a clear error).
packages/extension/src/types/activity.ts (3)

95-96: Typedef alias reads well

MassaRawInfo = OperationStatus keeps types lean and matches how other chains are modeled.


151-151: Export looks good

Publicly exposing MassaRawInfo is consistent with the rest of the file.


134-136: Confirmed handling of MassaRawInfo in all UI branches

Verified that every conditional in
packages/extension/src/ui/action/views/network-activity/index.vue
now includes the Massa case (lines 228–233), setting activity.rawInfo = massaInfo and updating status. The union in
packages/extension/src/types/activity.ts
already includes MassaRawInfo. No missing branches or serializers found. Approving changes.

packages/extension/src/libs/tokens-state/index.ts (1)

9-10: Importing CustomMassaToken is fine

No issues with the widened types import.

packages/extension/src/providers/massa/methods/massa_getNetwork.ts (1)

1-5: Middleware scaffolding and types are correct

Shape matches the provider’s middleware pattern and uses the MassaProvider context correctly.

packages/extension/src/providers/massa/ui/send-transaction/components/send-token-select.vue (1)

39-43: Confirm default decimals = 9 is correct for all Massa assets displayed here.

Hardcoding 9 as fallback may misrepresent balances for non-native assets. If this component can be used for tokens with different decimals, consider making decimals required or passing network/token defaults explicitly.

Would you like me to update this to prefer token.decimals and otherwise fall back to a provided network.decimals prop?

packages/extension/src/providers/massa/types/index.ts (3)

7-7: Re-exporting MassaNetworks looks good.


17-22: Fee info shape is pragmatic.

String-based values for fiat/native amounts are suitable for UI. No issues.


24-31: VerifyTransactionParams aligns with the UI flow.

Looks consistent with the verify screen’s needs.

packages/signers/massa/src/libs/ed25519.ts (2)

26-39: CKDPriv implementation matches SLIP-0010 hardened derivation.


1-3: Ensure Node crypto is available in all targets.

createHmac from "crypto" may not be polyfilled in browser builds (many bundlers dropped auto-polyfills). Confirm the build for the extension bundles a crypto shim or this runs only in Node-like contexts.

If needed, I can provide a minimal refactor to use a HMAC-SHA512 implementation that works in browsers (e.g., SubtleCrypto + a fallback).

packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue (1)

106-113: Confirm identicon() supports placeholder input.

Passing a 64-char zero string to identicon() may not be accepted by all implementations. If it expects a valid address, consider a local placeholder asset instead.

I can wire a lightweight SVG placeholder if needed.

packages/extension/src/providers/index.ts (1)

6-6: Massa provider is correctly wired into the providers map

Import and map entry look consistent with existing providers. The default export pattern remains unchanged and should integrate seamlessly with BackgroundHandler via Providers.

Also applies to: 15-15

packages/extension/src/ui/action/views/send-transaction/index.vue (1)

15-15: Cannot locate Massa send-transaction component for prop inspection

I wasn’t able to find send-transaction/index.vue under packages/extension/src/providers/massa/ui. Please verify:

  • The component exists at packages/extension/src/providers/massa/ui/send-transaction/index.vue
  • It defines the accountInfo and network props (via defineProps or props)
  • Its API matches other providers’ send-transaction components (e.g. Ethereum, Solana)
packages/extension/src/ui/provider-pages/routes.ts (1)

9-9: Massa UI routes export verified

  • packages/extension/src/providers/massa/ui/index.ts default export includes a routes property via getRoutes(ProviderName.massa).
  • packages/extension/src/providers/massa/ui/routes/index.ts exports a function that returns a RouteRecordRaw[].

This matches the pattern of other providers—no further changes required.

packages/extension/src/libs/background/types.ts (3)

6-6: Massa provider wired into background typings. LGTM.

The import looks correct and aligns with the provider’s default export.


8-17: TabProviderType updated to include Massa instances.

Union extension is consistent with existing providers; no issues spotted.


19-27: ProviderType includes Massa constructor.

Assuming MassaProvider is a class (constructor) default export (as in providers/massa/index.ts), this is correct. If the export ever changes to a factory or plain object, this would need to be revisited.

Please confirm that providers/index.ts (or equivalent registry) maps ProviderName.massa to MassaProvider so these types reflect actual runtime registration.

packages/extension/src/libs/utils/initialize-wallet.ts (2)

27-29: Account discovery for Massa integrated correctly.

Fetching and filtering Massa accounts mirrors the pattern used for other networks.


7-7: Import path looks right; ensure it aligns with the networks export.

No action needed if the default export from @/providers/massa/networks matches the usage above.

packages/extension/src/providers/massa/ui/index.ts (1)

1-9: UI export for Massa is correct.

providerName and routes wiring align with the established UIExportOptions pattern.

packages/extension/src/providers/massa/networks/mainnet.ts (2)

8-9: Explorer templates look correct for Massa mainnet

operation hash and address templates use the expected placeholders [[txHash]]/[[address]]. Looks consistent with BaseNetwork conventions.


5-14: Types are correct for MassaNetworkOptions

The createMassaNetworkOptions helper expects chainId to be a bigint and node to be a string.

  • CHAIN_ID.Mainnet is typed as bigint.
  • PublicApiUrl.Mainnet is a string.

No mismatches found—no changes required.

packages/extension/src/providers/massa/networks/index.ts (1)

5-8: LGTM: Network map wiring is correct

Massa mainnet/buildnet are correctly exposed under NetworkNames.Massa and NetworkNames.MassaBuildnet.

packages/extension/src/types/provider.ts (3)

26-27: MassaRawInfo union addition is good

Including MassaRawInfo in activity raw info unions keeps network activity UI/types coherent.


36-37: New provider name added

ProviderName.massa addition aligns with new network.


73-74: New provider type added

ProviderType.massa addition is consistent with existing patterns.

packages/extension/src/providers/massa/networks/buildnet.ts (2)

8-11: Explorer templates for Buildnet look fine

massexplo.com with network=buildnet parameters should work for test network activity/address deep links.


5-15: Confirm Buildnet network option types

Please verify in packages/extension/src/providers/massa/networks/buildnet.ts (lines 5–15) that:

  • node: PublicApiUrl.Buildnet is a string
  • chainId: CHAIN_ID.Buildnet is a bigint

If either value’s type doesn’t match the createMassaNetworkOptions signature, cast or convert it (e.g. BigInt(...) or .toString()) before passing into createMassaNetworkOptions.

packages/extension/src/libs/utils/networks.ts (6)

16-18: Wiring Massa into network registries is correct

Default import of MassaNetworks and mainnet anchor follows existing patterns used for other providers.


20-27: Provider map extended with Massa

Adding [ProviderName.massa]: MassaNetworks completes provider → networks mapping.


36-42: Include Massa networks in getAllNetworks

The concatenation order is fine; Massa networks will now be discoverable in generic listings.


75-83: Default network name/object for Massa added

Defaults mirror other providers. No issues spotted.


84-95: POPULAR_NAMES updated

Adding NetworkNames.Massa is reasonable to surface it in UI quick picks.


96-113: Export surface updated

DEFAULT_MASSA_NETWORK and DEFAULT_MASSA_NETWORK_NAME exported alongside others — consistent and helpful for consumers.

packages/keyring/src/index.ts (1)

22-22: Verification Complete: Massa signer wiring is correctly implemented

All end-to-end checks passed:

  • SignerType enum includes ed25519mas (packages/types/src/index.ts:53).
  • pathParser handles SignerType.ed25519mas with the correct hardened path (packages/keyring/src/utils.ts:17–19).
  • @enkryptcom/signer-massa is declared in keyring’s package.json (packages/keyring/package.json:28).
  • Registration in KeyRing maps SignerType.ed25519mas to new MassaSigner() (packages/keyring/src/index.ts:55–56).
packages/extension/src/ui/action/App.vue (1)

320-338: Preserve previously selected address if still valid — good improvement

Using DomainState.getSelectedAddress and falling back to the first active account is the right UX.

Edge case to double-check: networks where activeAccounts is empty. If this can happen, guard selectedAccount access elsewhere (e.g., places using selectedAccount!.address) to avoid runtime errors.

packages/extension/src/ui/action/views/verify-transaction/index.vue (1)

11-11: Massa verify flow is correctly registered

Import and mapping under ProviderName.massa are consistent with other providers.

Also applies to: 23-24

packages/extension/src/providers/massa/ui/routes/names.ts (1)

3-14: LGTM: minimal and consistent route wiring

send and verify routes follow the existing provider pattern with lazy-loaded components and provider-scoped names. Looks good.

packages/extension/src/ui/action/views/network-activity/index.vue (1)

71-73: Incorrect comparison concern—ignore

After checking the code:

  • type MassaRawInfo = OperationStatus;
  • getTransactionStatus for Massa returns an OperationStatus (not an object).
  • In index.vue, info as MassaRawInfo is itself the enum value, so comparing info === OperationStatus.X is correct.

Feel free to disregard the original comment.

Likely an incorrect or invalid review comment.

packages/extension/src/providers/massa/methods/massa_getBalance.ts (1)

24-30: LGTM: error-handled, delegated RPC with network-validated address

The middleware pattern is consistent with others: guards method, validates input, delegates to network API, and wraps errors in a provider-friendly format.

packages/extension/src/providers/massa/methods/massa_setNetwork.ts (1)

39-45: LGTM: provider swap with requestProvider handoff is correct

Switching networks via setRequestProvider aligns with the provider’s design and returns a concise result object.

packages/extension/src/types/base-network.ts (1)

37-44: Type unions updated correctly to include MassaAPI

Verified across the codebase that

  • BaseNetwork.api now includes Promise<MassaAPI>.
  • The only explicit cast to MassaAPI is in custom-massa-token.vue (line 165).
  • All other await network.api() calls remain narrowed to their respective API types (EvmAPI, SubstrateAPI, BitcoinAPI, KadenaAPI, SolanaAPI).

If you intend to support Massa in any conditional/switch over networkType, be sure to:

  • Add a NetworkType.Massa branch (e.g., in swap/libs/send-transactions.ts around lines 80–87, 174–181, 483–487).
  • Narrow the resulting API to MassaAPI before invoking its methods.

No other changes are required at this time.

packages/signers/massa/src/index.ts (3)

29-37: Private key construction matches Massa format

Prefixing 32-byte ed25519 seed with version byte (0) to produce a 33-byte Massa PrivateKey is correct; deriving PublicKey and Address from it is also correct.


60-64: sign() returns encoded signature string as expected

Returning the string form aligns with Massa web3 types and pairs with the verify() fix above.


22-27: Validate derivation path input & confirm seed format

In packages/signers/massa/src/index.ts (lines 22–27):

  • Ensure derivationPath is never empty. Either:
    • throw a clear error if it’s missing, e.g.
    if (!derivationPath) {
      throw new Error('Invalid derivationPath: must not be empty');
    }
    • or apply a project-wide default (for example, "m/44'/1022'/0'/0'/0'").
  • Confirm the imported derivePath implementation (likely from ed25519-hd-key or similar) accepts a hex seed string with a 0x prefix. If it does not, strip the prefix before calling it:
    const normalizedSeed = seed.startsWith('0x') ? seed.slice(2) : seed;
    const keys = derivePath(derivationPath, normalizedSeed);

Please verify both points are covered before merging.

packages/extension/src/providers/massa/libs/api.ts (2)

13-19: Provider initialization is straightforward

Constructing the JSON-RPC provider from RPC URL is idiomatic for massa-web3. No issues here.


49-59: Transaction and node status methods LGTM

Returning null on failure for operation status and direct node status passthrough both look fine.

packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (5)

183-192: Confirm unit handling for amount in native MAS transfers

amount: txData.toToken.amount implies base units. Ensure upstream always provides base units here. If not guaranteed, use a conversion similar to fee: toBase(displayValue, decimals).


203-215: MRC20 coins for balance creation: good UX consideration

Using StorageCost.MRC20BalanceCreationCost to pre-fund storage for recipients without balances is a nice touch. Ensure this returns "0" for recipients who already hold the token to avoid overpaying.

If you want, I can add a small unit to stub provider responses and assert the payload’s coins value varies (0 vs non-0) based on prior balance.


224-231: Sending operation payload looks correct

Passing serialized operation bytes, base58 public key, and encoded signature matches massa-web3 expectations. Combined with the verify fix in the signer, this should interoperate cleanly.


260-276: Storing activity for both parties is a good touch

Dual activity entries (sender and receiver) improve UX. Ensure background indexer updates the pending status to final when operation is included.


137-139: Ensure Buffer polyfill availability

It looks like Buffer.from(..., 'base64') is used here without any explicit import { Buffer } from 'buffer' in the extension code, so you’re relying on a global Buffer. Please verify that your bundler or extension build config injects a Buffer polyfill in all contexts—otherwise these base64-to-UTF8 decodes will break in environments where Buffer isn’t defined.

As an alternative, you can use native browser APIs for a zero-polyfill solution:

const binary = atob(route.query.txData as string);
const uint8 = Uint8Array.from(binary, c => c.charCodeAt(0));
const decoded = new TextDecoder().decode(uint8);
const txData: VerifyTransactionParams = JSON.parse(decoded);

Locations to review:

  • packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (lines 137–139)
  • Similar Buffer.from(..., 'base64') calls in other providers (kadena, polkadot, ethereum, solana, bitcoin) and swap/decode libraries
packages/extension/src/providers/massa/index.ts (1)

30-46: Could you show the surrounding context of the Massa provider’s constructor (e.g. the first ~100 lines of packages/extension/src/providers/massa/index.ts)? I want to confirm how and when network.node gets applied there before suggesting any changes.

packages/extension/src/providers/massa/ui/send-transaction/index.vue (1)

250-268: Balance/fee math relies on unit consistency (re-verify after the above fix)

After normalizing accountBalance to human units, hasEnoughBalance correctly converts to base with toBase. This will fix false positives/negatives on insufficient balance.

You don’t need code changes here beyond the previous comment, but please re-test:

  • MAS send: amount + fee <= balance
  • Token send: amount <= token balance and MAS balance >= fee

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 12

🧹 Nitpick comments (27)
packages/extension/configs/vitest.config.mts (1)

23-24: Consider broadening test globs (optional).
If you add UI tests, patterns like .tsx/.mts won’t match. Consider including them to avoid silent skips.

Apply if needed:

-    include: ['src/**/*.{test,spec}.ts', 'tests/**/*.{test,spec}.ts'],
+    include: [
+      'src/**/*.{test,spec}.{ts,tsx,mts}',
+      'tests/**/*.{test,spec}.{ts,tsx,mts}'
+    ],
packages/signers/massa/package.json (5)

8-12: Provide proper conditional exports for ESM/CJS and types

Relying on non-standard "module" risks resolver quirks. Add exports (applies only on publish via publishConfig).

Apply:

   "publishConfig": {
     "main": "dist/index.cjs",
     "module": "dist/index.js",
-    "types": "dist/index.d.ts"
+    "types": "dist/index.d.ts",
+    "exports": {
+      ".": {
+        "types": "./dist/index.d.ts",
+        "import": "./dist/index.js",
+        "require": "./dist/index.cjs"
+      }
+    }
   },

16-20: Ensure build artifacts exist before publish

Without a prepublish step, publishing could ship an empty dist if CI didn’t build.

Apply:

   "scripts": {
     "build": "tsup src/index.ts --format esm,cjs --dts --clean",
     "lint": "prettier --write .",
-    "test": "vitest run"
+    "test": "vitest run",
+    "prepublishOnly": "npm run build"
   },

5-7: Dev vs publish entrypoints: consider adding root types and sideEffects

Main/module pointing to TS source is fine in-workspace, but add root "types" for editor DX and declare sideEffects for better treeshaking.

Apply:

   "type": "module",
   "main": "src/index.ts",
   "module": "src/index.ts",
+  "types": "src/index.ts",
@@
   "files": [
     "dist"
   ],
+  "sideEffects": false,

Also applies to: 13-15


55-58: Fix repository URL and set monorepo directory

NPM expects the git remote URL; include "directory" for correct links.

Apply:

   "repository": {
     "type": "git",
-    "url": "git+https://github.com/enkryptcom/enKrypt/tree/main/packages/signers/massa"
+    "url": "git+https://github.com/enkryptcom/enKrypt.git",
+    "directory": "packages/signers/massa"
   },

34-38: Node types vs engines: consider aligning

Using @types/node@22 with engines ≥18 is okay but can cause minor lib mismatch. Either bump engines to ≥20 or downgrade types to match the supported baseline.

Would you prefer engines ">=20.11.0" to match Node 20 LTS used in many repos?

Also applies to: 21-23

packages/signers/massa/src/crypto/interfaces/sealer.ts (1)

3-6: Tighten Sealer types; avoid any and align with implementation.

PasswordSeal returns/consumes Uint8Array. The interface should reflect that for type safety.

 export default interface Sealer {
-  // eslint-disable-next-line @typescript-eslint/no-explicit-any
-  seal(data: Uint8Array): Promise<any>
-  // eslint-disable-next-line @typescript-eslint/no-explicit-any
-  unseal(data: any): Promise<Uint8Array>
+  seal(data: Uint8Array): Promise<Uint8Array>
+  unseal(data: Uint8Array): Promise<Uint8Array>
 }
packages/signers/massa/src/crypto/passwordSeal.ts (1)

51-51: Typo: PBKDF2 acronym.

Fix docstrings “PKDF2” → “PBKDF2”.

- * Seals data using password-based PKDF2 AES-256-GCM encryption.
+ * Seals data using password-based PBKDF2 AES-256-GCM encryption.
- * Unseals data using password-based PKDF2 AES-256-GCM decryption.
+ * Unseals data using password-based PBKDF2 AES-256-GCM decryption.

Also applies to: 64-64

packages/signers/massa/src/crypto/cross-browser.ts (1)

1-218: Optional: add minimal runtime guards for browser crypto availability.

You already throw on missing Web Crypto in PBKDF2; mirroring that in AES paths would make failures clearer.

packages/signers/massa/src/crypto/interfaces/signer.ts (1)

2-11: Clarify hashing responsibility in the contract.

Specify whether sign/verify expect raw message bytes or a pre-hashed digest (e.g., Blake3). This avoids double-hashing or interop breaks across providers.

packages/signers/massa/src/libs/ed25519.ts (1)

53-69: Confirm hardened-only semantics.

derivePath adds HARDENED_OFFSET unconditionally, so even m/0/1 becomes hardened-hardened. If you want apostrophes to matter, either reject non-hardened segments for ed25519 or only add offset when a segment ends with "'".

Optional change (reject non-hardened):

-  const segments = path
-    .split("/")
-    .slice(1)
-    .map(replaceDerive)
-    .map((el) => parseInt(el, 10));
-
-  return segments.reduce(
-    (parentKeys, segment) => CKDPriv(parentKeys, segment + offset),
-    { key, chainCode },
-  );
+  const raw = path.split("/").slice(1)
+  if (raw.some((s) => !s.endsWith("'"))) {
+    throw new Error("Non-hardened derivation is not supported for ed25519")
+  }
+  const segments = raw.map((s) => parseInt(replaceDerive(s), 10))
+  return segments.reduce((p, seg) => CKDPriv(p, seg + offset), { key, chainCode })
packages/signers/massa/src/crypto/interfaces/serializer.ts (1)

2-5: Document encoding to prevent ambiguity.

String format (base58/base64/hex) should be explicit to avoid mismatches across components.

-export default interface Serializer {
+/**
+ * Serializer for binary <-> string. The string encoding MUST be fixed and documented
+ * (e.g., base58, base64, hex) for cross-component compatibility.
+ */
+export default interface Serializer {
packages/signers/massa/src/crypto/base58.ts (2)

1-1: Avoid relying on esModuleInterop for CJS dependency.

Safer import style for bs58check across TS configs.

-import bs58check from 'bs58check'
+import * as bs58check from 'bs58check'

14-16: Type narrowing for decode result (minor).

Make the Uint8Array return explicit without extra allocs.

-  deserialize(data: string): Uint8Array {
-    return bs58check.decode(data)
-  }
+  deserialize(data: string): Uint8Array {
+    return bs58check.decode(data) as unknown as Uint8Array
+  }
packages/signers/massa/src/crypto/ed25519.ts (1)

16-23: Validate private key length to fail fast on misuse.

Accept common 32- or 64-byte inputs; throw otherwise.

   async getPublicKey(privateKey: Uint8Array): Promise<Uint8Array> {
-    return ed.getPublicKey(privateKey);
+    if (privateKey.length !== 32 && privateKey.length !== 64) {
+      throw new Error("Ed25519 privateKey must be 32 or 64 bytes");
+    }
+    return ed.getPublicKey(privateKey);
   }
@@
   async sign(privateKey: Uint8Array, data: Uint8Array): Promise<Uint8Array> {
-    return ed.sign(data, privateKey);
+    if (privateKey.length !== 32 && privateKey.length !== 64) {
+      throw new Error("Ed25519 privateKey must be 32 or 64 bytes");
+    }
+    return ed.sign(data, privateKey);
   }
packages/signers/massa/src/crypto/varintVersioner.ts (2)

17-20: Avoid spread copies when concatenating Uint8Arrays.

Use set() to reduce allocations.

   attach(version: Version, data: Uint8Array): Uint8Array {
-    const versionArray = varint.encode(version);
-    return new Uint8Array([...versionArray, ...data]);
+    const prefix = varint.encode(version);
+    const out = new Uint8Array(prefix.length + data.length);
+    out.set(prefix, 0);
+    out.set(data, prefix.length);
+    return out;
   }

31-33: Optional: Guard unsupported versions and use explicit consumed‐bytes in extract

We’ve confirmed that every caller in packages/signers/massa/src uses versioner.attach to prefix data with a varint-encoded version and versioner.extract to decode it (e.g. in libs/signature.ts, libs/address.ts, libs/keys.ts), so switching to an explicit consumed variable won’t break any single-byte expectations. To make future invalid or unrecognized versions fail fast and to clarify the byte‐offset calculation, consider this refactor in packages/signers/massa/src/crypto/varintVersioner.ts:

--- a/packages/signers/massa/src/crypto/varintVersioner.ts
+++ b/packages/signers/massa/src/crypto/varintVersioner.ts
@@ -30,4 +30,10 @@
   extract(data: Uint8Array): { version: Version; data: Uint8Array } {
-    const version = varint.decode(data);
-    return { data: data.slice(varint.decode.bytes), version };
+    const version = varint.decode(data);
+    const consumed = (varint.decode as any).bytes as number;
+    if (version !== Version.V0 && version !== Version.V1) {
+      throw new Error(`Unsupported version: ${version}`);
+    }
+    return { data: data.slice(consumed), version };
   }

• File needing update:
packages/signers/massa/src/crypto/varintVersioner.ts – inside the extract method.

This change is purely optional but improves safety and readability.

packages/signers/massa/src/libs/signature.ts (4)

71-75: Fix wrong variable used in version-mismatch error message.

The thrown message reports the detected version instead of the extracted one, making debugging confusing.

-        throw new Error(
-          `invalid version: ${version}. ${signature.version} was expected.`,
-        );
+        throw new Error(
+          `invalid version: ${extractedVersion}. ${version} was expected.`,
+        );
-      throw new Error(
-        `invalid version: ${version}. ${signature.version} was expected.`,
-      );
+      throw new Error(
+        `invalid version: ${extractedVersion}. ${version} was expected.`,
+      );

Also applies to: 97-101


76-78: Harden catch typing for TS “unknown” catch variables.

Avoid assuming e is Error.

-    } catch (e) {
-      throw new Error(`invalid signature string: ${e.message}`);
-    }
+    } catch (e) {
+      const msg = e instanceof Error ? e.message : String(e);
+      throw new Error(`invalid signature string: ${msg}`);
+    }

28-31: Mark ctor deps as readonly.

They’re never reassigned; readonly improves safety and intent.

-    public serializer: Serializer,
-    public versioner: Versioner,
-    public version: Version,
+    public readonly serializer: Serializer,
+    public readonly versioner: Versioner,
+    public readonly version: Version,

16-16: Typo in comment (“versionner”).

Minor docs nit.

-  // This should be done without serializer and versionner as they are potentially not known at this point
+  // This should be done without serializer and versioner as they are potentially not known at this point
packages/signers/massa/src/libs/address.ts (4)

161-167: Confirm address preimage (hashing versioned vs raw public key).

You hash publicKey.toBytes() (versioned). Many schemes hash the raw public key bytes. If Massa expects raw pubkey, the derived address will differ from reference implementations.

Proposed change if raw pubkey is required:

-    const rawBytes = publicKey.hasher.hash(publicKey.toBytes());
-    address.bytes = Uint8Array.from([
-      AddressType.EOA,
-      ...address.versioner.attach(Version.V0, rawBytes),
-    ]);
+    const { data: rawPublicKey } = address.versioner.extract(publicKey.toBytes());
+    const digest = publicKey.hasher.hash(rawPublicKey);
+    address.bytes = Uint8Array.from([
+      AddressType.EOA,
+      ...address.versioner.attach(Version.V0, digest),
+    ]);

If you want, I can cross-check against Massa’s spec and reference SDKs and adjust accordingly.


119-123: Fix wrong variable used in version-mismatch error message.

-        throw new Error(
-          `invalid version: ${version}. ${address.version} was expected.`,
-        );
+        throw new Error(
+          `invalid version: ${extractedVersion}. ${version} was expected.`,
+        );
-      throw new Error(
-        `invalid version: ${version}. ${address.version} was expected.`,
-      );
+      throw new Error(
+        `invalid version: ${extractedVersion}. ${version} was expected.`,
+      );

Also applies to: 188-191


37-38: Docstring return description is incorrect.

Function returns a prefix, not a version.

- * @returns the address version.
+ * @returns The address prefix.

142-147: Return type and error grammar in getType().

Tighten typing and fix message grammar.

-  private getType(): number {
+  private getType(): AddressType {
     if (!this.bytes) {
-      throw new Error("address bytes is not initialized");
+      throw new Error("address bytes are not initialized");
     }
-    return varint.decode(this.bytes);
+    return varint.decode(this.bytes) as AddressType;
   }
packages/signers/massa/src/libs/keys.ts (2)

341-345: Fix typo in verify() docs.

-   * This function very a byte-encoded message. The message is first hashed and then verified.
+   * This function verifies a byte-encoded message. The message is first hashed and then verified.

50-55: Mark ctor deps as readonly.

Consistency with Signature/Address suggestion; prevents accidental reassignment.

-    public hasher: Hasher,
-    public signer: Signer,
-    public serializer: Serializer,
-    public versioner: Versioner,
-    public version: Version,
+    public readonly hasher: Hasher,
+    public readonly signer: Signer,
+    public readonly serializer: Serializer,
+    public readonly versioner: Versioner,
+    public readonly version: Version,

Also applies to: 231-237

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 555d271 and a754ac7.

⛔ Files ignored due to path filters (1)
  • yarn.lock is excluded by !**/yarn.lock, !**/*.lock
📒 Files selected for processing (27)
  • packages/extension/configs/vitest.config.mts (1 hunks)
  • packages/extension/src/libs/utils/initialize-wallet.ts (3 hunks)
  • packages/extension/src/providers/massa/index.ts (1 hunks)
  • packages/extension/src/providers/massa/libs/activity-handlers/massa.ts (1 hunks)
  • packages/extension/src/providers/massa/libs/api.ts (1 hunks)
  • packages/extension/src/providers/massa/methods/index.ts (1 hunks)
  • packages/extension/src/providers/massa/methods/massa_getBalance.ts (1 hunks)
  • packages/extension/src/providers/massa/methods/massa_getNetwork.ts (1 hunks)
  • packages/extension/src/providers/massa/networks/massa-base.ts (1 hunks)
  • packages/signers/massa/package.json (1 hunks)
  • packages/signers/massa/src/crypto/base58.ts (1 hunks)
  • packages/signers/massa/src/crypto/blake3.ts (1 hunks)
  • packages/signers/massa/src/crypto/cross-browser.ts (1 hunks)
  • packages/signers/massa/src/crypto/ed25519.ts (1 hunks)
  • packages/signers/massa/src/crypto/interfaces/hasher.ts (1 hunks)
  • packages/signers/massa/src/crypto/interfaces/sealer.ts (1 hunks)
  • packages/signers/massa/src/crypto/interfaces/serializer.ts (1 hunks)
  • packages/signers/massa/src/crypto/interfaces/signer.ts (1 hunks)
  • packages/signers/massa/src/crypto/interfaces/versioner.ts (1 hunks)
  • packages/signers/massa/src/crypto/passwordSeal.ts (1 hunks)
  • packages/signers/massa/src/crypto/varintVersioner.ts (1 hunks)
  • packages/signers/massa/src/index.ts (1 hunks)
  • packages/signers/massa/src/libs/address.ts (1 hunks)
  • packages/signers/massa/src/libs/ed25519.ts (1 hunks)
  • packages/signers/massa/src/libs/index.ts (1 hunks)
  • packages/signers/massa/src/libs/keys.ts (1 hunks)
  • packages/signers/massa/src/libs/signature.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (9)
  • packages/extension/src/providers/massa/methods/massa_getNetwork.ts
  • packages/extension/src/providers/massa/methods/massa_getBalance.ts
  • packages/extension/src/providers/massa/networks/massa-base.ts
  • packages/extension/src/providers/massa/libs/activity-handlers/massa.ts
  • packages/signers/massa/src/index.ts
  • packages/extension/src/providers/massa/methods/index.ts
  • packages/extension/src/providers/massa/index.ts
  • packages/extension/src/libs/utils/initialize-wallet.ts
  • packages/extension/src/providers/massa/libs/api.ts
🧰 Additional context used
🧬 Code graph analysis (9)
packages/signers/massa/src/crypto/base58.ts (1)
packages/signers/massa/src/crypto/interfaces/serializer.ts (1)
  • Serializer (2-5)
packages/signers/massa/src/crypto/ed25519.ts (1)
packages/signers/massa/src/crypto/interfaces/signer.ts (1)
  • Signer (2-11)
packages/signers/massa/src/crypto/blake3.ts (1)
packages/signers/massa/src/crypto/interfaces/hasher.ts (1)
  • Hasher (2-4)
packages/signers/massa/src/crypto/cross-browser.ts (1)
packages/keyring/src/index.ts (1)
  • password (113-133)
packages/signers/massa/src/crypto/passwordSeal.ts (2)
packages/signers/massa/src/crypto/cross-browser.ts (4)
  • PBKDF2Options (84-88)
  • pbkdf2 (99-109)
  • aesGCMEncrypt (123-159)
  • aesGCMDecrypt (176-217)
packages/signers/massa/src/crypto/interfaces/sealer.ts (1)
  • Sealer (2-7)
packages/signers/massa/src/crypto/varintVersioner.ts (1)
packages/signers/massa/src/crypto/interfaces/versioner.ts (1)
  • Versioner (2-5)
packages/signers/massa/src/libs/address.ts (5)
packages/signers/massa/src/crypto/interfaces/serializer.ts (1)
  • Serializer (2-5)
packages/signers/massa/src/crypto/interfaces/versioner.ts (1)
  • Versioner (2-5)
packages/signers/massa/src/crypto/base58.ts (1)
  • Base58 (7-17)
packages/signers/massa/src/crypto/varintVersioner.ts (1)
  • VarintVersioner (7-34)
packages/signers/massa/src/libs/keys.ts (1)
  • PublicKey (225-384)
packages/signers/massa/src/libs/keys.ts (10)
packages/signers/massa/src/crypto/interfaces/hasher.ts (1)
  • Hasher (2-4)
packages/signers/massa/src/crypto/interfaces/signer.ts (1)
  • Signer (2-11)
packages/signers/massa/src/crypto/interfaces/serializer.ts (1)
  • Serializer (2-5)
packages/signers/massa/src/crypto/interfaces/versioner.ts (1)
  • Versioner (2-5)
packages/signers/massa/src/crypto/blake3.ts (1)
  • Blake3 (7-12)
packages/signers/massa/src/crypto/ed25519.ts (1)
  • Ed25519 (9-33)
packages/signers/massa/src/crypto/base58.ts (1)
  • Base58 (7-17)
packages/signers/massa/src/crypto/varintVersioner.ts (1)
  • VarintVersioner (7-34)
packages/signers/massa/src/libs/signature.ts (1)
  • Signature (23-122)
packages/signers/massa/src/libs/address.ts (1)
  • Address (65-254)
packages/signers/massa/src/libs/signature.ts (4)
packages/signers/massa/src/crypto/interfaces/serializer.ts (1)
  • Serializer (2-5)
packages/signers/massa/src/crypto/interfaces/versioner.ts (1)
  • Versioner (2-5)
packages/signers/massa/src/crypto/base58.ts (1)
  • Base58 (7-17)
packages/signers/massa/src/crypto/varintVersioner.ts (1)
  • VarintVersioner (7-34)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test
🔇 Additional comments (6)
packages/extension/configs/vitest.config.mts (1)

25-35: CI Node versions are sufficiently modern for import.meta.resolve

  • In .github/workflows/test-swap.yml and test-all.yml, the actions/setup-node@v4 step pins node-version: "22.10.0".
  • Other workflows (e.g. release/build-all) rely on the GitHub runner’s default Node.js (currently v20.x), which also supports import.meta.resolve.
  • All package.json files declare "node": ">=14.15.0", and since import.meta.resolve is stable in Node.js v16+, your CI configuration exceeds that requirement.

No further changes are required to avoid runtime errors in CI. You may optionally tighten your engines.node field to >=16.0.0 for local-development consistency, but it isn’t strictly necessary given your current CI setup.

packages/signers/massa/package.json (1)

21-23: Align Node engine with tooling requirements

Tooling here (eslint@9, vitest@3, tsup@8, typescript-eslint@8) requires Node ≥18. Engines set to 14 will break CI/local installs.

Apply:

-  "engines": {
-    "node": ">=14.15.0"
-  },
+  "engines": {
+    "node": ">=18.18.0"
+  },

Likely an incorrect or invalid review comment.

packages/signers/massa/src/crypto/cross-browser.ts (2)

123-159: LGTM on AES-GCM implementation details and tag handling.

Node/browser parity is clear; validations are good. With the Uint8Array changes above, this will be robust across environments.

Also applies to: 176-217


1-6: Doc nit: module comments are helpful and accurate.

No changes needed.

packages/signers/massa/src/libs/index.ts (1)

1-4: libs/index.ts correctly exports only derivePath; no default Ed25519 to forward

The file packages/signers/massa/src/libs/ed25519.ts only defines and exports the derivePath function—there is no export default class Ed25519 in this module. The Ed25519 signer implementation lives in packages/signers/massa/src/crypto/ed25519.ts.

• If you intended to expose the Ed25519 Signer class from this barrel, add:

export { default as Ed25519 } from "../crypto/ed25519";

• Otherwise, the current barrel is correct in re-exporting the HD derivation utility (derivePath) only.

Likely an incorrect or invalid review comment.

packages/signers/massa/src/crypto/interfaces/versioner.ts (1)

2-10: LGTM — clear, minimal contract for versioned payloads.

Interface and enum are straightforward and align with intended consumers.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between a754ac7 and afe65f1.

⛔ Files ignored due to path filters (1)
  • yarn.lock is excluded by !**/yarn.lock, !**/*.lock
📒 Files selected for processing (3)
  • package.json (1 hunks)
  • packages/extension/package.json (1 hunks)
  • packages/extension/src/providers/massa/networks/mainnet.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • packages/extension/package.json
🧰 Additional context used
🧬 Code graph analysis (1)
packages/extension/src/providers/massa/networks/mainnet.ts (1)
packages/extension/src/providers/massa/networks/massa-base.ts (2)
  • createMassaNetworkOptions (249-285)
  • MassaNetwork (22-246)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test
🔇 Additional comments (6)
package.json (2)

42-43: Unable to verify automatically—no vite.config.* files reference vite-plugin-node-polyfills or the script tooling failed. Please confirm that any workspace importing this plugin in its Vite config has it listed in its own package.json.


43-43: No changes required: vite-plugin-node-polyfills@0.24.0 is confirmed compatible with Vite 5.x and Node 18/20.

packages/extension/src/providers/massa/networks/mainnet.ts (4)

16-18: LGTM: network instantiation and export.

Instantiation and default export are clean and consistent with the pattern.


13-14: Confirmed CoinGecko ID: ‘massa’ is the correct CoinGecko asset ID for Massa (MAS); no changes needed.


12-12: No action required—chainId type is correct.
CHAIN_ID.Mainnet is already a bigint, matching the expected type in createMassaNetworkOptions.


8-9: Confirmed explorer URL patterns. The existing URLs (https://explorer.massa.net/mainnet/operation/[[txHash]] and https://explorer.massa.net/mainnet/address/[[address]]) match the live explorer; no changes needed.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

♻️ Duplicate comments (2)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (2)

72-86: Resolved: native symbol now correct

send-alert uses selectedAsset?.symbol || network.currencyName instead of network.name. Good catch.


376-386: Balance units bug (base vs human) and mutating a computed

api.getBalance returns base units, but elsewhere accountBalance is treated as human-readable. Also, writing to account.value.balance mutates a computed result.

Minimal fix (convert to human units):

-      const balance = await api.getBalance(addressFrom.value);
-      // Update the account object with the new balance
-      if (account.value) {
-        account.value.balance = balance;
-      }
+      const balanceBase = await api.getBalance(addressFrom.value);
+      const balance = fromBase(balanceBase, 9); // MAS has 9 decimals
+      // Update the account object with the human-readable balance
+      if (account.value) {
+        account.value.balance = balance;
+      }

Optional refactor (avoid mutating a computed): introduce a local ref and derive accountBalance from it.

// declare near other refs
const accountBalanceRef = ref<string>('0');

// replace the computed at lines 200-203:
const accountBalance = computed(() => accountBalanceRef.value);

// and set it here instead of mutating `account.value`:
accountBalanceRef.value = balance;
🧹 Nitpick comments (4)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (4)

281-283: Avoid magic number for MAS decimals

Use the selected token’s decimals for consistency.

-      return fromBase(insufficientBase.toString(), 9);
+      return fromBase(
+        insufficientBase.toString(),
+        selectedAsset.value.decimals
+      );

89-89: Dynamic fee label

Avoid hard-coding “MAS” so testnets or future networks display the right symbol.

-        <label>Fee (MAS)</label>
+        <label>Fee ({{ network.currencyName }})</label>

144-153: Make required props explicit

Using {} defaults on typed objects can mask errors. Mark as required.

   network: {
-    type: Object as PropType<BaseNetwork>,
-    default: () => ({}),
+    type: Object as PropType<BaseNetwork>,
+    required: true,
   },
   accountInfo: {
-    type: Object as PropType<AccountsHeaderData>,
-    default: () => ({}),
+    type: Object as PropType<AccountsHeaderData>,
+    required: true,
   },

505-508: Remove dead handler or implement toggle

toggleSelector is a no-op; either wire it to open token selector or remove the listener from send-header.

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between afe65f1 and f173a23.

📒 Files selected for processing (3)
  • packages/extension/package.json (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue (1 hunks)
  • packages/signers/massa/src/crypto/ed25519.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (2)
  • packages/signers/massa/src/crypto/ed25519.ts
  • packages/extension/package.json
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: buildAll
🔇 Additional comments (3)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (3)

537-537: Verify toTokenAddress for MAS

For native MAS transfers, contract may be empty/undefined. Ensure the verify flow and signer handle native transfers without a contract address.


553-557: Buffer API is already polyfilled via Vite config
The Vite setup in packages/extension/vite.config.ts uses nodePolyfills({ include: ['buffer', …] }), so Buffer.from(...).toString('base64') and its reverse on the verify screen will work without importing Buffer or switching to btoa.


248-261: Ensure api.getBalance returns raw base units
In updateAccountBalance, account.value.balance = balance assigns whatever MassaAPI.getBalance returns. In getAllTokenInfo, api.getBalance yields a base‐unit string (e.g. raw integer amount) which is then converted to human units via fromBase(balance, decimals) before use(). If api.getBalance indeed returns base units, then elsewhere using accountBalance.value directly (e.g. parseFloat(accountBalance)) treats it as human units—causing incorrect fee checks.

  • Confirm in packages/extension/src/providers/massa/libs/api.ts that getBalance returns a raw string/BigInt in base units; if it already formats to human units, update comment here.
  • If it returns base units, wrap balance in fromBase(balance, 9) before assigning to account.value.balance, or adjust all downstream uses to convert from base units.

Comment on lines +352 to +360
onMounted(async () => {
const currentAccount = account.value;
if (currentAccount?.address && !addressFrom.value) {
addressFrom.value = currentAccount.address;
} else {
const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
addressFrom.value = accounts[0].address;
}

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Guard against empty keyring accounts

accounts[0] can be undefined and crash subsequent logic.

Apply:

-    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
-    addressFrom.value = accounts[0].address;
+    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
+    addressFrom.value = accounts?.[0]?.address || '';

Optionally, early-return or show an error if no accounts are found.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
onMounted(async () => {
const currentAccount = account.value;
if (currentAccount?.address && !addressFrom.value) {
addressFrom.value = currentAccount.address;
} else {
const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
addressFrom.value = accounts[0].address;
}
onMounted(async () => {
const currentAccount = account.value;
if (currentAccount?.address && !addressFrom.value) {
addressFrom.value = currentAccount.address;
} else {
const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
addressFrom.value = accounts?.[0]?.address || '';
}
// …rest of the mounted logic…
});
🤖 Prompt for AI Agents
In packages/extension/src/providers/massa/ui/send-transaction/index.vue around
lines 352–360, the code assumes accounts[0] exists which can be undefined and
crash; after awaiting keyRing.getAccounts([...]) check that accounts is non-null
and accounts.length > 0, and if empty either set a user-visible
error/notification and return early (or set a sensible fallback), otherwise
safely use accounts[0].address; ensure you don’t dereference accounts[0] before
this check and keep the existing addressFrom assignment inside the validated
branch.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (4)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (4)

332-369: Validate fee decimals and enforce minimal fee in isInputsValid

Without this, users can submit with invalid precision or below-network fee; downstream toBase() may also throw on bad input.

 const isInputsValid = computed<boolean>(() => {
   // First check if address is provided
   if (!addressTo.value || addressTo.value.trim() === '') {
     return false;
   }
@@
   // Check if a token is selected
   if (!selectedAsset.value) {
     return false;
   }
@@
   // Check if amount is greater than 0
   if (amountNum <= 0) {
     return false;
   }
-
-  const result = hasEnoughBalance.value;
-  return result;
+
+  // Validate fee precision and minimal fee
+  if (!isValidDecimals(fee.value, 9)) return false;
+  try {
+    const feeBase = BigInt(toBase(fee.value || '0', 9));
+    const minBase = BigInt(toBase(minimalFee.value || '0', 9));
+    if (feeBase < minBase) return false;
+  } catch {
+    return false;
+  }
+
+  return hasEnoughBalance.value;
 });

381-383: Guard against empty keyring results to avoid runtime crash

getAccounts() can return an empty array. Accessing accounts[0].address will throw.

-    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
-    addressFrom.value = accounts[0].address;
+    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
+    addressFrom.value = accounts?.[0]?.address || '';
+    if (!addressFrom.value) {
+      // No Massa accounts; keep UI inert
+      return;
+    }

404-409: Balance units mismatch: convert base→human before storing

Elsewhere balance is treated as human-readable and re-converted with toBase (e.g., Line 259). Writing base units here breaks fee/balance checks.

-      const balance = await api.getBalance(addressFrom.value);
-      // Update the account object with the new balance
-      if (account.value) {
-        account.value.balance = balance;
-      }
+      const balanceBase = await api.getBalance(addressFrom.value);
+      const balance = fromBase(balanceBase, 9); // MAS has 9 decimals
+      // Update the account object with the human-readable balance
+      if (account.value) {
+        account.value.balance = balance;
+      }

560-561: Fix typo: price uses non-existent field valuef

This serializes undefined and breaks USD pricing on verify.

-        price: selectedAsset.value.valuef || '0',
+        price: selectedAsset.value.value || '0',
🧹 Nitpick comments (4)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (4)

433-441: Type the augmented assets instead of using any[]

Define a narrowed type that extends AssetsType with price to improve safety across AssetsSelectList usage.

-const accountAssets = ref<any[]>([]);
+type AssetWithPrice = AssetsType & { price: string };
+const accountAssets = ref<AssetWithPrice[]>([]);
@@
-    const tokensWithPrice = tokenInfos.map((token: AssetsType) => ({
+    const tokensWithPrice: AssetWithPrice[] = tokenInfos.map((token: AssetsType) => ({
       ...token,
       price: token.value, // Use value field as price for USD display
     }));

135-137: Decouple from Solana provider component

Importing SendAlert from the Solana path couples Massa UI to another provider. Move/alias this alert in common or the Massa folder for locality.


506-517: Max for MAS should clamp at zero with explicit guard

BigInt subtraction can be negative; you already check >0n, but make the clamp explicit to avoid accidental negative conversions if logic changes.

-    const maxAmountBase = balanceNum - feeNum;
-    if (maxAmountBase > 0n) {
+    const maxAmountBase = balanceNum > feeNum ? balanceNum - feeNum : 0n;
+    if (maxAmountBase > 0n) {
       amount.value = fromBase(
         maxAmountBase.toString(),
         selectedAsset.value.decimals,
       );

239-245: Round fiat values consistently

Consider using toFixed(2, BigNumber.ROUND_DOWN) or a shared formatter to avoid rounding up fees/amounts unexpectedly.

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between f173a23 and 0115ba6.

⛔ Files ignored due to path filters (1)
  • yarn.lock is excluded by !**/yarn.lock, !**/*.lock
📒 Files selected for processing (3)
  • packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue (1 hunks)
  • packages/extension/vite.config.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test
🔇 Additional comments (4)
packages/extension/vite.config.ts (1)

56-60: Make BUILD_TIME locale-agnostic and reproducible

toLocaleString()+replace(/\D/g, '') depends on the build machine’s locale and can yield ambiguous or empty values. Switch to a stable UTC format with an optional env override:

-        : JSON.stringify(new Date().toLocaleString().replace(/\D/g, '')),
+        : JSON.stringify(process.env.BUILD_TIME ?? new Date().toISOString().slice(0, 19).replace(/[-:T]/g, '')),

Also confirm whether the static 'FF-build' for Firefox builds is intentional; otherwise align it to use the same timestamp logic.

packages/extension/src/providers/massa/ui/send-transaction/index.vue (3)

72-76: Good fix on native symbol

Passing selectedAsset?.symbol || network.currencyName to the balance alert is correct and resolves the earlier mismatch.


562-562: Native MAS may not have a contract address

If MAS is native, selectedAsset.contract could be empty/undefined. Ensure the verify flow treats this field as optional or conditionally omit it.

Would you like me to patch this to set toTokenAddress only for non-MAS tokens?


579-581: No changes required—Buffer is polyfilled in the extension build
Rollup’s inject plugin already provides a browser‐safe Buffer (see packages/extension/configs/rollup.config.base.ts:36–37), so using Buffer.from(...).toString('base64') here is safe.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (2)
packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue (2)

127-130: Always emit toggle state on both focus and blur.

Consumers won’t know when to hide contacts otherwise.

 const changeFocus = (val: FocusEvent) => {
   isFocus.value = val.type === 'focus';
-  if (isFocus.value) emit('toggle:showContacts', isFocus.value);
+  emit('toggle:showContacts', isFocus.value);
 };

79-82: Guard against undefined validator to prevent runtime crash.

props.network defaults to {} and isValidAddress may be undefined, which will throw on non-empty input.

Apply:

-const isValidMassaAddress = computed(() => {
-  if (!massaAddress.value || massaAddress.value.trim() === '') return false;
-  return props.network.isValidAddress(massaAddress.value);
-});
+const isValidMassaAddress = computed(() => {
+  const val = massaAddress.value?.trim() ?? '';
+  if (!val) return false;
+  return props.network?.isValidAddress?.(val) ?? false;
+});
🧹 Nitpick comments (5)
packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue (5)

46-51: Use Clipboard API (with fallback) and declare emit before use.

document.execCommand('paste') is deprecated and often blocked. Prefer navigator.clipboard.readText() with a safe fallback. This also requires moving defineEmits above the function.

-const pasteFromClipboard = () => {
-  addressInput.value?.focus();
-  document.execCommand('paste');
-};
-defineExpose({ addressInput, pasteFromClipboard });
+const emit = defineEmits<{
+  (e: 'update:inputAddress', address: string): void;
+  (e: 'toggle:showContacts', show: boolean): void;
+}>();
+
+const pasteFromClipboard = async () => {
+  try {
+    addressInput.value?.focus();
+    const text = await navigator.clipboard.readText();
+    emit('update:inputAddress', text.trim());
+  } catch {
+    // Fallback for environments without Clipboard API/permissions
+    addressInput.value?.focus();
+    document.execCommand?.('paste');
+  }
+};
+defineExpose({ addressInput, pasteFromClipboard });
-const emit = defineEmits<{
-  (e: 'update:inputAddress', address: string): void;
-  (e: 'toggle:showContacts', show: boolean): void;
-}>();
+// moved above to use in pasteFromClipboard

Also applies to: 70-73


93-103: Avoid side-effects inside a computed getter.

Setting reactive state (identiconError) from within a computed can cause re-computation loops and is an anti-pattern. Just return null on error; rely on @error handler for load failures.

-  try {
-    if (props.network && props.network.identicon) {
-      return props.network.identicon(massaAddress.value);
-    }
-  } catch (error) {
-    console.error('Error generating identicon:', error);
-    // Set error state outside of computed property
-    nextTick(() => {
-      identiconError.value = true;
-    });
-  }
+  try {
+    return props.network?.identicon?.(massaAddress.value) ?? null;
+  } catch (error) {
+    console.error('Error generating identicon:', error);
+    return null;
+  }

20-31: Minor a11y: reflect validity and disable noisy browser heuristics.

Expose validity and turn off autocorrect for addresses.

       <input
         ref="addressInput"
         v-model="address"
         type="text"
         :disabled="disableDirectInput"
         placeholder="Enter Massa address"
+        :aria-invalid="!!(massaAddress && !isValidMassaAddress)"
+        autocomplete="off"
+        autocapitalize="none"
+        spellcheck="false"
         :style="{
           color: massaAddress && !isValidMassaAddress ? 'red' : 'black',
         }"
         @focus="changeFocus"
         @blur="changeFocus"
       />

59-63: Type-safe default for network or make it required.

Defaulting to {} violates the contract and forces defensive checks. Prefer null default (with optional chaining) or required: true.

-  network: {
-    type: Object as PropType<MassaNetwork>,
-    default: () => ({}),
-  },
+  network: {
+    type: Object as PropType<MassaNetwork | null>,
+    default: null,
+  },

145-147: Duplicate CSS declaration.

box-sizing: border-box; is set twice; keep one.

   box-sizing: border-box;
-  border: 1px solid @gray02;
-  box-sizing: border-box;
+  border: 1px solid @gray02;
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 0115ba6 and 99c6b70.

📒 Files selected for processing (3)
  • packages/extension/src/providers/common/ui/send-transaction/send-input-amount.vue (2 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/components/send-address-input.vue (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue (1 hunks)
✅ Files skipped from review due to trivial changes (1)
  • packages/extension/src/providers/common/ui/send-transaction/send-input-amount.vue
🚧 Files skipped from review as they are similar to previous changes (1)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

🧹 Nitpick comments (4)
packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (4)

173-174: Confirm hardcoded MAS decimals

toBase(txData.txFee.nativeValue, 9) assumes 9 decimals. If MAS decimals are centralized elsewhere, derive from network/token metadata to avoid drift.


15-21: Replace inline error color with themed class

Inline style="color: red" bypasses theming. Use a BEM modifier and theme variable (e.g., --error color) for consistency/accessibility.


258-276: Activity type for token transfers

If ActivityType differentiates native vs token transfers, consider using a token-specific type for MRC20 to improve UX/filters.


318-324: Micro: avoid DOM reads on render for scroll check

isHasScroll() reads classList each render. Consider caching via a computed or an event from the scrollbar to toggle the border class.

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 99c6b70 and 660ea08.

📒 Files selected for processing (1)
  • packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (1 hunks)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test
🔇 Additional comments (1)
packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (1)

209-215: Verify Massa call payload field names and sendOperation return shape

  • Ensure OperationType.CallSmartContractFunction expects { to, func, data, coins } as named; some APIs use targetAddress, targetFunction, parameter.
  • Confirm massaClient.sendOperation returns a single operation ID (string). If it returns an array, assign the first element and store consistently in operationIdRef.

Also applies to: 224-230

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (1)
packages/extension/src/ui/action/views/network-activity/index.vue (1)

222-245: Do not fail non-terminal Massa states; map only terminal states and keep polling otherwise

Anything not “success” is currently marked failed, and PendingInclusion is the only non-terminal you skip. Massa distinguishes terminal vs non-terminal states; treat only terminal success/failure as final, keep polling for the rest.

Apply:

-  } else if (props.network.provider === ProviderName.massa) {
-    if (!info) return;
-    const massaInfo = info as MassaRawInfo;
-    if (isActivityUpdating || massaInfo === OperationStatus.PendingInclusion)
-      return;
-
-    let status = ActivityStatus.failed;
-    // if the transaction is not found, and it's been less than 1 minute, wait for it to be processed
-    if (
-      massaInfo === OperationStatus.NotFound &&
-      Date.now() < activity.timestamp + 60_000
-    ) {
-      return;
-    } else if (
-      massaInfo === OperationStatus.Success ||
-      massaInfo === OperationStatus.SpeculativeSuccess
-    ) {
-      status = ActivityStatus.success;
-    }
-
-    activity.status = status;
-    activity.rawInfo = massaInfo;
-    updateActivitySync(activity).then(() => updateVisibleActivity(activity));
+  } else if (props.network.provider === ProviderName.massa) {
+    if (!info || isActivityUpdating) return;
+    const status = info as unknown as OperationStatus;
+
+    // Non-terminal: keep polling
+    if (
+      status === OperationStatus.INCLUDED_PENDING ||
+      status === OperationStatus.AWAITING_INCLUSION
+    ) {
+      return;
+    }
+
+    // Grace period for NOT_FOUND (node lag)
+    if (
+      status === OperationStatus.NOT_FOUND &&
+      Date.now() < activity.timestamp + 60_000
+    ) {
+      return;
+    }
+
+    // Terminal mapping
+    activity.status =
+      status === OperationStatus.FINAL
+        ? ActivityStatus.success
+        : ActivityStatus.failed; // e.g., INCONSISTENT or late NOT_FOUND
+    activity.rawInfo = info as MassaRawInfo;
+    updateActivitySync(activity).then(() => updateVisibleActivity(activity));
   }

Rationale: FINAL is terminal success; INCONSISTENT/late NOT_FOUND are terminal failures; INCLUDED_PENDING/AWAITING_INCLUSION are non-terminal and must not stop the poller. Keep the global clearInterval reliant on reaching this block only after a terminal state. (npmjs.com, docs.massa.net)

🧹 Nitpick comments (1)
packages/extension/src/ui/action/views/network-activity/index.vue (1)

71-72: Clarify MassaRawInfo shape vs value

You use massaInfo as a bare enum value (compared directly to OperationStatus.*) but assign it to activity.rawInfo typed as MassaRawInfo. Ensure MassaRawInfo is actually the enum (or wrap it as { status: OperationStatus }) to avoid type drift at persistence/serialization boundaries.
Would you like me to align the activity type and storage schema?

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 660ea08 and 543105b.

📒 Files selected for processing (4)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue (1 hunks)
  • packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue (1 hunks)
  • packages/extension/src/ui/action/views/network-activity/index.vue (3 hunks)
  • packages/extension/src/ui/action/views/network-assets/components/custom-massa-token.vue (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (3)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue
  • packages/extension/src/ui/action/views/network-assets/components/custom-massa-token.vue
  • packages/extension/src/providers/massa/ui/send-transaction/verify-transaction/index.vue
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (4)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (4)

549-550: Fix typo: toToken.price uses non-existent field valuef

This serializes undefined and breaks fiat display on verify.

-        price: selectedAsset.value.valuef || '0',
+        price: selectedAsset.value.value || '0',

Run to confirm there are no other valuef typos:

#!/bin/bash
rg -n "valuef" -S

87-94: Bind fee placeholder/min correctly (mustache doesn't work in Vue templates)

Current attributes won’t reflect minimalFee and won’t enforce min.

-          <input
-            v-model="fee"
-            type="number"
-            placeholder="{{ minimalFee }}"
-            class="fee-input"
-            step="0.000000001"
-            min="{{ minimalFee }}"
-          />
+          <input
+            v-model="fee"
+            type="number"
+            :placeholder="minimalFee"
+            class="fee-input"
+            step="0.000000001"
+            :min="minimalFee"
+            inputmode="decimal"
+          />

383-391: Keep account.balance in human units (9 decimals), not base units

Elsewhere you treat account.balance as human-readable and convert via toBase. Assigning base units here breaks fee/balance checks.

-      const api = (await network.value.api()) as MassaAPI;
-      const balance = await api.getBalance(addressFrom.value);
-      // Update the account object with the new balance
-      if (account.value) {
-        account.value.balance = balance;
-      }
+      const api = (await network.value.api()) as MassaAPI;
+      const balanceBase = await api.getBalance(addressFrom.value);
+      const balance = fromBase(balanceBase, 9); // MAS has 9 decimals
+      if (account.value) {
+        account.value.balance = balance;
+      }

358-366: Guard against empty keyring accounts to avoid crash

accounts[0] may be undefined.

-  } else {
-    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
-    addressFrom.value = accounts[0].address;
-  }
+  } else {
+    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
+    addressFrom.value = accounts?.[0]?.address || '';
+  }
🧹 Nitpick comments (3)
packages/extension/src/ui/action/components/app-menu/index.vue (1)

352-361: Sorting by name_long is sensible. Consider immutability, fallback, and case-insensitive compare.

  • Don’t mutate the input array; return a sorted copy to avoid side effects.
  • Gracefully fallback to name if name_long is ever missing.
  • Use case-insensitive comparison for a more consistent UX.
 const sortNetworks = (networks: BaseNetwork[], sortBy: NetworkSort) => {
-  return networks.sort((a, b) => {
+  return [...networks].sort((a, b) => {
     if (sortBy.name === NetworkSortOption.Name) {
-      return sortBy.direction === NetworkSortDirection.Asc
-        ? a.name_long.localeCompare(b.name_long)
-        : b.name_long.localeCompare(a.name_long);
+      const aName = a.name_long ?? a.name;
+      const bName = b.name_long ?? b.name;
+      return sortBy.direction === NetworkSortDirection.Asc
+        ? aName.localeCompare(bName, undefined, { sensitivity: 'base' })
+        : bName.localeCompare(aName, undefined, { sensitivity: 'base' });
     }
     return 0;
   });
 };
packages/extension/src/providers/massa/ui/send-transaction/index.vue (2)

172-198: Avoid mutating a computed ref (account)

You mutate account.value.balance though account is derived from props. Prefer a writable ref synced from props to prevent surprising overrides when props change.

  • Create const accountRef = ref({...}) on mount and watch props.accountInfo to resync fields; replace usages of account with accountRef.
  • Keep API refreshes writing to accountRef.value.balance.

Also applies to: 383-391


120-141: Decouple Solana-specific path for SendAlert

Importing from solana path in a Massa view creates cross-provider coupling.

  • Move send-alert.vue to a shared location (e.g., @/providers/common/ui/send-transaction/components/) and import from there, or re-export under a common alias.
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 543105b and 776c10b.

📒 Files selected for processing (2)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue (1 hunks)
  • packages/extension/src/ui/action/components/app-menu/index.vue (1 hunks)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test
🔇 Additional comments (1)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (1)

541-561: toTokenAddress correctly optional for native MAS
VerifyTransactionParams declares toTokenAddress?, and in sendAction the branch txData.toToken.symbol === 'MAS' skips any check on toTokenAddress, so native MAS transfers proceed without it.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

♻️ Duplicate comments (5)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (5)

386-391: Fix unit mismatch: keep account.balance in human-readable MAS

api.getBalance returns base units. You later call toBase(accountBalance, 9), double-converting and breaking balance/fee math.

-      const balance = await api.getBalance(addressFrom.value);
-      // Update the account object with the new balance
-      if (account.value) {
-        account.value.balance = balance;
-      }
+      const balanceBase = await api.getBalance(addressFrom.value);
+      const balance = fromBase(balanceBase, 9); // MAS has 9 decimals
+      // Update the account object with the human-readable balance
+      if (account.value) {
+        account.value.balance = balance;
+      }

363-365: Guard against empty keyring accounts to avoid crash

accounts[0] can be undefined. Add a safe check and early return/UI notice.

-    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
-    addressFrom.value = accounts[0].address;
+    const accounts = await keyRing.getAccounts([SignerType.ed25519mas]);
+    addressFrom.value = accounts?.[0]?.address || '';
+    if (!addressFrom.value) {
+      // Optionally show a user-facing error or disable form
+      return;
+    }

90-94: Bind fee placeholder/min with Vue bindings (mustache here doesn’t work)

Current markup shows literal “{{ minimalFee }}” and doesn’t enforce min.

-          <input
-            v-model="fee"
-            type="number"
-            placeholder="{{ minimalFee }}"
-            class="fee-input"
-            step="0.000000001"
-            min="{{ minimalFee }}"
-          />
+          <input
+            v-model="fee"
+            type="number"
+            :placeholder="minimalFee"
+            class="fee-input"
+            step="0.000000001"
+            :min="minimalFee"
+          />

162-166: Enforce minimal fee and validate fee before balance math

Fee is neither validated nor checked against minimalFee; toBase(fee) can throw and allow under-min fees.

@@
-const fee = ref<string>('0.01');
-const minimalFee = ref<string>('0.01');
+const fee = ref<string>('0.01');
+const minimalFee = ref<string>('0.01');
+const isFeeValid = computed(() => {
+  if (!isValidDecimals(fee.value, 9) || !isNumericPositive(fee.value)) return false;
+  try {
+    return BigInt(toBase(fee.value, 9)) >= BigInt(toBase(minimalFee.value, 9));
+  } catch {
+    return false;
+  }
+});
@@
-  const amount = BigInt(toBase(sendAmount.value, selectedAsset.value.decimals));
+  const amount = BigInt(toBase(sendAmount.value, selectedAsset.value.decimals));
   const tokenBalance = BigInt(selectedAsset.value.balance || '0');
-  const masBalance = BigInt(toBase(accountBalance.value, 9));
-  const feeRaw = BigInt(toBase(fee.value, 9));
+  if (!isFeeValid.value) return false;
+  const masBalance = BigInt(toBase(accountBalance.value, 9));
+  const feeRaw = BigInt(toBase(fee.value, 9));
@@
   if (selectedAsset.value && !hasValidDecimals.value) {
     return `Too many decimals.`;
   }
+  if (!isFeeValid.value) {
+    return `Fee is invalid or below network minimum (${minimalFee.value} MAS).`;
+  }
   return '';
@@
   if (amountBN.lte(0)) {
     return false;
   }
-
-  return hasEnoughBalance.value;
+  if (!isFeeValid.value) {
+    return false;
+  }
+  return hasEnoughBalance.value;

Also applies to: 244-264, 284-308, 310-351


549-550: Fix typo: use token.value, not valuef

valuef doesn’t exist; breaks USD pricing on verify.

-        price: selectedAsset.value.valuef || '0',
+        price: selectedAsset.value.value || '0',
🧹 Nitpick comments (4)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (4)

486-517: Handle invalid fee in setMaxValue to avoid toBase throwing

If fee is invalid/below min, set max to 0 or skip subtract; otherwise toBase(fee, 9) can throw.

-  const feeBase = toBase(fee.value, 9); // Fee is always in MAS
+  const feeBase = isFeeValid?.value ? toBase(fee.value, 9) : '0';

45-46: Optional: null-safe template ref call

Protect against rare timing issues with the template ref.

-        @update:paste-from-clipboard="addressInputTo.pasteFromClipboard()"
+        @update:paste-from-clipboard="addressInputTo?.pasteFromClipboard?.()"

131-131: Consider de-coupling SendAlert from Solana path

Importing from a Solana provider path in Massa UI is brittle; move/alias to a common location if available.


208-211: Type the assets list

Use a typed array to avoid any[] and align with AssetsSelectList expectations.

-const accountAssets = ref<any[]>([]);
+const accountAssets = ref<(AssetsType & { price?: string })[]>([]);
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 776c10b and ac3c8f0.

📒 Files selected for processing (1)
  • packages/extension/src/providers/massa/ui/send-transaction/index.vue (1 hunks)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test
🔇 Additional comments (2)
packages/extension/src/providers/massa/ui/send-transaction/index.vue (2)

555-559: LGTM: correct native currency symbol

Using network.value.currencyName here resolves the earlier nativeSymbol issue.


244-255: Confirm unit of activeBalances
The hasEnoughBalance check uses toBase(accountBalance.value, 9), which assumes accountBalance (from props.accountInfo.activeBalances) is a human-readable MAS decimal. Verify that activeBalances indeed supplies decimal MAS strings; if it already returns base-unit values, drop the extra toBase conversion.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 17

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (5)
Dockerfile (1)

1-7: Harden and slim image; ensure Yarn works under Node 22.

  • Combine apt steps, use --no-install-recommends, and clean apt lists to cut image size.
  • Enable Corepack before yarn -v to avoid failures if Yarn isn’t activated.
  • Optional: install python3 for native module builds commonly required in Node toolchains.
-FROM node:22.18-bookworm
-RUN apt-get update
-RUN apt-get install build-essential zip -y
+FROM node:22.18-bookworm
+RUN set -eux; \
+  apt-get update; \
+  DEBIAN_FRONTEND=noninteractive apt-get install -y --no-install-recommends \
+    build-essential zip python3 ca-certificates git \
+  ; \
+  rm -rf /var/lib/apt/lists/*
 ENV HOME /home
 ENV NODE_OPTIONS --max-old-space-size=8192
-RUN node -v && npm -v && yarn -v
+RUN corepack enable && node -v && npm -v && yarn -v
 WORKDIR /home
packages/storage/package.json (1)

30-45: Avoid duplicate TypeScript-ESLint installs; keep the meta package only.
Installing both typescript-eslint and the individual @typescript-eslint/* packages is redundant and can cause version skew.

   "devDependencies": {
-    "@types/node": "^22.18.1",
-    "@typescript-eslint/eslint-plugin": "^8.43.0",
-    "@typescript-eslint/parser": "^8.43.0",
+    "@types/node": "^22.18.1",
     "eslint": "^9.35.0",
     "eslint-config-airbnb-base": "^15.0.0",
     "eslint-config-prettier": "^10.1.8",
     "eslint-import-resolver-alias": "^1.1.2",
     "eslint-plugin-import": "^2.32.0",
     "eslint-plugin-module-resolver": "^1.5.0",
     "prettier": "^3.6.2",
     "ts-node": "^10.9.2",
     "tsconfig-paths": "^4.2.0",
     "tsup": "^8.5.0",
     "typescript": "^5.9.2",
     "typescript-eslint": "8.43.0",
     "vitest": "^3.2.4"
   },
packages/signers/polkadot/src/index.ts (2)

115-123: Assertions never validate signatures (async verify is not awaited)

this.verify(...) returns a Promise, so assert(...) always sees a truthy value and never actually checks validity. Use signatureVerify synchronously.

Apply this diff in all three cases:

-        assert(
-          this.verify(
-            bufferToHex(msgHashBuffer),
-            bufferToHex(sig),
-            bufferToHex(pair.publicKey),
-          ),
-          Errors.SigningErrors.UnableToVerify,
-        );
+        assert(
+          signatureVerify(
+            msgHashBuffer,
+            sig,
+            pair.publicKey,
+          ).isValid,
+          Errors.SigningErrors.UnableToVerify,
+        );

Also applies to: 126-134, 137-145


49-55: Remove invalid fifth argument from mnemonicToMiniSecret
In packages/signers/polkadot/src/index.ts (around line 49), mnemonicToMiniSecret only accepts four parameters (mnemonic, password?, wordlist?, onlyJs?). Passing 2048 causes TS errors—revert to the 4-arg call.

packages/name-resolution/package.json (1)

21-23: Engines mismatch: bump Node to ≥18.18 to align with ESLint 9 and TS toolchain.

ESLint 9 requires Node 18.18+; keeping "engines.node": ">=14.15.0" will break local linting/CI for this package. typescript-eslint v8 explicitly targets ESLint 9, which you’ve added. Recommend raising the engine floor here (and at the repo root if enforced). (eslint.org, typescripteslint.com)

Apply:

 "engines": {
-  "node": ">=14.15.0"
+  "node": ">=18.18.0"
 }

Also applies to: 25-28, 38-41

♻️ Duplicate comments (1)
packages/extension/configs/vitest.config.mts (1)

20-28: Make resolver cross-platform and robust (use fileURLToPath + try/catch).

Regex‑stripping "file://" is brittle (breaks on Windows, UNC paths, and encoded chars). Convert file URLs properly and fall back to default resolution on errors. This mirrors a prior review—resurfacing because the issue persists.

Apply within this hunk:

       {
         find: /^(vite-plugin-node-polyfills\/shims\/.+)/,
         replacement: '$1',
-        customResolver(source) {
-          return import.meta.resolve(source).replace(/^file:\/\//, '');
-        },
+        customResolver(source: string): string | undefined {
+          try {
+            const resolved = import.meta.resolve(source);
+            if (resolved.startsWith('file://')) {
+              return fileURLToPath(new URL(resolved));
+            }
+            // Defer to Vite when it's not a file URL
+            return undefined;
+          } catch {
+            // Defer to normal alias replacement / Vite resolution
+            return undefined;
+          }
+        },
       },

Also add this import at the top of the file:

import { fileURLToPath } from 'node:url';
🧹 Nitpick comments (21)
packages/signers/polkadot/package.json (1)

47-48: Unify typescript-eslint versioning to avoid drift.

  • parser and eslint-plugin use caret but typescript-eslint is pinned. Prefer consistent spec to keep the trio in lockstep.

Option A (caret everywhere):

-    "typescript-eslint": "8.43.0",
+    "typescript-eslint": "^8.43.0",

Option B (pin all three to exact versions) for stricter reproducibility:

-    "@typescript-eslint/eslint-plugin": "^8.43.0",
-    "@typescript-eslint/parser": "^8.43.0",
+    "@typescript-eslint/eslint-plugin": "8.43.0",
+    "@typescript-eslint/parser": "8.43.0",
.github/workflows/test-all.yml (1)

10-16: Improve Yarn availability and cache hit rate.

  • Add Corepack to guarantee yarn under Node 22.
  • Cache all workspace locks for better cache hits.
       - uses: actions/setup-node@v4
         with:
           node-version: "22.18.0"
           cache: "yarn"
+          cache-dependency-path: |
+            yarn.lock
+            **/yarn.lock
+      - run: corepack enable
       - run: yarn install
Dockerfile (2)

4-5: Double-check 8 GB heap cap is intended for CI/build.
On smaller runners this can backfire; consider making it configurable via build arg.

-ENV NODE_OPTIONS --max-old-space-size=8192
+ARG NODE_MAX_OLD_SPACE=8192
+ENV NODE_OPTIONS="--max-old-space-size=${NODE_MAX_OLD_SPACE}"

1-7: Optional: run as non-root for safer builds.
Create a user and switch to it unless root is required later.

 RUN corepack enable && node -v && npm -v && yarn -v
-WORKDIR /home
+RUN useradd -m -d /home nodeuser
+USER nodeuser
+WORKDIR /home
packages/storage/package.json (2)

21-23: Update engines.node to match repo toolchain.
Repo CI/Docker use Node 22.18.x; raise the floor to reduce surprises.

   "engines": {
-    "node": ">=14.15.0"
+    "node": ">=20.0.0"
   },

16-20: Add a type-check script for CI clarity.
Separate type-check from build for faster feedback.

   "scripts": {
     "build": "tsup src/index.ts --format esm,cjs --dts --clean",
     "lint": "prettier --write .",
-    "test": "vitest run"
+    "test": "vitest run",
+    "type-check": "tsc -p tsconfig.json --noEmit"
   },
packages/signers/ethereum/package.json (2)

36-37: Avoid duplicating typescript-eslint stacks. Pick meta or plugin+parser.

You have both @typescript-eslint/{parser,eslint-plugin} and the meta package “typescript-eslint”. Use one approach to reduce install time and peer-dep churn.

Option to keep meta only (remove plugin+parser here):

-    "@typescript-eslint/eslint-plugin": "^8.43.0",
-    "@typescript-eslint/parser": "^8.43.0",

Refs: v8 supports ESLint 9 and documents recommended setups. (tseslint.com, typescript-eslint.io)


48-49: If keeping plugin+parser, drop the meta package.

This avoids redundant deps while remaining ESLint 9 compatible.

     "typescript": "^5.9.2",
-    "typescript-eslint": "8.43.0",
+    // (optional) keep only @typescript-eslint/{parser,eslint-plugin} or switch to meta package; don't use both

Refs: Supported ranges for ESLint/Node/TS. (tseslint.com)

packages/hw-wallets/package.json (1)

25-25: @types/node v24 with Node 14 engines is inconsistent.

Node 14 is EOL and far below the API surface modeled by @types/node 24.x. Once engines.node is raised (see above), this mismatch is resolved. Keep @types/node aligned with the Node version you run in CI/dev.

packages/name-resolution/package.json (2)

25-28: Add an ESLint script (you only run Prettier today).

You’ve added ESLint deps but the script runs Prettier only. Add an eslint script and consider separating format vs. lint.

Outside this hunk, update scripts:

 "scripts": {
-  "build": "tsup src/index.ts --format esm,cjs --dts",
-  "lint": "prettier --write .",
+  "build": "tsup src/index.ts --format esm,cjs --dts",
+  "lint": "eslint .",
+  "format": "prettier --write .",
   "test": "vitest run"
 },

51-52: Dependency bumps: request quick smoke tests against ENS/SNS flows.

@bonfida/spl-name-service 3.0.16 and @ensdomains/address-encoder ^1.1.4 look fine, but please rerun ENS/Solana name encode/decode tests to catch subtle codec changes. If consumers are sensitive, consider pinning exacts until validated across the monorepo.

packages/signers/bitcoin/package.json (1)

48-49: Version pinning inconsistency and TS/Node types alignment.

  • Parser/plugin use caret (^8.43.0) while "typescript-eslint" meta package is pinned to 8.43.0. Align to caret for consistent patch/minor updates, or pin all three—pick one strategy.
  • @types/node is at ^24.x while engines will be ≥18.18 after the change; consider matching your supported runtime (e.g., ^20 or ^22) to avoid accidentally using APIs not present in Node 18.

Apply this minimal diff for consistency:

-    "typescript-eslint": "8.43.0",
+    "typescript-eslint": "^8.43.0",
packages/name-resolution/src/index.ts (3)

31-46: Harden reverse resolution against single-resolver failures

One resolver rejecting will reject the whole call. Use allSettled to ignore failures and return the first fulfilled non-null.

-    return this.initDone.then(() =>
-      Promise.all([
-        this.ens.resolveReverseName(address),
-        // this.sid.resolveReverseName(address),
-        this.rns.resolveReverseName(address),
-        this.ud.resolveReverseName(address),
-      ]).then((results) => {
-        // eslint-disable-next-line no-restricted-syntax
-        for (const name of results) {
-          if (name !== null) return name;
-        }
-        return null;
-      }),
-    );
+    return this.initDone.then(() =>
+      Promise.allSettled([
+        this.ens.resolveReverseName(address),
+        this.rns.resolveReverseName(address),
+        this.ud.resolveReverseName(address),
+      ]).then((results) => {
+        for (const r of results) {
+          if (r.status === "fulfilled" && r.value !== null) return r.value;
+        }
+        return null;
+      }),
+    );

48-53: Mark _paymentIdChain as deprecated/ignored

The param remains public but unused. Add a brief JSDoc to avoid confusion.

   public async resolveAddress(
+    /**
+     * @deprecated Ignored while SID resolution is disabled.
+     */
     name: string,
     coin: CoinType = "ETH",
     _paymentIdChain?: string,
   ): Promise<string | null> {

35-35: Delete commented-out SID calls

They’re noise now; removing avoids drift.

-        // this.sid.resolveReverseName(address),
@@
-      // if (this.sid.isSupportedName(name))
-      //   return this.sid.resolveAddress(name, paymentIdChain);

Also applies to: 58-59

packages/name-resolution/tests/resolver.test.ts (2)

23-25: Remove stale commented assertion

Keep the test concise; the new expectation is null.

-    // expect(address).to.be.eq("0xb5932a6B7d50A966AEC6C74C97385412Fb497540");
     expect(address).to.be.eq(null);

11-17: Drop unused SID config in tests

SID is disabled; this config is unused and can mislead.

       ens: {
         node: "https://nodes.mewapi.io/rpc/eth",
       },
-      sid: {
-        node: {
-          bnb: "https://nodes.mewapi.io/rpc/bsc",
-          arb: "https://nodes.mewapi.io/rpc/arb",
-        },
-      },
       ens: {
         node: "https://nodes.mewapi.io/rpc/eth",
       },
-      sid: {
-        node: {
-          bnb: "https://nodes.mewapi.io/rpc/bsc",
-          arb: "https://nodes.mewapi.io/rpc/arb",
-        },
-      },

Also applies to: 32-38

packages/extension/src/providers/ethereum/networks/zksepolia.ts (2)

6-19: Rename vars to zksepolia for clarity

Names still say goerli. Keeps code grep-friendly and avoids confusion.

-const zkgoerliOptions: EvmNetworkOptions = {
+const zksepoliaOptions: EvmNetworkOptions = {

21-23: Follow-through rename on instance and export

-const zkgoerli = new EvmNetwork(zkgoerliOptions);
-
-export default zkgoerli;
+const zksepolia = new EvmNetwork(zksepoliaOptions);
+export default zksepolia;
packages/utils/package.json (1)

27-27: Align @polkadot/util-crypto versions across the monorepo – update packages/signers/massa/package.json (line 35) from ^13.5.1 to ^13.5.6 to match the other packages.

packages/extension/src/providers/ethereum/networks/index.ts (1)

144-146: Export key naming: prefer cotiTestnet (without Node) for consistency

Most keys are network names without the Node suffix. Consider aligning this export to avoid surprise for consumers.

-  cotiTestnetNode: cotiTestnetNode,
+  cotiTestnet: cotiTestnetNode,
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between ac3c8f0 and 901ece0.

⛔ Files ignored due to path filters (1)
  • yarn.lock is excluded by !**/yarn.lock, !**/*.lock
📒 Files selected for processing (43)
  • .github/workflows/test-all.yml (1 hunks)
  • .github/workflows/test-swap.yml (1 hunks)
  • .nvmrc (1 hunks)
  • Dockerfile (1 hunks)
  • package.json (1 hunks)
  • packages/extension-bridge/package.json (2 hunks)
  • packages/extension/configs/vitest.config.mts (1 hunks)
  • packages/extension/package.json (6 hunks)
  • packages/extension/src/providers/common/libs/new-features.ts (1 hunks)
  • packages/extension/src/providers/ethereum/libs/activity-handlers/providers/etherscan/configs.ts (1 hunks)
  • packages/extension/src/providers/ethereum/libs/assets-handlers/assetinfo-mew.ts (1 hunks)
  • packages/extension/src/providers/ethereum/networks/cagaAnkara.ts (0 hunks)
  • packages/extension/src/providers/ethereum/networks/coti-devnet.ts (0 hunks)
  • packages/extension/src/providers/ethereum/networks/coti-testnet.ts (1 hunks)
  • packages/extension/src/providers/ethereum/networks/form-testnet.ts (0 hunks)
  • packages/extension/src/providers/ethereum/networks/form.ts (0 hunks)
  • packages/extension/src/providers/ethereum/networks/index.ts (6 hunks)
  • packages/extension/src/providers/ethereum/networks/skale/chaos.ts (0 hunks)
  • packages/extension/src/providers/ethereum/networks/skale/index.ts (0 hunks)
  • packages/extension/src/providers/ethereum/networks/tac.ts (1 hunks)
  • packages/extension/src/providers/ethereum/networks/zkgoerli.ts (0 hunks)
  • packages/extension/src/providers/ethereum/networks/zksepolia.ts (1 hunks)
  • packages/extension/src/providers/polkadot/networks/index.ts (0 hunks)
  • packages/extension/src/providers/polkadot/networks/unique/opal.ts (0 hunks)
  • packages/hw-wallets/package.json (3 hunks)
  • packages/keyring/package.json (2 hunks)
  • packages/name-resolution/package.json (3 hunks)
  • packages/name-resolution/src/index.ts (2 hunks)
  • packages/name-resolution/tests/resolver.test.ts (1 hunks)
  • packages/name-resolution/tests/sid.test.ts (1 hunks)
  • packages/request/package.json (2 hunks)
  • packages/signers/bitcoin/package.json (2 hunks)
  • packages/signers/ethereum/package.json (2 hunks)
  • packages/signers/kadena/package.json (2 hunks)
  • packages/signers/polkadot/package.json (2 hunks)
  • packages/signers/polkadot/src/index.ts (1 hunks)
  • packages/storage/package.json (2 hunks)
  • packages/swap/package.json (2 hunks)
  • packages/swap/src/common/estimateGasList.ts (0 hunks)
  • packages/swap/src/index.ts (1 hunks)
  • packages/types/package.json (2 hunks)
  • packages/types/src/networks.ts (4 hunks)
  • packages/utils/package.json (2 hunks)
💤 Files with no reviewable changes (10)
  • packages/extension/src/providers/ethereum/networks/coti-devnet.ts
  • packages/extension/src/providers/polkadot/networks/unique/opal.ts
  • packages/swap/src/common/estimateGasList.ts
  • packages/extension/src/providers/ethereum/networks/cagaAnkara.ts
  • packages/extension/src/providers/ethereum/networks/form.ts
  • packages/extension/src/providers/polkadot/networks/index.ts
  • packages/extension/src/providers/ethereum/networks/skale/chaos.ts
  • packages/extension/src/providers/ethereum/networks/form-testnet.ts
  • packages/extension/src/providers/ethereum/networks/zkgoerli.ts
  • packages/extension/src/providers/ethereum/networks/skale/index.ts
✅ Files skipped from review due to trivial changes (3)
  • packages/name-resolution/tests/sid.test.ts
  • .github/workflows/test-swap.yml
  • .nvmrc
🚧 Files skipped from review as they are similar to previous changes (2)
  • package.json
  • packages/keyring/package.json
🧰 Additional context used
🧬 Code graph analysis (3)
packages/extension/src/providers/ethereum/networks/coti-testnet.ts (1)
packages/extension/src/providers/ethereum/types/evm-network.ts (2)
  • EvmNetworkOptions (22-53)
  • EvmNetwork (55-286)
packages/extension/src/providers/ethereum/networks/zksepolia.ts (1)
packages/extension/src/providers/ethereum/types/evm-network.ts (2)
  • EvmNetworkOptions (22-53)
  • EvmNetwork (55-286)
packages/extension/src/providers/ethereum/networks/tac.ts (2)
packages/extension/src/providers/ethereum/types/evm-network.ts (2)
  • EvmNetworkOptions (22-53)
  • EvmNetwork (55-286)
packages/extension/src/providers/ethereum/libs/activity-handlers/index.ts (1)
  • EtherscanActivity (10-10)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: buildAll
  • GitHub Check: test
  • GitHub Check: test
🔇 Additional comments (18)
packages/swap/package.json (2)

27-28: Solana libs: patch bumps look good

Patch updates for @solana/spl-token and @solana/web3.js are low risk and align with the broader dependency refresh. No further action from me here.


34-34: rango-sdk-basic bump: verify no breaking metadata or enum changes
Imports in packages/swap/src/providers/rango/index.ts. Confirm v0.1.71 didn’t alter RangoTransactionType or RoutingResultType values or supportedNetworkByRangoBlockchain mappings. Sanity-check swap flows on EVM and Solana and run existing Rango provider tests.

.github/workflows/test-all.yml (1)

12-12: Include hidden files in ripgrep search
Your rg invocation skipped the .github folder by default; rerun with -u (or --hidden) so all workflows are checked, e.g.:

rg -u -nP '(node-version|setup-node)' -g '.github/workflows/**/*.yml'
packages/hw-wallets/package.json (2)

28-29: Verify ESLint v9 compatibility with Airbnb base config
Ensure eslint-config-airbnb-base@^15.0.0’s peerDependencies support ESLint 9 and that your .eslintrc* in packages/hw-wallets (and similar packages) correctly extends it via the compatibility layer or flat config per the ESLint 9 migration guide.


55-60: Patch bumps verified; no unmet peers or duplicate transports detected. Manual testing of WebUSB flows in Chromium-based browsers is still required.

packages/extension/configs/vitest.config.mts (1)

18-19: Test globs look good.

Patterns cover src and tests folders for .test/.spec TS files; no concerns.

packages/name-resolution/package.json (1)

25-28: Verify ESLint 9 compatibility with current plugins/config

  • Current stack in packages/name-resolution:
    • ESLint ^9.35.0
    • eslint-config-airbnb-base ^15.0.0
    • eslint-plugin-import ^2.32.0
    • eslint-plugin-module-resolver ^1.5.0
  • Ensure each package’s peerDependencies permit eslint@^9 (e.g. npm view eslint-plugin-import@2.32.0 peerDependencies); upgrade or replace any that don’t.
  • Legacy .eslintrc.json remains supported in ESLint 9; migrating to Flat Config is optional.
packages/name-resolution/src/index.ts (1)

5-5: Remove SIDResolver import and wiring in NameResolver

In packages/name-resolution/src/index.ts:

  • Delete import SIDResolver from "./sid";
  • Remove the sid: SIDResolver; class property
  • Drop this.sid = new SIDResolver(options.sid); from the constructor
  • Remove the commented // this.sid.init(), line in the initDone array
packages/extension-bridge/package.json (1)

47-65: [Waiting for script results]

packages/signers/kadena/package.json (1)

31-37: Dev deps bump LGTM

No runtime/API surface changes; safe to merge.

Also applies to: 46-48

packages/types/package.json (1)

27-43: No action needed: @massalabs/massa-web3 is only in devDependencies
Verified no imports of @massalabs/massa-web3 in the published packages/types/src surface—keeping it as a devDependency is safe.

packages/extension/src/providers/ethereum/networks/zksepolia.ts (1)

12-17: Resolve: Chain ID and WebSocket endpoint are correct
Chain ID 0x12c (300) and wss://sepolia.era.zksync.dev/ws match the official zkSync Era Sepolia documentation.

packages/request/package.json (1)

34-49: Tooling bumps LGTM

No functional/runtime impact here.

packages/types/src/networks.ts (1)

182-183: CoinGecko slug “massa” is valid
Confirmed that CoinGecko recognizes the smart-contract platform with API id “massa”, so no changes are needed.

packages/extension/src/providers/ethereum/libs/activity-handlers/providers/etherscan/configs.ts (1)

71-71: No changes needed for TAC explorer URL
TAC’s explorer is a custom Blockscout instance exposing the standard /api endpoints, so activity fetching with EtherscanActivity will work as is.

packages/extension/package.json (1)

26-68: Verify major-version upgrades (Vite 7, ECharts 6, Vue 3.5, TS 5.9)

  • CRX plugin (packages/extension/vite.config.ts:81) – confirm vite-plugin-crx options remain compatible under Vite 7.
  • ECharts imports – code scan didn’t find direct import 'echarts' or renderer usage; ensure vue-echarts@7.0.3 integration still works with echarts@6.
  • Vite config APIs – optimizeDeps, build.rollupOptions, and plugins remain valid in Vite 7 (config at lines 95–117).
  • TypeScript setup – verify tsconfig and any plugins handle TS 5.9 without regressions.
packages/extension/src/providers/common/libs/new-features.ts (1)

3-3: LGTM: TAC flagged as new

This matches the TAC additions elsewhere.

packages/extension/src/providers/ethereum/networks/tac.ts (1)

11-19: TAC network configuration verified

  • chainID 0xEF (239) matches the official EVM chain ID
  • RPC: primary https://rpc.tac.build (official) with fallback https://rpc.ankr.com/tac
  • Explorer endpoints /tx/[[txHash]] and /address/[[address]] align with the Blockscout instance (API docs at /explorer.tac.build/api_docs)
  • CoinGecko ID tac exists for the main currency

Comment on lines 145 to 149
[NetworkNames.Sanko]: {
tbName: 'sanko',
tbName: '',
cgPlatform: CoingeckoPlatform.Sanko,
bsEndpoint: true,
},
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Verification agent

🧩 Analysis chain

Sanko → Blockscout: drop unused tbName and confirm Blockscout mapping exists

Switching to bsEndpoint: true is good. Since MEW tbName is no longer used, remove the empty tbName to avoid accidental future use.

   [NetworkNames.Sanko]: {
-    tbName: '',
     cgPlatform: CoingeckoPlatform.Sanko,
     bsEndpoint: true,
   },

Run to confirm Sanko is supported in the Blockscout handler:


🏁 Script executed:

#!/bin/bash
set -euo pipefail
FILE=$(fd -a 'blockscout.ts' packages/extension/src/providers/ethereum | head -n1)
echo "Blockscout file: $FILE"
rg -nC2 -e 'Sanko|sanko' "$FILE" || { echo "No Sanko mapping found in $FILE"; exit 1; }

Length of output: 234


Add missing Blockscout mapping for Sanko and remove unused tbName

  • In packages/extension/src/providers/ethereum/libs/assets-handlers/assetinfo-mew.ts, drop the empty tbName: '' under the NetworkNames.Sanko entry.
  • In packages/extension/src/providers/ethereum/libs/assets-handlers/blockscout.ts, add a NetworkNames.Sanko mapping so that bsEndpoint: true resolves correctly (e.g. map to the appropriate “sanko” identifier).
🤖 Prompt for AI Agents
In
packages/extension/src/providers/ethereum/libs/assets-handlers/assetinfo-mew.ts
around lines 145-149, remove the unused empty property tbName: '' from the
NetworkNames.Sanko entry so the object only contains cgPlatform and bsEndpoint;
then in
packages/extension/src/providers/ethereum/libs/assets-handlers/blockscout.ts add
a mapping for NetworkNames.Sanko pointing to the correct Blockscout identifier
(e.g. "sanko" or the project's expected string) so bsEndpoint: true can resolve
correctly — update the exported mapping object, ensure imports/constants align,
and run type checks.

Comment on lines 17 to 18
import zkSepoliaNode from './zksepolia';
import vicNode from './vic';
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Verification agent

🧩 Analysis chain

Renames/removals: verify downstream references

You renamed zkGoerlizkSepolia and replaced COTI devnet with testnet. Ensure no remaining imports/usages expect the old keys or removed networks.

Also applies to: 98-99


🏁 Script executed:

#!/bin/bash
# Find stale references to renamed/removed networks
rg -nP -C2 '\b(zkGoerli|cotiDevnet|skaleChaos|formTestnet|form|cagaAnkara)\b' -- \
  packages apps configs src || true

Length of output: 6587


Rename remaining cotiDevnet references – packages/extension/src/providers/ethereum/networks/coti.ts lines 23–25 still define/export cotiDevnet; update the identifier and export to cotiTestnet to reflect the COTI testnet replacement. No stale zkGoerli references found.

🤖 Prompt for AI Agents
In packages/extension/src/providers/ethereum/networks/coti.ts around lines 23 to
25, the exported identifier is still named cotiDevnet; rename the identifier and
its export to cotiTestnet (and update any internal variable names) so the module
reflects the COTI testnet replacement, then update any imports/exports that
reference cotiDevnet (including
packages/extension/src/providers/ethereum/networks/index.ts) to use cotiTestnet.

Comment on lines 42 to 45
"@types/node": "^22.18.1",
"@typescript-eslint/eslint-plugin": "^8.43.0",
"@typescript-eslint/parser": "^8.43.0",
"eslint": "^9.35.0",
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Verification agent

🧩 Analysis chain

Tooling bumped to ESLint 9 / @typescript-eslint 8 / TS 5.9 — engines.node is now too low

ESLint 9 and @typescript-eslint v8 require Node ≥18 (typically ≥18.18). tsup 8 also targets modern Node. Current engines.node (>=14.15.0) is misleading and will fail local/CI installs using engines-strict.

Update engines.node here (and align at repo root if needed):

-  "engines": {
-    "node": ">=14.15.0"
-  },
+  "engines": {
+    "node": ">=18.18.0"
+  },

Quick audit across the monorepo:

Also applies to: 55-56


🏁 Script executed:

#!/bin/bash
# List all declared Node engine constraints to spot inconsistencies
fd -H --full-path 'package.json' | while read -r f; do
  nodeVal=$(jq -r '.engines.node // empty' "$f" 2>/dev/null)
  if [ -n "$nodeVal" ]; then
    echo "$f -> engines.node: $nodeVal"
  fi
done

Length of output: 783


Bump engines.node to ≥18.18.0 across all package.json files
ESLint v9.x drops support for Node.js < 18.18.0 (requires ≥ 18.18.0) (eslint.org) and tsup v8 targets Node.js ≥ 18 (app.unpkg.com); every package currently declares >=14.15.0—update them (and the root) to >=18.18.0.

🤖 Prompt for AI Agents
In packages/swap/package.json around lines 42-45, the package.json currently
declares Node engine ">=14.15.0" while newer tool versions require Node
>=18.18.0; update the "engines.node" entry in this file to ">=18.18.0" (and
mirror the same change across all other package.json files including the
repository root) so ESLint/tsup and related tooling run on the supported Node
version; no other changes required beyond updating the engine specification and
committing the modified package.json files.

@kvhnuke kvhnuke changed the base branch from develop to devop/package-upgrades-2-11 September 11, 2025 17:07
@kvhnuke kvhnuke merged commit 7950524 into devop/package-upgrades-2-11 Sep 11, 2025
5 checks passed
@kvhnuke kvhnuke deleted the feat/massalabs-extension branch September 11, 2025 17:23
This was referenced Sep 11, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants