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

Whitelisting of possible signups #36

Open
1 task done
hechi opened this issue Jan 8, 2023 · 3 comments
Open
1 task done

Whitelisting of possible signups #36

hechi opened this issue Jan 8, 2023 · 3 comments
Labels
enhancement New feature or request

Comments

@hechi
Copy link

hechi commented Jan 8, 2023

Clear and concise description of the problem

Hey Nico,
first of all thx a lot for briefkasten and your contribution in so many project ❤️ it's really nice. I really envy your frontend as well as backend skill 😅
anyway...

I played around with briefkasten and one thing which i miss is to not allow everybody to sign up on my instance 😅 ex. i have email verify activated (easiest one for me) and i would like to give it to my family members and some friends but not the whole world. Same applies if i would use one of the Oauth Providers (like github). I tried to search on next-auth.js but they also don't have an option for it.


I wish i could have a list of allowed user/domain's to my instance, so that i can provide access to some people around me but not everybody.

Suggested solution

Before sending the login option to next-auth.js check if a domain or usernames are in the whitelist 🤷

Alternative

Hardcoded ENV with domainnames would be totally enough i think

ALLOWED_EMAIL_SIGNUP=*example.com,[email protected]

Additional context

No response

Validations

  • Check that there isn't already an issue that request the same feature to avoid creating a duplicate.
@hechi hechi added the enhancement New feature or request label Jan 8, 2023
Copy link
Owner

ndom91 commented Jan 14, 2023

One quick option would be to limit Google OAuth logins to internal domain members only. This only works in the case that you're using it for a family/company domain. So for example, if you set it up under a G Suite / Google Worksapce domain company.com. Then you can check the box in the Client ID setup for "internal only" and it'll only allow users with google accounts *@company.com.

Obviously this is a rather limited use-case..

For the email provider, you could theoretically return early from the createVerificationRequest method. This is the callback next-auth gives you to modify the Email it generates to send out to potential sign-ups. So what you cuold do it take the built-in behavior of that, and just wrap it to see if the domains you want are included in the email or not and if not just don't send the email.

See: https://next-auth.js.org/providers/email#customizing-emails

For example:

import { createTransport } from "nodemailer"
  
const wantedEmails = process.env.ALLOWED_EMAIL_DOMAINS?.split(' ')
// This is the space separated ALLOWED_EMAILS you'd suggested.
// For example: 
// ALLOWED_EMAIL_DOMAINS=gmx.de gmail.com company.de
  
async function sendVerificationRequest(params) {
  const { identifier, url, provider, theme } = params
  const emailDomain = identifier.split("@")[1]
  
  if (wantedEmails.includes(emailDomain)) {
    const { host } = new URL(url)
    const transport = createTransport(provider.server)
    const result = await transport.sendMail({
      to: identifier,
      from: provider.from,
      subject: `Sign in to ${host}`,
      text: text({ url, host }),
      html: html({ url, host, theme }),
    })
    const failed = result.rejected.concat(result.pending).filter(Boolean)
    if (failed.length) {
      throw new Error(`Email(s) (${failed.join(", ")}) could not be sent`)
    }
  }
}

@hechi
Copy link
Author

hechi commented Jan 15, 2023

Thanks a lot for your detailed answer :) The google solution sounds interesting but not all of them have google yet :D

I agree its probably a very limited use-case but the customizing-email solution looks very interesting. If i would try my luck would here be the best place for it or would you see it somewhere else?

Thanks again 😊

@ndom91
Copy link
Owner

ndom91 commented Jan 25, 2023

Thanks a lot for your detailed answer :) The google solution sounds interesting but not all of them have google yet :D

I agree its probably a very limited use-case but the customizing-email solution looks very interesting. If i would try my luck would here be the best place for it or would you see it somewhere else?

Thanks again blush

Exactly, so there you could do something like:

const wantedEmails = process.env.ALLOWED_EMAIL_DOMAINS?.split(' ') ?? []
// This is the space separated ALLOWED_EMAILS you'd suggested.
// For example: 
// ALLOWED_EMAIL_DOMAINS=gmx.de gmail.com company.de

...

if (process.env.SMTP_SERVER && process.env.SMTP_FROM) {
  providers.push(
    EmailProvider({
      server: process.env.SMTP_SERVER,
      from: process.env.SMTP_FROM,
      sendVerificationRequest: async ({
        identifier: email,
        url,
        provider: { server, from },
        theme,
      }) => {
        const emailDomain = email.split("@")[1];

        if (wantedEmails.includes(emailDomain)) {
          const { host } = new URL(url);
          const transport = createTransport(server);
          const result = await transport.sendMail({
            to: email,
            from: from,
            subject: `Sign in to ${host}`,
            text: text({ url, host }),
            html: html({ url, host, theme }),
          });
          const failed = result.rejected.concat(result.pending).filter(Boolean);
          if (failed.length) {
            throw new Error(
              `Email(s) (${failed.join(", ")}) could not be sent`
            );
          }
        }
      },
    })
  );
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

2 participants