fix(crypto): use 27 base-30 chars for Secret Key to prevent data loss

The Secret Key encoder used 26 base-30 characters which can only
represent 30^26 ≈ 2^127.58 values. Since the key is 128 bits,
~25% of generated keys silently lost their high bits during
formatting, making the Emergency Kit key unable to reconstruct
the original bytes on a new browser.

Changed KEY_CHAR_LENGTH from 26 to 27 (30^27 > 2^128). Parser
accepts both old 26-char and new 27-char keys for backward
compatibility. Format: A3-XXXXXX-XXXXXX-XXXXXX-XXXXXX-XXX

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Jason Staack
2026-03-10 14:04:24 -05:00
parent b954e0aa2a
commit d0548bec86
2 changed files with 11 additions and 9 deletions

View File

@@ -103,7 +103,7 @@ export function SecretKeyInput({ value, onChange, error }: SecretKeyInputProps)
[groups],
)
// 26-char key = 4 groups of 6 + 1 group of 2
// 27-char key = 4 groups of 6 + 1 group of 3 (old keys: 26 chars, last group = 2)
const isComplete =
groups.slice(0, 4).every((g) => g.length === 6) && groups[4].length >= 2
const hasContent = groups.some((g) => g.length > 0)
@@ -151,7 +151,7 @@ export function SecretKeyInput({ value, onChange, error }: SecretKeyInputProps)
</div>
{error && hasContent && !isComplete && (
<p className="text-xs text-error">
Enter all 30 characters of your Secret Key
Enter all characters of your Secret Key
</p>
)}
</div>