# Email Flow
In creating an email flow that maintains PRIVACY and SECURITY whilst also being convenient to use, the following principles were observed:
- Keypair must be generated client-side
- Keypair must be protected by a password
- There must be protection from keyloggers
- It must be possible to change the password
- It must remain possible to work offline
- Network traffic must not contain identifying metadata
All of the above is achieved using a high level flow as follows:
1. Generate temporary key pair for secure server communication
2. Validate email using a 6 digit code
3. Provide some server side entropy to client
4. Combine entropy + complex user password to encrypt the final keypair
5. Store the encrypted keypair on the server
The password is only used to encrypt the key and is never stored or sent anywhere. Hence, the server cannot decrypt the backup. All key signing / encryption operations happen on client side using [private class properties](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes/Private_properties).
## SIGNUP FLOW
```mermaid
sequenceDiagram
autoNumber
actor U as SIGit User
participant W as SIGit Website
participant D as DVM
Participant DB as DataBase
Note over W,D: All comms over
Nostr Relay
U->>W: Click SIGNUP and enter
email address
Note over W: Ephemeral key generated
to communicate with DVM
W->>D: Request Account
Note right of W: Event uses PoW and
encrypts only EMAIL
to dvm@sigit.io pubkey
D -x DB: Verify PoW and check
if email exists
Note over D: If email already exists,
send user to LOGIN.
Otherwise#58;
D->>DB: Create Temp Session
Note over DB: SESSION entry#58;
#128274;session.pubkey="ephemeral pubkey"
session.email=lowcase($EMAIL)
session.email_code=INT (6 digits)
session.created_at=now()
D->>U: Send session.email_code via email
D->>W: Account created
Note left of D: Payload is an empty string or
an encrypted (and detailed)
error message
W->>U: Tell user to check email and
to open it in the
SAME BROWSER SESSION
Note over W: Screen to accept the 6 digits
is already displayed
(mobile optimised if relevant)
U->>W: User opens link or enters the code
W->>D: Verify Account
Note right of W: Event uses PoW and
encrypts only CODE
to DVM pubkey
D -x DB: Check email_code where
session pk=event pk
D->>DB: If code matches,
create User Account
Note over DB: USER entry#58;
#128274;user.id=uid()
user.email=session.email
user.pubkey=""
user.activated=false
user.created_at=now()
user.bkp=""
user.entropy=uid()
D->>W: Provide user.entropy
Note left of D: Payload encrypted to ephemeral
pubkey. Is either a UID or a
detailed error message.
Note over W: Client verifies that
DVM response came from
DVM pubkey
W->>U: Ask for secure password
Note right of U: This password is what prevents
backend from decrypting the nsec
Note right of U: User is warned that they CANNOT
RESET PASSWORD, should USE
PASSWORD MANAGER etc
U->>W: Enter password (twice)
Note over W: Nostr Keypair Generated
& Encrypted inside a
PRIVATE METHOD,
using password + entropy.
Password variable is not
stored, sent or printed
anywhere. Temporary
variables are destroyed.
W->>D: Request account activation
Note right of W: Event uses PoW and
encrypts both PUBKEY
and the already-
encrypted BACKUP
to the DVM pubkey
D -x DB: Ensure event pubkey
in SESSION table
D->>DB: Update Account
Note over DB: user.activated=true
user.pubkey=$pubkey
user.bkp=$backup
D->>W: Account activated
Note left of D: Payload is an empty string or
an encrypted (and detailed)
error message
W->>U: User is automatically logged in
Note over W: Ephemeral key is destroyed
Default relay list applied
```