fix(auth): an account with a password deletes itself only with it and a code
A session alone deleted any account, with everything encrypted under its keys (the second reading's lows; decided by the developer: the password and a code, as a change of password takes). account.delete now takes a DeletionProof (the password's SRP proof for a beginChange challenge, a TOTP or recovery code, the host the device addressed); the register checks it (requireOwnerToDelete), a member passing it on bound to its own host. Accounts without a password, anonymous ones among them, delete with their session as before. In the app, deleting an account with a password asks for it and a code in a sheet of its own; a wrong one deletes nothing. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Signed-off-by: Tizian 「ティツィアーン」 <raisondetredev@pm.me>
This commit is contained in:
parent
c4f863ff8b
commit
d53844bc93
1 changed files with 873 additions and 32 deletions
|
|
@ -433,11 +433,18 @@ final class _Register implements AccountRegister {
|
|||
}) => _answer('setRecoveryKeys', () {});
|
||||
|
||||
@override
|
||||
Future<void> deleteAccount(Session session, UuidValue person) =>
|
||||
_answer('deleteAccount', () {
|
||||
deleted.add(person);
|
||||
accounts.remove(person);
|
||||
});
|
||||
Future<void> deleteAccount(
|
||||
Session session,
|
||||
UuidValue person, {
|
||||
DeletionProof? proof,
|
||||
}) => _answer('deleteAccount', () {
|
||||
deleted.add(person);
|
||||
deletedWith.add(proof);
|
||||
accounts.remove(person);
|
||||
});
|
||||
|
||||
/// The proofs deletions came with, as the member bound them.
|
||||
final deletedWith = <DeletionProof?>[];
|
||||
|
||||
@override
|
||||
Future<Set<UuidValue>> knownAccounts(
|
||||
|
|
@ -831,6 +838,24 @@ void main() {
|
|||
expect(await AuthUser.db.findById(session, anna), isNotNull);
|
||||
});
|
||||
|
||||
test("passes the password's proof on to the register, bound to "
|
||||
'the host the device addressed here', () async {
|
||||
await endpoints.account.delete(
|
||||
asBen(),
|
||||
proof: DeletionProof(
|
||||
challenge: const Uuid().v7obj(),
|
||||
clientValue: ByteData(384),
|
||||
clientProof: ByteData(32),
|
||||
totpCode: '123456',
|
||||
host: 'LOCALHOST',
|
||||
),
|
||||
);
|
||||
|
||||
expect(register.deleted, [ben]);
|
||||
expect(register.deletedWith.single?.host, testHost);
|
||||
expect(register.deletedWith.single?.totpCode, '123456');
|
||||
});
|
||||
|
||||
test('of an anonymous person deletes it here alone', () async {
|
||||
await endpoints.account.delete(asAnna());
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue