Device linking and recovery
A passkey account's keystore lives in consensus state: link more devices, require two of them, name recovery signers, and recover a lost account behind a wait any device can cancel.
A device-bound passkey cannot be copied, which is what makes it a safe root. It also means that one passkey cannot survive the loss of its device. On Tenzro Network an account survives device loss by having more than one independent root: another device, or a set of recovery signers. It never does so by making any single root weaker.
The keystore
A passkey account is its devices plus its keystore on the ledger: the passkeys that may act for the account, its policy, its recovery signers and any recovery in progress. The keystore is consensus state, so every node returns the same record, any linked device works through any node, and the account outlives every site, wallet and node that served it.
The account address commits to the first passkey, the account's identity and a salt. It never changes when devices change. Until its first change the keystore is that first passkey alone.
Every change is a KeystoreUpdate transaction:
| Change | Approved by |
|---|---|
| Link a passkey | The account's passkeys, per its policy, plus the new passkey's own assertion (proof of possession) |
| Unlink a passkey | The account's passkeys, per its policy. The last passkey stays. |
| Set the policy | The account's passkeys, per its policy |
| Set the recovery signers | The account's passkeys, per its policy |
| Start a recovery | The recovery signers, by threshold, plus the joining passkey's proof of possession |
| Cancel a recovery | Any one passkey of the account |
| Finish a recovery | Anyone, once its wait has passed |
Each approval signs a digest of the account, the commitment of the keystore being changed and the change itself. The commitment moves with every change, so an approval applies once and cannot be replayed. Any account may send and pay for a keystore change: the authority is in the approvals, never in the sender. A change the account sends itself, signed by one of its passkeys, counts as that passkey's approval.
Independent roots
Any linked passkey acts for the account on its own: it signs transactions, approves payments and keystore changes, and roots agents. What counts for safety is independence. Passkeys held by one sync provider count as one root of control; each device-bound credential counts as its own.
- Spending needs two independent roots. An account with one root can receive funds but cannot send them, so one stolen sync account is never enough to move money.
- A new root waits. A passkey linked while the account holds fewer than two independent roots signs at once, but counts as a root only after 48 hours. During that time any other passkey can unlink it, so one stolen passkey cannot add a "second root" and spend.
tenzro_getKeystore returns the record, its commitment, the number of independent roots and whether the account may spend now.
Link another device
In the console, open Wallet, choose to add a device and follow the prompts:
- On the new device, create a passkey. Its assertion is the proof of possession the change carries.
- On an existing device, approve the change. If that passkey is on your phone, the browser shows a QR code; scan it and approve with your fingerprint, face or PIN.
- The
KeystoreUpdateis sent. Once its block is final, the new passkey acts for the account. The address does not change.
From the command line, read the keystore and send a change that your wallet prepared and approved:
# The keystore as consensus state holds it
tenzro passkey keystore 0xYourAccount
# Which accounts a passkey is linked to (credential id and relying party)
tenzro passkey resolve <CREDENTIAL_ID_HEX> --rp-id tenzro.com
# Send an approved change, paying its fee from this machine's client account
tenzro passkey update ./update.jsonThe update file holds the account, its anchor (only for the first change), the previous commitment, the change and its approvals. The SDKs build it: see Wallet SDK.
Passkeys from any wallet provider
Each passkey in a keystore records its own relying party: the domain of the wallet that registered it. Its assertions must carry that relying party's hash and come from that domain or a subdomain of it, over HTTPS. No list of related origins applies in consensus, so no wallet provider needs another's permission. A passkey registered with any provider joins an account through an ordinary link change approved by a passkey already on it, and from then on acts for the account like any other.
Require two devices
By default any one linked passkey approves a change (single_credential). With two_credentials, every keystore change needs two passkeys, and no single passkey acts alone.
Recovery signers
Recovery signers are keys you name to approve moving your account to a new passkey when you have none left: a recovery key, an email verifier, or a device such as another person's passkey or a machine's TPM or Secure Enclave. You choose the signers and the threshold in one set_recovery change, approved by your passkeys.
Recovery
If you lose every device, or want to replace the one you have, you recover the account onto a new passkey:
- Start. The recovery signers approve a
start_recoverychange that names the new passkey, and the new passkey proves possession of itself. - Wait. The recovery waits 1 hour when a recovery key and an email verifier approved it, 48 hours for a recovery key alone, and 7 days otherwise.
- Cancel. Any passkey still on the account can cancel the recovery during the wait.
- Finish. Once the wait has passed, anyone can send
finish_recovery, and the new passkey joins the keystore. The account address, balance and history are unchanged.
Recovery adds a passkey and removes nothing. An attacker who starts a recovery gains nothing while you still hold any device: you see it pending in the keystore and cancel it.
Email is an alarm, not a key
An email address can be used for account lookup, as the alarm channel for a pending recovery, and as one recovery signer among others. It is never a root on its own:
- email cannot create, replace or recover a signer without the other approvals the keystore requires;
- email cannot raise a spending limit;
- a recovery alert by email only warns you; you cancel the recovery with a device you hold.
Machines
Machine identities are rooted in the machine's own TPM 2.0 or Secure Enclave. The key is derived from the hardware on demand, so reinstalling the software or wiping the data directory does not change the machine's DID. A replacement machine is a new machine with a new DID; its controller links it and moves any delegations across. See Hardware-rooted keys.
Methods
| Method | Access | Purpose |
|---|---|---|
tenzro_getKeystore | open | An account's keystore, its commitment, independent roots and whether it may spend |
tenzro_resolveCredential | open | The accounts a passkey (credential id and relying party) is linked to |
tenzro_enrollPasskey | open | Create an account from its first passkey; returns the account, its keystore and the anchor its first change carries |
tenzro_sendRawTransaction | signed | Send a KeystoreUpdate; the approvals inside it carry the authority |