Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Unverified user login attempts still getting generic error on V3 #11358

Open
nfl001 opened this issue Feb 24, 2025 · 3 comments · May be fixed by #11647
Open

Unverified user login attempts still getting generic error on V3 #11358

nfl001 opened this issue Feb 24, 2025 · 3 comments · May be fixed by #11647
Labels
status: needs-triage Possible bug which hasn't been reproduced yet

Comments

@nfl001
Copy link

nfl001 commented Feb 24, 2025

Describe the Bug

This issue is similar to #5040 in V3. When logging into an auth-enabled collection that requires email verification, users who haven't verified their email get a generic error:

AuthenticationError: The email or password provided is incorrect.

Instead, the error should clearly state that email verification is required, helping users understand why they can't log in and directing them to check their email.

Link to the code that reproduces this issue

https://github.com/nfl001/payload

Reproduction Steps

  • Create a collection
  • Enable auth.verify
  • Create a user
  • Don't verify email
  • Try to log in

Which area(s) are affected? (Select all that apply)

area: core

Environment Info

Payload: 3.24.0
NodeJS: 22.0.0
@nfl001 nfl001 added status: needs-triage Possible bug which hasn't been reproduced yet validate-reproduction Auto-added tag on create to tell bot to check recreation URL, removed after check. labels Feb 24, 2025
@github-actions github-actions bot removed the validate-reproduction Auto-added tag on create to tell bot to check recreation URL, removed after check. label Feb 24, 2025
@nfl001
Copy link
Author

nfl001 commented Feb 24, 2025

Currently I use custom login endpoint as workaround to return custom error if the user is not validated.

import {
  Collection,
  CollectionConfig,
  generatePayloadCookie,
  headersWithCors,
  PayloadRequest,
} from 'payload'
...
endpoints: [
    {
      path: '/verified/login',
      method: 'post',
      handler: async (req: PayloadRequest) => {
        try {
          if (!req.json)
            return new Response('body is missing', {
              headers: headersWithCors({ headers: new Headers(), req }),
              status: 400,
            })

          const body = await req.json()

          const email = body.email ? body.email.toLowerCase().trim() : null
          const password = body.password

          if (!email || !password) {
            return new Response('email or password is missing', {
              headers: headersWithCors({ headers: new Headers(), req }),
              status: 400,
            })
          }

          const collection = req.payload.collections['users'] as Collection

          const user = await req.payload.find({
            collection: 'users',
            where: {
              email,
            },
          })

          if (user.docs.length === 0) {
            return new Response('invalid email or password', {
              headers: headersWithCors({ headers: new Headers(), req }),
              status: 401,
            })
          }

          if (!user.docs[0]._verified) {
            return new Response('email not verified', {
              headers: headersWithCors({ headers: new Headers(), req }),
              status: 401,
            })
          }

          const authResult = await req.payload.login({
            collection: 'users',
            data: {
              email,
              password,
            },
            req: req,
          })

          const cookie = generatePayloadCookie({
            collectionAuthConfig: collection.config.auth,
            cookiePrefix: req.payload.config.cookiePrefix,
            token: authResult.token ?? '',
          })

          if (!authResult) {
            return new Response('invalid email or password', {
              headers: headersWithCors({ headers: new Headers(), req }),
              status: 401,
            })
          }

          return new Response(JSON.stringify(authResult), {
            headers: headersWithCors({ headers: new Headers({ 'Set-Cookie': cookie }), req }),
            status: 200,
          })
        } catch (error: unknown) {
          return new Response('internal server error', {
            headers: headersWithCors({ headers: new Headers(), req }),
            status: 500,
          })
        }
      },
    },
  ],

@RaghavJha1965
Copy link

Hi @nfl001 and Payload CMS team,

I'd like to contribute to resolving this issue. I understand that when auth.verify is enabled, unverified users currently receive a generic error message:

AuthenticationError: The email or password provided is incorrect.

Proposed Solution:

I plan to:

  • Investigate the authentication flow in the Payload CMS codebase to identify where the error message is generated.
  • Add a Check to determine if the user is unverified and return a more specific error message, such as:
Email not verified. Please check your inbox to verify your email before logging in.
  • Ensure Compatibility with existing authentication and error-handling flows.

Benefits:

  • Improves user experience by providing a clear and actionable error message.
  • Reduces confusion for unverified users, leading to fewer support requests.

Next Steps:

  • I'll start by replicating the issue locally and explore the core code.
  • I'll provide updates on my progress here and submit a pull request if I find a viable solution.

Please let me know if there are any guidelines or preferences I should follow while implementing this fix.

Looking forward to your feedback!

@nfl001
Copy link
Author

nfl001 commented Mar 3, 2025

Hi @RaghavJha1965 love to hear that. I am also new in term of using payload CMS, not really sure how the default auth workflow works. Totally excited to see your solution implemented.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
status: needs-triage Possible bug which hasn't been reproduced yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants