Mnemonic.fromSentence constructor

Mnemonic.fromSentence(
  1. String sentence,
  2. Language language, {
  3. String passphrase = "",
})

Constructs Mnemonic from a sentence by retrieving the original entropy.

Implementation

Mnemonic.fromSentence(String sentence, this.language,
    {this.passphrase = ""}) {
  List<String> words = sentence.split(language.separator);
  List<int> indexes = [];
  Map<int, String> map = language.map;
  // convert to indexes.
  for (var word in words) {
    var nfkdWord = nfkd(word);
    if (map.containsValue(nfkdWord) == false) {
      throw Exception('mnemonic: "$word" does not exist in $language');
    } else {
      int index =
          map.entries.firstWhere((entry) => entry.value == nfkdWord).key;
      indexes.add(index);
    }
  }
  // determine checksum length in bits.
  int checksumLength;
  switch (indexes.length) {
    case 12:
      checksumLength = 4;
      break;
    case 15:
      checksumLength = 5;
      break;
    case 18:
      checksumLength = 6;
      break;
    case 21:
      checksumLength = 7;
      break;
    case 24:
      checksumLength = 8;
      break;
    default:
      throw Exception("mnemonic: unexpected sentence length");
  }
  // convert indexes to bits to remove the checksum.
  String bits = indexes
      .map((byte) => byte
          .toRadixString(2)
          .padLeft(11, '0')) // (each index is encoded on 11 bits)
      .join('');
  // remove checksum from bits.
  var bitsEntropy = bits.substring(0, bits.length - checksumLength);
  var extractedChecksum = bits.substring(bits.length - checksumLength);
  // converts bits entropy back to bytes.
  entropy = [];
  for (var i = 0; i < bitsEntropy.length; i += 8) {
    String bit = bitsEntropy.substring(i, i + 8);
    entropy.add(int.parse(bit, radix: 2));
  }
  if (_checksum != extractedChecksum) {
    throw Exception('mnemonic: invalid checksum');
  }
}