Back

Email verification

  • 0
  • Self Hosted
  • Accounts
  • General
  • Web
kathelia.dokgu
28 Jul, 2023, 20:36

I am trying to send an email verification when a user registers on my project but I am getting the following error:

TypeScript
{
  message: 'User (role: guests) missing scope (account)',
  code: 401,
  type: 'general_unauthorized_scope',
  version: '1.3.8'
}

At this point the user isn't logged in yet as they have just submitted their registration form:

TypeScript
try {
  const userAccount = await account.create(ID.unique(), email, password, `${firstname} ${lastname}`);
  await account.createVerification(Constants.BASE_URL);

  res.status(StatusCodes.OK).json(userAccount);
} catch (error: any) {
  res.status(StatusCodes.INTERNAL_SERVER_ERROR).json(error);
}
TL;DR
The user is encountering an error when trying to send an email verification to a newly registered user. The error message states that the user is missing the 'account' scope. The suggested solution is to create a session for the user after they register by calling `account.createSession()`. Then, proceed to call `account.createVerification()` to send the email verification. This should resolve the error. Flow: 1. User submits registration form. 2. Server validates the form and calls `account.create()`. 3. Server calls `account.createSession()` to create a session for the user. 4. Server calls `account.createVerification()` to
kathelia.dokgu
28 Jul, 2023, 22:47

@Steven any idea why it's telling me I am not logged in when trying to send the verification email to a user who just registered to my project?

Drake
28 Jul, 2023, 23:14

please don't tag people just because you need help as it can be disruptive. just post and wait

Drake
28 Jul, 2023, 23:15

This error means there is no session (the user is not logged in).

Looking at the code you shared, you created an account, but you didn't create a session

kathelia.dokgu
28 Jul, 2023, 23:22

Looking at this page: https://gist.github.com/eldadfux/2eea9df7cc6dc18b63955dd8b10ad758

There's a quoted text that says

By default, unverified users are not restricted in any special way. It's up to you and your app logic to decide how these users are treated. You can prompt them with a verification message or limit their access to your application.

It does mention that users need to be logged in before calling createVerification but what if I want to control access so that only verified accounts are able to log in?

Drake
28 Jul, 2023, 23:33

It does mention that users need to be logged in before calling createVerification but what if I want to control access so that only verified accounts are able to log in?

You would do that with permissions; limit access to resources to verified users. See https://appwrite.io/docs/permissions#permission-roles

kathelia.dokgu
28 Jul, 2023, 23:48

That's not really what I want to do as it pertains to resources like documents - what I want to do is after a user registers, they'll get an email to verify their account. Until they verify their account, they should be just be stuck on the login screen until they click on the link. Any attempt to login as an unverified account should be blocked. The permissions are for a different layer I think.

Anyway I tried:

TypeScript
const userAccount = await account.create(ID.unique(), email, password, `${firstname} ${lastname}`);
await account.createEmailSession(email, password);
await account.createVerification(Constants.BASE_URL);
await account.deleteSessions();

But I'm still getting the same error.

Drake
28 Jul, 2023, 23:59

Until they verify their account, they should be just be stuck on the login screen until they click on the link.

Your UI can just show a page saying they must verify instead of showing data

The permissions are for a different layer I think.

No, i recommend this approach.

Drake
28 Jul, 2023, 23:59

where is this code running? client side or server side?

kathelia.dokgu
28 Jul, 2023, 23:59

Currently on server side.

Drake
29 Jul, 2023, 00:00

well ya that's not going to work because the web sdk uses cookies or local storage for session management. neither of those are available server side

kathelia.dokgu
29 Jul, 2023, 00:06

So what's the flow that I should implement here?

[CLIENT] - User submits the registration form [SERVER] - Validate the registration form and return the result of account.create() [CLIENT] - Call account.createEmailSession() [CLIENT] - Call account.get() [CLIENT/SERVER] - call account.createVerification()

This doesn't look right to me.

Drake
29 Jul, 2023, 00:22

SSR is a huge pain. I would recommend avoiding it if possible. If you really want to use SSR, you'll need to figure out a way to have the session server-side when needed.

One way to do this is to create the session client side, create a jwt token, and then pass that server side.

Another way is to proxy the session creation through your backend where your backend will create the session manually, grab the cookie, and set it for the client. You can see an example of that here: https://next-js.ssr.almostapps.eu/

kathelia.dokgu
29 Jul, 2023, 00:50

I think I am okay with avoiding SSR for most stuff - I really only need the backend API of NextJS to limit the registrations and login to certain emails - that's why I have some extra validation before I call account.create().

Reply

Reply to this thread by joining our Discord

Reply on Discord

Need support?

Join our Discord

Get community support by joining our Discord server.

Join Discord

Get premium support

Join Appwrite Pro and get email support from our team.

Learn more