Skip to content

Heir addresses are never verified, and a typo only surfaces at claim time #327

Description

@Jolah1

What's wrong

There is no heir equivalent of owner_contact_verified_at. No column, no flow, nothing anywhere in the codebase. heir_contact_ciphertext is sealed at setup and never tested.

So a mistyped heir address is discovered the day the claim link fires. That is the one moment it matters and the one moment the owner is not around to fix it. The whole product does exactly one thing, and this is the way it silently fails to do it.

Mainnet has 16 vaults, all with an email heir channel, none confirmed reachable.

The constraint

We cannot just copy the owner flow. The heir usually should not learn the vault exists until the owner chooses to tell them. A "confirm your address" email is a disclosure.

That constraint only blocks half the problem though. There are two questions and they separate cleanly:

  1. Is this address deliverable? Answerable without the heir doing anything.
  2. Does it belong to the intended person? Needs the heir to act, and therefore needs the owner's consent to disclose.

Proposed design

Tier 1 — syntax and domain check at setup. No email, no disclosure.

Most real typos are gmial.com, gmail.con, yaho.com, a missing TLD. An MX lookup on the domain plus strict address parsing catches nearly all of them at the moment the owner types it, while they can still fix it. Zero heir involvement. This is the cheapest large win and should land first.

Tier 2 — the practice drill is already the verification mechanism.

drill::start_drill is owner-initiated and already emails the heir. With delivery feedback now landing (#322), an email.delivered verdict on that invite proves the mailbox exists. Set heir_contact_verified_at on delivery, not on completion. Nothing new is sent, no new disclosure decision, and the owner already controls when it happens.

This means reframing the drill in the UI from "practice" to "confirm your heir can be reached" so owners actually run it.

Tier 3 — identity. Drill completion already proves the right person holds the address. That part exists.

Also needed

Related

#326 is the owner-side half. Found together while investigating mistyped addresses on the Resend suppression list.

Metadata

Metadata

Assignees

No one assigned

    Labels

    area:serverghostkey-serverbugSomething isn't working

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions