A person the app has not seen
The first time someone signs in whom your app has no user for, Jadpo
asks your app what to do. on_first_sign_in: in authentication { }
names the action that decides: create a user, link one that already
exists, or refuse. One action decides for every way in.
It runs when:
- a magic link or code is used for an address no user has;
- a provider returns an account not yet linked to a user;
- an external token names a subject not yet linked to a user.
Here the action refuses an address Google hasn't verified, and creates a member otherwise:
// domains/accounts/actions/create_member.jadpoaction create_member(first: FirstSignIn) fails SignUpClosed -> Member.id { if (first.method == SignInMethod.google and not first.address_verified) { reject SignUpClosed } var member: Member = attempt Member.create(...) return member.id}
FirstSignIn field |
Type | Holds |
|---|---|---|
method |
SignInMethod |
The way in: magic_link, each provider named under sign_in:, or external_token; a built-in enum with one value per way the app declares |
address |
Email? |
For a magic link, the address, verified; for a provider, its email claim; for an external token, none |
address_verified |
Bool |
true for a magic link; the provider's own verified claim for a provider; false for an external token |
subject |
Text? |
The provider's or token's subject; none for a magic link |
name |
Text? |
The display name a provider's profile gives, when it gives one |
- The action takes exactly one
FirstSignInand returns theidof the principal's user entity: a user it created, or one that already exists. It runs in its own transaction before the session starts. - To refuse, it fails with any failure it declares. The person always
sees the same built-in
sign_in_refused, whatever the reason. The log and theSignInRefusedevent keep the real one. - For a provider or an external token, Jadpo then records the link, from
the method and subject to the user's
id, in thejadpo_sign_in_linkssystem table, so the next sign-in skips the action. A magic link needs no link: Jadpo finds the user byaddress:. - Linking a user who already exists, by their address, is the action's
choice. Do it only when
address_verifiedistrue, so no one can take over an account by claiming its address at a provider that doesn't check it. - Without
on_first_sign_in:, only users who already exist sign in. An unknown address gets no email, and an unknown provider account or token subject issign_in_refused. - A passkey never runs it. Only a person already signed in can add a passkey, so every passkey that signs in has its user.
Not built yet: on_first_sign_in: for provider and external-token sign-in.
An external token whose subject no user has is sign_in_refused (403).
Markdown for agents: /docs/a-person-the-app-has-not-seen.md.Built from Jadpo main at a707efb.