Skip to main content

Accounts and signing

Personal accounts​

Each user's account is a Soroban smart account built from Stellar's open-source Passkey Kit wallet, pinned by its code hash. The user's passkey, a secp256r1 key held on their device, is its signer.

StepWhat happens
Sign upThe user signs in with email or Google, then creates a passkey
Account createdBlockFinaX deploys the user's smart account with the passkey as its signer, and pays the deployment fee
Approving an actionThe passkey signs a Soroban authorization entry for the exact call (WebAuthn, with the user's fingerprint or face)
Backup passkeysAdded as further signers with add_signer, each approved by an existing passkey on chain

BlockFinaX never holds a key that controls a user's account. Losing every passkey means losing access, which is why backup passkeys exist.

Business accounts​

A business account is a separate Soroban smart account running OpenZeppelin stellar-accounts 0.8.0. BlockFinaX deploys it when a member creates the business, with that member's passkey as its first admin, and pays the deployment fee. Each member's passkey sits on the account's context rules for their role (details).

StepWhat happens
CreateThe account is deployed with rule 0 (Default): the creator's passkey and a threshold policy of 1
Add a memberAn admin approves add_signer (or, for the first operator, add_context_rule for each operator rule); BlockFinaX confirms the change by reading the account back
Remove a memberAn admin approves remove_signer (or remove_context_rule for the last operator); the member loses app access when removal starts
Approving an actionThe member's passkey signs the OpenZeppelin auth digest, which binds the account, the call and the context rule ids the member claims

A member uses the same passkey for their personal wallet and a business account. The two sign different digests for different accounts, so an approval for one can never be used on the other.

The app acts for a business by sending X-BFX-Organisation: <id> on API requests. The API checks active membership on every request and swaps in the business account.

Users never need XLM. The app sends the signed authorization to BlockFinaX, which checks it and passes it to OpenZeppelin Relayer Channels. Channels builds the transaction and pays the fee. If Channels can't complete it, a BlockFinaX fee account submits and pays instead.

Relayer policyRule
One callExactly one contract call per transaction
Allowed targetsThe currency pool, the rate pool, USDC transfers and approvals to Circle's TokenMessenger, Circle CCTP, and adding a signer to the user's own account
Own accountCalls that name an account must name the signed-in user's
Bound signatureThe authorization must be for that exact call
Fallback fee capThe BlockFinaX fee account spends at most 50 XLM per call; normal calls cost far less

For a business account the relayer also applies the member's role. The account's context rules enforce the same on chain.

RoleRelayed
AdminPool calls, USDC transfers, Circle CCTP, and changes to the business account's signers, rules and policies. Never upgrade or execute
OperatorPool calls only
ViewerNothing