FuelLabs/fuels-ts · error · FuelError

INVALID_MNEMONIC

INVALID_MNEMONIC

Error message

Invalid mnemonic: the word '${words[i]}' is not found in the provided wordlist.

What it means

Thrown by mnemonicWordsToEntropy when a word in the mnemonic phrase cannot be found in the provided wordlist. The function maps each word to an 11-bit index via wordlist.indexOf; a return of -1 means the word is not part of the (default English) BIP-39 wordlist. NFKD normalization is applied before lookup, so visually similar words still must match a canonical entry.

Source

Thrown at packages/account/src/mnemonic/utils.ts:74

  const checksumBits = entropy.length / 4;
  const checksum = arrayify(sha256(entropy))[0] & getUpperMask(checksumBits);

  // Shift the checksum into the word indices
  indices[indices.length - 1] <<= checksumBits;
  indices[indices.length - 1] |= checksum >> (8 - checksumBits);

  return indices;
}

export function mnemonicWordsToEntropy(words: Array<string>, wordlist: Array<string>): BytesLike {
  const size = Math.ceil((11 * words.length) / 8);
  const entropy = arrayify(new Uint8Array(size));

  let offset = 0;
  for (let i = 0; i < words.length; i += 1) {
    const index = wordlist.indexOf(words[i].normalize('NFKD'));
    if (index === -1) {
      throw new FuelError(
        ErrorCode.INVALID_MNEMONIC,
        `Invalid mnemonic: the word '${words[i]}' is not found in the provided wordlist.`
      );
    }

    for (let bit = 0; bit < 11; bit += 1) {
      if (index & (1 << (10 - bit))) {
        entropy[offset >> 3] |= 1 << (7 - (offset % 8));
      }
      offset += 1;
    }
  }
  const entropyBits = (32 * words.length) / 3;
  const checksumBits = words.length / 3;
  const checksumMask = getUpperMask(checksumBits);
  const checksum = arrayify(sha256(entropy.slice(0, entropyBits / 8)))[0] & checksumMask;

  if (checksum !== (entropy[entropy.length - 1] & checksumMask)) {

View on GitHub (pinned to b3f37c91ac)

Solutions

  1. Inspect the exact word reported in the error message and correct the typo against the BIP-39 English wordlist.
  2. Strip surrounding punctuation/whitespace from each word before passing: words.map(w => w.trim().replace(/[^a-z]/gi, '')).
  3. If using a non-English phrase, construct Mnemonic with the matching wordlist (e.g. japanese) instead of the default english.
  4. Validate each word with wordlist.includes(word) before calling mnemonicToEntropy to surface the bad word early.

Example fix

// before
const entropy = Mnemonic.mnemonicToEntropy('abandon ability abndon about ...'); // 'abndon' typo

// after
// fix the typo to a valid word
const entropy = Mnemonic.mnemonicToEntropy('abandon ability abandon about ...');

// or pre-validate
const words = phrase.trim().split(/\s+/);
const bad = words.filter(w => !english.includes(w));
if (bad.length) throw new Error(`Unknown words: ${bad.join(', ')}`);
Defensive patterns

Strategy: validation

Validate before calling

import { english } from '@fuel-ts/account/wordlists';
function validateWords(words: string[], wordlist = english) {
  const unknown = words.filter(w => !wordlist.includes(w.normalize('NFKD')));
  if (unknown.length) throw new Error(`Unknown mnemonic words: ${unknown.join(', ')}`);
}

Type guard

function allWordsInList(words: string[], wordlist: string[]): boolean {
  return words.every(w => wordlist.includes(w.normalize('NFKD')));
}

Try / catch

import { FuelError, ErrorCode } from '@fuel-ts/errors';
try {
  const entropy = mnemonicWordsToEntropy(words, wordlist);
} catch (e) {
  if (e instanceof FuelError && e.code === ErrorCode.INVALID_MNEMONIC) {
    // show the offending word from the message to the user for correction
  }
  throw e;
}

Prevention

When it happens

Trigger: Calling mnemonicToEntropy on a phrase containing a typo, a word from a different language wordlist, a non-BIP-39 word, or extra punctuation; passing a custom wordlist that omits a word; mixing wordlists (e.g. Japanese words with the default English list).

Common situations: User mistyped a seed word (e.g. 'aple' instead of 'apple'); phrase was OCR'd or auto-corrected, substituting a real but wrong word; phrase contains words from another BIP-39 language; copy-paste included a trailing comma or period attached to a word.

Related errors


AI-assisted analysis of FuelLabs/fuels-ts@b3f37c91ac (2026-08-12). Data as JSON: /api/errors/17ea14cceafb6e17. Report an issue: GitHub.