From ec86bbc4fea268cece08d340b184b1fba3f5e767 Mon Sep 17 00:00:00 2001 From: Charis <26616127+charislam@users.noreply.github.com> Date: Tue, 7 May 2024 16:15:06 -0400 Subject: [PATCH] feat: new auth ia (#22812) Co-authored-by: Kang Ming Co-authored-by: Joel Lee --- .../AuthSmsProviderConfig.Warnings.tsx | 19 + .../AuthSmsProviderConfig.tsx | 86 ++ .../MessageBirdConfig.mdx | 48 ++ .../AuthSmsProviderConfig/TextLocalConfig.mdx | 42 + .../AuthSmsProviderConfig/TwilioConfig.mdx | 130 +++ .../AuthSmsProviderConfig/VonageConfig.mdx | 49 ++ .../AuthSmsProviderConfig/index.tsx | 7 + .../docs/components/GuidesTableOfContents.tsx | 5 +- apps/docs/components/MDX/auth_rate_limits.mdx | 14 + .../MDX/oauth_pkce_flow.mdx} | 96 +-- ...ser_management_quickstart_sql_template.mdx | 2 +- .../NavigationMenu.constants.ts | 219 ++--- .../Navigation/NavigationMenu/TopNavBar.tsx | 2 +- apps/docs/components/SharedData.tsx | 25 +- apps/docs/components/Tabs.tsx | 31 +- apps/docs/components/index.tsx | 10 +- .../reference/RefFunctionSection.tsx | 16 +- apps/docs/content/guides/api/api-keys.mdx | 2 +- .../content/guides/api/securing-your-api.mdx | 2 +- apps/docs/content/guides/auth.mdx | 145 +--- .../content/guides/auth/_flow-template.mdx | 34 + .../docs/content/guides/auth/architecture.mdx | 70 ++ .../content/guides/auth/auth-anonymous.mdx | 4 +- .../docs/content/guides/auth/auth-captcha.mdx | 11 +- .../auth/auth-deep-dive/auth-google-oauth.mdx | 105 --- .../auth/auth-deep-dive/auth-gotrue.mdx | 79 -- .../auth/auth-deep-dive/auth-policies.mdx | 186 ---- .../auth-row-level-security.mdx | 135 --- .../guides/auth/auth-email-passwordless.mdx | 281 ++++++ .../guides/auth/auth-email-templates.mdx | 8 + apps/docs/content/guides/auth/auth-email.mdx | 213 ----- .../guides/auth/auth-helpers/sveltekit.mdx | 2 +- .../guides/auth/auth-identity-linking.mdx | 17 - apps/docs/content/guides/auth/auth-mfa.mdx | 2 +- .../guides/auth/general-configuration.mdx | 27 + apps/docs/content/guides/auth/identities.mdx | 27 + .../auth-deep-dive-jwts.mdx => jwts.mdx} | 53 +- .../guides/auth/managing-user-data.mdx | 192 +---- .../auth/native-mobile-deep-linking.mdx | 14 +- .../guides/auth/native-mobile-login.mdx | 51 -- .../content/guides/auth/password-security.mdx | 48 ++ .../guides/auth/passwordless-login.mdx | 51 -- .../passwordless-login/auth-email-otp.mdx | 163 ---- .../passwordless-login/auth-magic-link.mdx | 163 ---- apps/docs/content/guides/auth/passwords.mdx | 798 ++++++++++++++++-- apps/docs/content/guides/auth/phone-login.mdx | 247 ++---- apps/docs/content/guides/auth/rate-limits.mdx | 8 + .../auth/{concepts => }/redirect-urls.mdx | 4 +- .../guides/auth/row-level-security.mdx | 310 ------- .../guides/auth/server-side-rendering.mdx | 240 ------ .../overview.mdx => server-side.mdx} | 39 +- .../auth/server-side/advanced-guide.mdx | 67 ++ ...mail-based-auth-with-pkce-flow-for-ssr.mdx | 305 ------- apps/docs/content/guides/auth/sessions.mdx | 31 +- .../guides/auth/sessions/implicit-flow.mdx | 33 + .../guides/auth/sessions/pkce-flow.mdx | 83 ++ apps/docs/content/guides/auth/signout.mdx | 77 ++ .../guides/auth/social-login/auth-apple.mdx | 2 + .../guides/auth/social-login/auth-azure.mdx | 2 + .../auth/social-login/auth-bitbucket.mdx | 2 + .../guides/auth/social-login/auth-discord.mdx | 2 + .../auth/social-login/auth-facebook.mdx | 2 + .../guides/auth/social-login/auth-figma.mdx | 2 + .../guides/auth/social-login/auth-github.mdx | 2 + .../guides/auth/social-login/auth-gitlab.mdx | 2 + .../guides/auth/social-login/auth-google.mdx | 2 + .../guides/auth/social-login/auth-kakao.mdx | 2 + .../auth/social-login/auth-keycloak.mdx | 2 + .../auth/social-login/auth-linkedin.mdx | 2 + .../guides/auth/social-login/auth-notion.mdx | 2 + .../guides/auth/social-login/auth-slack.mdx | 2 + .../guides/auth/social-login/auth-spotify.mdx | 2 + .../guides/auth/social-login/auth-twitch.mdx | 2 + .../guides/auth/social-login/auth-twitter.mdx | 2 + .../guides/auth/social-login/auth-workos.mdx | 2 + .../guides/auth/social-login/auth-zoom.mdx | 2 + .../{auth-user-management.mdx => users.mdx} | 60 +- ...ims-and-role-based-access-control-rbac.mdx | 8 +- .../guides/database/postgres/roles.mdx | 2 +- .../database/postgres/row-level-security.mdx | 114 ++- apps/docs/content/guides/functions/auth.mdx | 4 +- .../docs/content/guides/functions/secrets.mdx | 4 +- .../guides/getting-started/features.mdx | 4 +- .../guides/platform/going-into-prod.mdx | 17 +- .../docs/content/guides/realtime/concepts.mdx | 4 +- .../guides/realtime/postgres-changes.mdx | 2 +- apps/docs/hooks/useHash.ts | 17 +- apps/docs/layouts/MainSkeleton.tsx | 19 +- apps/docs/layouts/guides/index.tsx | 2 +- apps/docs/lib/docs.ts | 26 +- apps/docs/pages/guides/cli/config.tsx | 2 +- apps/docs/spec/examples/examples.yml | 6 +- apps/docs/spec/supabase_csharp_v0.yml | 4 +- apps/docs/spec/supabase_dart_v1.yml | 4 +- apps/docs/spec/supabase_dart_v2.yml | 4 +- apps/docs/spec/supabase_js_v2.yml | 6 +- apps/docs/spec/supabase_kt_v1.yml | 6 +- apps/docs/spec/supabase_kt_v2.yml | 6 +- apps/docs/spec/supabase_py_v2.yml | 8 +- apps/docs/spec/supabase_swift_v1.yml | 6 +- apps/docs/spec/supabase_swift_v2.yml | 4 +- package-lock.json | 84 +- packages/shared-data/config.ts | 104 +++ packages/shared-data/index.ts | 3 +- packages/ui-patterns/ComplexTabs/index.tsx | 1 + .../ComplexTabs/withQueryParams.tsx | 15 +- .../ui-patterns/ComplexTabs/withSticky.tsx | 60 ++ .../ComplexTabs/withSticky.utils.ts | 53 ++ packages/ui/package.json | 2 + .../components/CustomHTMLElements/Heading.tsx | 75 +- packages/ui/src/components/Tabs/Tabs.tsx | 22 +- vale/styles/Custom/Contractions.yml | 30 - vale/styles/Custom/Quotes.yml | 7 - 113 files changed, 2857 insertions(+), 3104 deletions(-) create mode 100644 apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.Warnings.tsx create mode 100644 apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.tsx create mode 100644 apps/docs/components/AuthSmsProviderConfig/MessageBirdConfig.mdx create mode 100644 apps/docs/components/AuthSmsProviderConfig/TextLocalConfig.mdx create mode 100644 apps/docs/components/AuthSmsProviderConfig/TwilioConfig.mdx create mode 100644 apps/docs/components/AuthSmsProviderConfig/VonageConfig.mdx create mode 100644 apps/docs/components/AuthSmsProviderConfig/index.tsx create mode 100644 apps/docs/components/MDX/auth_rate_limits.mdx rename apps/docs/{content/guides/auth/server-side/oauth-with-pkce-flow-for-ssr.mdx => components/MDX/oauth_pkce_flow.mdx} (85%) create mode 100644 apps/docs/content/guides/auth/_flow-template.mdx create mode 100644 apps/docs/content/guides/auth/architecture.mdx delete mode 100644 apps/docs/content/guides/auth/auth-deep-dive/auth-google-oauth.mdx delete mode 100644 apps/docs/content/guides/auth/auth-deep-dive/auth-gotrue.mdx delete mode 100644 apps/docs/content/guides/auth/auth-deep-dive/auth-policies.mdx delete mode 100644 apps/docs/content/guides/auth/auth-deep-dive/auth-row-level-security.mdx create mode 100644 apps/docs/content/guides/auth/auth-email-passwordless.mdx delete mode 100644 apps/docs/content/guides/auth/auth-email.mdx create mode 100644 apps/docs/content/guides/auth/general-configuration.mdx create mode 100644 apps/docs/content/guides/auth/identities.mdx rename apps/docs/content/guides/auth/{auth-deep-dive/auth-deep-dive-jwts.mdx => jwts.mdx} (80%) delete mode 100644 apps/docs/content/guides/auth/native-mobile-login.mdx create mode 100644 apps/docs/content/guides/auth/password-security.mdx delete mode 100644 apps/docs/content/guides/auth/passwordless-login.mdx delete mode 100644 apps/docs/content/guides/auth/passwordless-login/auth-email-otp.mdx delete mode 100644 apps/docs/content/guides/auth/passwordless-login/auth-magic-link.mdx create mode 100644 apps/docs/content/guides/auth/rate-limits.mdx rename apps/docs/content/guides/auth/{concepts => }/redirect-urls.mdx (93%) delete mode 100644 apps/docs/content/guides/auth/row-level-security.mdx delete mode 100644 apps/docs/content/guides/auth/server-side-rendering.mdx rename apps/docs/content/guides/auth/{server-side/overview.mdx => server-side.mdx} (55%) create mode 100644 apps/docs/content/guides/auth/server-side/advanced-guide.mdx delete mode 100644 apps/docs/content/guides/auth/server-side/email-based-auth-with-pkce-flow-for-ssr.mdx create mode 100644 apps/docs/content/guides/auth/sessions/implicit-flow.mdx create mode 100644 apps/docs/content/guides/auth/sessions/pkce-flow.mdx create mode 100644 apps/docs/content/guides/auth/signout.mdx rename apps/docs/content/guides/auth/{auth-user-management.mdx => users.mdx} (75%) rename apps/docs/content/guides/{auth => database/postgres}/custom-claims-and-role-based-access-control-rbac.mdx (96%) create mode 100644 packages/shared-data/config.ts create mode 100644 packages/ui-patterns/ComplexTabs/withSticky.tsx create mode 100644 packages/ui-patterns/ComplexTabs/withSticky.utils.ts delete mode 100644 vale/styles/Custom/Contractions.yml delete mode 100644 vale/styles/Custom/Quotes.yml diff --git a/apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.Warnings.tsx b/apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.Warnings.tsx new file mode 100644 index 0000000000..23801c33a0 --- /dev/null +++ b/apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.Warnings.tsx @@ -0,0 +1,19 @@ +import Link from 'next/link' +import { Admonition } from 'ui' + +const CostWarning = () => ( + +

+ To keep SMS sending costs under control, make sure you adjust your project's rate limits + and configure CAPTCHA. See the{' '} + Production Checklist to learn more. +

+

+ Some countries have special regulations for services that send SMS messages to users, for + example, India's TRAI DLT regulations. Remember to look up and follow the regulations of + countries where you operate. +

+
+) + +export { CostWarning } diff --git a/apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.tsx b/apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.tsx new file mode 100644 index 0000000000..e0e74bcd7a --- /dev/null +++ b/apps/docs/components/AuthSmsProviderConfig/AuthSmsProviderConfig.tsx @@ -0,0 +1,86 @@ +import { useEffect, useReducer, useRef } from 'react' +import { PhoneLoginsItems } from '../Navigation/NavigationMenu/NavigationMenu.constants' +import { IconPanel } from 'ui-patterns/IconPanel' +import { Dialog, DialogContent, DialogHeader, DialogSection, Heading } from 'ui' +import MessageBird from './MessageBirdConfig.mdx' +import Twilio from './TwilioConfig.mdx' +import Vonage from './VonageConfig.mdx' +import TextLocal from './TextLocalConfig.mdx' + +const reducer = (_, action: (typeof PhoneLoginsItems)[number] | undefined) => { + const url = new URL(document.location.href) + if (action) { + url.searchParams.set('showSmsProvider', encodeURIComponent(action.name)) + } else { + url.searchParams.delete('showSmsProvider') + } + window.history.replaceState(null, '', url) + return action +} + +const AuthSmsProviderConfig = () => { + const [selectedProvider, setSelectedProvider] = useReducer(reducer, undefined) + + useEffect(() => { + const providerName = new URLSearchParams(document.location.search ?? '').get('showSmsProvider') + if (!providerName) return + + const provider = PhoneLoginsItems.find((item) => item.name === decodeURIComponent(providerName)) + if (provider) setSelectedProvider(provider) + }, []) + + const headingRef = useRef(null) + + return ( + <> +
+

+ Configuring SMS Providers +

+
+ {PhoneLoginsItems.map((provider) => ( + + ))} +
+
+ !open && setSelectedProvider(undefined)} + > + {selectedProvider && ( + { + evt.preventDefault() + headingRef.current?.focus() + }} + > + + + {selectedProvider.name} + + + + {selectedProvider.name.toLowerCase().includes('messagebird') && } + {selectedProvider.name.toLowerCase().includes('twilio') && } + {selectedProvider.name.toLowerCase().includes('vonage') && } + {selectedProvider.name.toLowerCase().includes('textlocal') && } + + + )} + + + ) +} + +export default AuthSmsProviderConfig diff --git a/apps/docs/components/AuthSmsProviderConfig/MessageBirdConfig.mdx b/apps/docs/components/AuthSmsProviderConfig/MessageBirdConfig.mdx new file mode 100644 index 0000000000..b875124ca4 --- /dev/null +++ b/apps/docs/components/AuthSmsProviderConfig/MessageBirdConfig.mdx @@ -0,0 +1,48 @@ +import { CostWarning } from './AuthSmsProviderConfig.Warnings' + +## Prerequisites + +You'll need: + +- A MessageBird account (sign up [here](https://dashboard.messagebird.com/en/sign-up)) +- A Supabase project (create one [here](https://supabase.com/dashboard)) +- A mobile phone capable of receiving SMS + + + +## Set up MessageBird as your SMS provider + +Start by logging into your MessageBird account and verify the mobile number you'll be using to test with [here](https://dashboard.messagebird.com/en/getting-started/sms). This is the number that will be receiving the SMS OTPs. + +![Verify your own phone number](/docs/img/guides/auth-messagebird/1.png) + +![Get your API Keys](/docs/img/guides/auth-messagebird/2.png) + +Navigate to the [dashboard settings](https://dashboard.messagebird.com/en/settings/sms) to set the default originator. The messagebird originator is the name or number from which the message is sent. For more information, you can refer to the messagebird article on choosing an originator [here](https://support.messagebird.com/hc/en-us/articles/115002628665-Choosing-an-originator) + +![Set the default originator](/docs/img/guides/auth-messagebird/3.png) + +You will need the following values to get started: + +- Live API Key / Test API Key +- MessageBird originator + +Now go to the [Auth > Providers](https://supabase.com/dashboard/project/_/auth/providers) page in the Supabase dashboard and select "Phone" from the Auth Providers list. + +You should see an option to enable the Phone provider. + +Toggle it on, and copy the 2 values over from the Messagebird dashboard. Click save. + + + +If you use the Test API Key, the OTP will not be delivered to the mobile number specified but messagebird will log the response in the dashboard. If the Live API Key is used instead, the OTP will be delivered and there will be a deduction in your free credits. + + + +#### SMS custom template + +The SMS message sent to a phone containing an OTP code can be customized. This is useful if you need to mention a brand name or display a website address. + +Go to [Auth > Templates](https://supabase.com/dashboard/project/_/auth/templates) page in the Supabase dashboard. + +Use the variable `.Code` in the template to display the code. diff --git a/apps/docs/components/AuthSmsProviderConfig/TextLocalConfig.mdx b/apps/docs/components/AuthSmsProviderConfig/TextLocalConfig.mdx new file mode 100644 index 0000000000..c5ced2742f --- /dev/null +++ b/apps/docs/components/AuthSmsProviderConfig/TextLocalConfig.mdx @@ -0,0 +1,42 @@ +import { CostWarning } from './AuthSmsProviderConfig.Warnings' + +## Prerequisites + +Before you begin, ensure you have the following: + +- **A Textlocal account**: Sign up for [TextLocal](https://www.textlocal.com/signup) to start sending SMS messages. +- **A Supabase project**: Necessary for SMS authentication integration. Create your project in the [Supabase Dashboard](https://supabase.com/dashboard). +- **A mobile phone**: To receive SMS messages and test your setup. + + + +## Setting up Textlocal as your SMS provider + +To integrate Textlocal with Supabase: + +1. [Get a Textlocal API key](#get-a-textlocal-api-key) +2. [Customize your sender name](#customize-your-sender-name-optional) +3. [Configure your Supabase project](#configure-supabase) + +### Get a Textlocal API key + +1. Log into your Textlocal account and go to `Settings` > `API Keys`. +2. Generate a new API Key. Save your new API key in a safe location. + +### Customize your sender name (Optional) + +Textlocal defaults to `TXTLCL` as the sender name for all messages. You can customize this to better reflect your brand: + +1. In your Textlocal dashboard, go to `Settings` > `All Settings` > `Sender Names`. +2. Change your sender name. + +### Configure Supabase + +To set up Textlocal as your SMS provider in Supabase, follow these steps: + +1. In your Supabase Dashboard, go to the [Auth Providers section](https://supabase.com/dashboard/project/_/auth/providers). +2. From the list of available authentication providers, select `Phone`. +3. Toggle `Enable Phone Provider`. +4. Under `SMS Provider`, select `Textlocal.` +5. Enter your Textlocal API Key and Sender Name. +6. Customize your SMS Message (optional). diff --git a/apps/docs/components/AuthSmsProviderConfig/TwilioConfig.mdx b/apps/docs/components/AuthSmsProviderConfig/TwilioConfig.mdx new file mode 100644 index 0000000000..87a97928a7 --- /dev/null +++ b/apps/docs/components/AuthSmsProviderConfig/TwilioConfig.mdx @@ -0,0 +1,130 @@ +import { CostWarning } from './AuthSmsProviderConfig.Warnings' + +## Prerequisites + +You'll need: + +- Twilio account ([sign up](https://www.twilio.com/try-twilio)) +- Supabase project (create one [here](https://supabase.com/dashboard)) +- Mobile phone capable of receiving SMS + +SMS Authentication can be done with either Twilio Verify or Twilio Programmable Messaging. [Twilio Verify](https://www.twilio.com/en-us/trusted-activation/verify) is a specialized OTP solution and is recommended for most developers that need over-the-phone authentication. Alternatively you can use [Twilio Programmable Messaging](https://www.twilio.com/docs/messaging) which offers generic SMS sending support. + + + +## Twilio Verify + +To set up Twilio Verify, you will need to: + +1. Create a new [verification service](https://support.twilio.com/hc/en-us/articles/360033309133-Getting-Started-with-Twilio-Verify-V2) in the Twilio dashboard. +2. [Switch Phone Provider to Twilio Verify](https://supabase.com/dashboard/project/_/auth/providers) +3. Configure the Twilio Verify Service ID field using the Verification Service ID obtained in 1. + +When using Twilio Verify, OTPs are generated by Twilio. This means that: + +- Unlike other providers, the OTP expiry duration and message content fields are not configurable via the Supabase dashboard. Please head to Twilio Verify to configure these settings. +- The token remains the same during its validity period until the verification is successful. This means if your user makes another request within that period, they will receive the same token. +- Twilio Verify has a separate set of rate limits that apply. Visit Twilio's [Rate Limit and Timeouts page](https://www.twilio.com/docs/verify/api/rate-limits-and-timeouts) to find out more. + + + +At this time, Twilio Verify is only supported on the `whatsapp` and `sms` channels. + + + +## Twilio (Programmable Messaging) + +In this section, you'll set up Twilio as an SMS provider: + +What you'll need: + +- A Twilio account (sign up here: https://www.twilio.com/try-twilio) +- A Supabase project (create one here: https://supabase.com/dashboard) +- A mobile phone capable of receiving SMS + +
+ +
+ +### Setting up your Twilio credentials + +Start by logging into your Twilio account and starting a new project: https://www.twilio.com/console/projects/create + +Give your project a name and verify the mobile number you'll be using to test with. This is the number that will be receiving the SMS OTPs. + +![Name your twilio project](/docs/img/guides/auth-twilio/1.png) +![verify your own phone number](/docs/img/guides/auth-twilio/2.png) + +Select 'SMS', 'Identity & Verification', and 'With code' as options on the welcome form. + +![Form Fields](/docs/img/guides/auth-twilio/3.png) + +When you're back on the [Twilio console screen](https://www.twilio.com/console), you need to scroll down and click 'Get a trial phone number' - this is the number that you'll be sending SMSs from. + +![Get a trial phone number](/docs/img/guides/auth-twilio/4.png) + +![Successful phone number](/docs/img/guides/auth-twilio/5.png) + +You should now be able to see all three values you'll need to get started: + +- Account SID +- Auth Token +- Sender Phone Number + +![All the credentials you'll need](/docs/img/guides/auth-twilio/6.png) + +Now go to the [Auth > Providers](https://supabase.com/dashboard/project/_/auth/providers) page in the Supabase dashboard and select "Phone" from the Auth Providers list. + +You should see an option to enable the Phone provider. + +Toggle it on, and copy the 3 values over from the Twilio dashboard. Click save. + +Note: for "Twilio Message Service SID" you can use the Sender Phone Number generated above. + +![Plug in Twilio credentials](/docs/img/guides/auth-twilio/8.png) + +Now the backend should be setup, we can proceed to add our client-side code! + + + The `Twilio Content SID` field is specific to Twilio Programmable Messaging (WhatsApp) senders. + Disregard this field if you are only sending SMS messages. Refer to the section on WhatsApp OTP + Logins for further details. + + +#### SMS custom template + +The SMS message sent to a phone containing an OTP code can be customized. This is useful if you need to mention a brand name or display a website address. + +Go to the [Auth > Providers](https://supabase.com/dashboard/project/_/auth/providers) page in the Supabase dashboard and select "Phone" from the Auth Providers list. Scroll to the very bottom of the "Phone" section to the "SMS Message" input - you can customize the SMS message here. + +Use the variable `.Code` in the template to display the OTP code. Here's an example in the SMS template. + +![example in the SMS template](/docs/img/guides/auth-twilio/9.png) + +## WhatsApp OTP logins + +In some cases, you may wish to use WhatsApp as a delivery channel instead. Here are some examples our users have cited: + +- You want higher deliverability +- You wish for a secure channel +- Your users mostly use WhatsApp as a messaging platform + +Twilio Verify can be used with WhatsApp OTPs with no additional configuration. + +Complete the following steps to use WhatsApp OTP with Twilio Programmable Messaging: + +1. Go through the [Twilio self sign up guide for WhatsApp](https://www.twilio.com/docs/whatsapp/self-sign-up). +2. Register a Twilio Content Template via the [API](https://www.twilio.com/docs/content/whatsappauthentication) and note the corresponding Twilio Content SID. You can also use the Template Builder on the Twilio dashboard to create a Content Template + ![Twilio Content SID Image](/docs/img/guides/auth-twilio/twilio_content_sid.png) +3. Register the Twilio Content SID on the Supabase dashboard under Authentication > Providers > Phone > Twilio Content SID. Ensure you have Twilio selected as your phone provider. + + + +You may only use one Twilio Content SID at a time. Supabase Auth will use the Content Template over the `SMS Message` field when sending WhatsApp messages. Use Twilio Verify if you need to use more than one message template. + + diff --git a/apps/docs/components/AuthSmsProviderConfig/VonageConfig.mdx b/apps/docs/components/AuthSmsProviderConfig/VonageConfig.mdx new file mode 100644 index 0000000000..89d13bf93a --- /dev/null +++ b/apps/docs/components/AuthSmsProviderConfig/VonageConfig.mdx @@ -0,0 +1,49 @@ +import { CostWarning } from './AuthSmsProviderConfig.Warnings' + +## Prerequisites + +You'll need: + +- A Vonage account (sign up here: https://dashboard.nexmo.com/sign-up) +- A Supabase project (create one here: https://supabase.com/dashboard) +- A mobile phone capable of receiving SMS + + + +## Set up Vonage as an SMS provider + +### Getting your Vonage credentials + +Start by logging into your Vonage Dashboard at https://dashboard.nexmo.com/ + +You will see you API Key and API Secret here, which is actually all you need to get started. + +In most countries, a phone number is actually optional and you can also use any Alphanumeric Sender ID of up to 11 characters length (8 for India) as a Sender ID (from). This means you do not need a number to test with in most cases. + +To find out more about supported countries for Alphanumeric Sender ID, check this overview: https://help.nexmo.com/hc/en-us/articles/115011781468-SMS-Features-Overview-Outbound-only- + +Hint: Some countries might need a Sender ID Registration to allow sending with an Alphanumeric Sender ID. You can find this information in the help article as well. If Alpha Sender IDs are not supported, you will need to buy a phone number. + +### Getting a phone number (optional) + +If you want a phone number to send SMS from, you can buy one from the Vonage Dashboard under Numbers > Buy Numbers (https://dashboard.nexmo.com/buy-numbers). + +Select the country you want a number for. You will need a mobile phone number with SMS or SMS+Voice capability. After you have bought the number, you will be able to send SMS from it. + +### Configure Supabase + +Now go to the [Auth > Providers](https://supabase.com/dashboard/project/_/auth/providers) page in the Supabase dashboard and select "Phone" from the Auth Providers list. + +You should see an option to enable the Phone provider. + +Toggle it on, and copy the API key, API secret and phone number values over from the Vonage dashboard. Click save. + +Now the backend should be setup, we can proceed to add our client-side code! + +#### SMS custom template + +The SMS message sent to a phone containing an OTP code can be customized. This is useful if you need to mention a brand name or display a website address. + +Go to [Auth > Templates](https://supabase.com/dashboard/project/_/auth/templates) page in the Supabase dashboard. + +Use the variable `.Code` in the template to display the code. diff --git a/apps/docs/components/AuthSmsProviderConfig/index.tsx b/apps/docs/components/AuthSmsProviderConfig/index.tsx new file mode 100644 index 0000000000..70911f76d4 --- /dev/null +++ b/apps/docs/components/AuthSmsProviderConfig/index.tsx @@ -0,0 +1,7 @@ +import dynamic from 'next/dynamic' + +const LazyConfig = dynamic(() => import('./AuthSmsProviderConfig')) + +const AuthSmsProviderConfig = () => + +export { AuthSmsProviderConfig } diff --git a/apps/docs/components/GuidesTableOfContents.tsx b/apps/docs/components/GuidesTableOfContents.tsx index 5b42a189ed..3e4aefbc7b 100644 --- a/apps/docs/components/GuidesTableOfContents.tsx +++ b/apps/docs/components/GuidesTableOfContents.tsx @@ -83,10 +83,13 @@ const GuidesTableOfContents = ({ .filter((heading) => heading.id) .map((heading) => { const text = heading.textContent.replace('#', '') - const link = heading.querySelector('a').getAttribute('href') + const link = heading.querySelector('a')?.getAttribute('href') + if (!link) return null + const level = heading.tagName === 'H2' ? 2 : 3 return { text, link, level } }) + .filter(Boolean) setTocList(newHeadings) }) diff --git a/apps/docs/components/MDX/auth_rate_limits.mdx b/apps/docs/components/MDX/auth_rate_limits.mdx new file mode 100644 index 0000000000..f5ac2fb149 --- /dev/null +++ b/apps/docs/components/MDX/auth_rate_limits.mdx @@ -0,0 +1,14 @@ +| Endpoint | Path | Limited By | Rate Limit | +| ------------------------------------------------ | -------------------------------------------------------------- | ------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | +| All endpoints that send emails | `/auth/v1/signup` `/auth/v1/recover` `/auth/v1/user`[^1] | Sum of combined requests | Defaults to 30 emails per hour. As of 14th July 2023, this has been updated to 4 emails per hour. As of 21 Oct 2023, this has been updated to auth.rate_limits.email.inbuilt_smtp_per_hour emails per hour. You can only change this with your own custom SMTP setup. | +| All endpoints that send One-Time-Passwords (OTP) | `/auth/v1/otp` | Sum of combined requests | Defaults to auth.rate_limits.otp.requests_per_hour OTPs per hour. Is customizable. | +| Send OTPs or magiclinks | `/auth/v1/otp` | Last request | Defaults to auth.rate_limits.otp.period window before a new request is allowed. Is customizable. | +| Signup confirmation request | `/auth/v1/signup` | Last request | Defaults to auth.rate_limits.signup_confirmation.period window before a new request is allowed. Is customizable. | +| Password Reset Request | `/auth/v1/recover` | Last request | Defaults to auth.rate_limits.password_reset.period window before a new request is allowed. Is customizable. | +| Verification requests | `/auth/v1/verify` | IP Address | auth.rate_limits.verification.requests_per_hour requests per hour (with bursts up to auth.rate_limits.verification.requests_burst requests) | +| Token refresh requests | `/auth/v1/token` | IP Address | auth.rate_limits.token_refresh.requests_per_hour requests per hour (with bursts up to auth.rate_limits.token_refresh.requests_burst requests) | +| Create or Verify an MFA challenge | `/auth/v1/factors/:id/challenge` `/auth/v1/factors/:id/verify` | IP Address | auth.rate_limits.mfa.requests_per_hour requests per hour (with bursts up to auth.rate_limits.verification.mfa requests) | +| Anonymous sign-ins | `/auth/v1/signup`[^2] | IP Address | auth.rate_limits.anonymous_signin.requests_per_hour requests per hour (with bursts up to auth.rate_limits.anonymous_signin.requests_burst requests) | + +[^1]: The rate limit is only applied on `/auth/v1/user` if this endpoint is called to update the user's email address. +[^2]: The rate limit is only applied on `/auth/v1/signup` if this endpoint is called without passing in an email or phone number in the request body. diff --git a/apps/docs/content/guides/auth/server-side/oauth-with-pkce-flow-for-ssr.mdx b/apps/docs/components/MDX/oauth_pkce_flow.mdx similarity index 85% rename from apps/docs/content/guides/auth/server-side/oauth-with-pkce-flow-for-ssr.mdx rename to apps/docs/components/MDX/oauth_pkce_flow.mdx index 40af43d1fd..53c03e47c4 100644 --- a/apps/docs/content/guides/auth/server-side/oauth-with-pkce-flow-for-ssr.mdx +++ b/apps/docs/components/MDX/oauth_pkce_flow.mdx @@ -1,16 +1,49 @@ ---- -title: 'OAuth with PKCE flow for SSR' -description: 'Learn how to configure OAuth authentication in your server-side rendering (SSR) application to work with the PKCE flow.' -subtitle: 'Learn how to configure OAuth authentication in your server-side rendering (SSR) application to work with the PKCE flow.' ---- +For a PKCE flow, for example in Server-Side Auth, you need an extra step to handle the code exchange. When calling `signInWithOAuth`, provide a `redirectTo` URL which points to a callback route. This redirect URL should be added to your [redirect allow list](/docs/guides/auth/redirect-urls). -### Setting up SSR client + + -Check out our [guide for creating a client](/docs/guides/auth/server-side/creating-a-client) to learn how to install the necessary packages, declare environment variables, and create a Supabase client configured for SSR in your framework. +In the browser, `signInWithOAuth` automatically redirects to the OAuth provider's authentication endpoint, which then redirects to your endpoint. -### Create API endpoint for handling the `code` exchange +```js +await supabase.auth.signInWithOAuth({ + provider, + options: { + redirectTo: `http://example.com/auth/callback`, + }, +}) +``` -In order to use OAuth we will need to setup a endpoint for the `code` exchange, to exchange an auth `code` for the user's `session`, which is set as a cookie for future requests made to Supabase. + + + + +In the server, you need to handle the redirect to the OAuth provider's authentication endpoint. The `signInWithOAuth` method returns the endpoint URL, which you can redirect to. + +```js +const { data, error } = await supabase.auth.signInWithOAuth({ + provider, + options: { + redirectTo: 'http://example.com/auth/callback', + }, +}) + +if (data.url) { + redirect(data.url) // use the redirect API for your server framework +} +``` + + + + + +At the callback endpoint, handle the code exchange to save the user session. - -Let's point our `.signInWithOAuth` method's redirect to the callback route we create above: - - - - -In the browser, `signInWithOAuth` automatically redirects to the SSO provider's authentication endpoint, which then redirects to your endpoint. - -```js -await supabase.auth.signInWithOAuth({ - provider, - options: { - redirectTo: `http://example.com/auth/callback`, - }, -}) -``` - - - - - -In the server, you need to handle the redirect to the OAuth provider's authentication endpoint. The `signInWithOAuth` method returns the endpoint URL, which you can redirect to. - -```js -const { data, error } = await supabase.auth.signInWithOAuth({ - provider, - options: { - redirectTo: 'http://example.com/auth/callback', - }, -}) - -if (data.url) { - redirect(data.url) // use the redirect API for your server framework -} -``` - - - - diff --git a/apps/docs/components/MDX/user_management_quickstart_sql_template.mdx b/apps/docs/components/MDX/user_management_quickstart_sql_template.mdx index 74129ccf02..28b560e84b 100644 --- a/apps/docs/components/MDX/user_management_quickstart_sql_template.mdx +++ b/apps/docs/components/MDX/user_management_quickstart_sql_template.mdx @@ -11,7 +11,7 @@ create table profiles ( constraint username_length check (char_length(username) >= 3) ); -- Set up Row Level Security (RLS) --- See https://supabase.com/docs/guides/auth/row-level-security for more details. +-- See https://supabase.com/docs/guides/database/postgres/row-level-security for more details. alter table profiles enable row level security; diff --git a/apps/docs/components/Navigation/NavigationMenu/NavigationMenu.constants.ts b/apps/docs/components/Navigation/NavigationMenu/NavigationMenu.constants.ts index 26d333582e..976a4c4eee 100644 --- a/apps/docs/components/Navigation/NavigationMenu/NavigationMenu.constants.ts +++ b/apps/docs/components/Navigation/NavigationMenu/NavigationMenu.constants.ts @@ -471,19 +471,19 @@ export const SocialLoginItems = [ export const PhoneLoginsItems = [ { - name: 'MessageBird SMS Login', + name: 'MessageBird', icon: '/docs/img/icons/messagebird-icon', linkDescription: 'Communication between businesses and their customers — across any channel.', url: '/guides/auth/phone-login/messagebird', }, { - name: 'Twilio SMS Login', + name: 'Twilio', icon: '/docs/img/icons/twilio-icon', url: '/guides/auth/phone-login/twilio', linkDescription: 'Customer engagement platform used by hundreds of thousands of businesses.', }, { - name: 'Vonage SMS Login', + name: 'Vonage', icon: '/docs/img/icons/vonage-icon', url: '/guides/auth/phone-login/vonage', linkDescription: @@ -492,7 +492,7 @@ export const PhoneLoginsItems = [ hasLightIcon: true, }, { - name: 'Textlocal SMS Login (Community Supported)', + name: 'Textlocal (Community Supported)', icon: '/docs/img/icons/textlocal-icon', url: '/guides/auth/phone-login/textlocal', linkDescription: 'Textlocal is a cloud-based SMS platform offering bulk messaging services.', @@ -508,83 +508,71 @@ export const auth = { url: '/guides/auth', }, { - name: 'Redirect URLs', - url: '/guides/auth/concepts/redirect-urls', + name: 'Architecture', + url: '/guides/auth/architecture', }, { - name: 'Quickstarts', + name: 'Getting Started', items: [ - { name: 'Next.js', url: '/guides/auth/quickstarts/nextjs', items: [] }, + { + name: 'Next.js', + url: '/guides/auth/quickstarts/nextjs', + }, { name: 'React', url: '/guides/auth/quickstarts/react', items: [] }, { name: 'React Native', url: '/guides/auth/quickstarts/react-native', - items: [], }, ], }, { - name: 'Authentication', - url: undefined, + name: 'Concepts', items: [ - { name: 'Anonymous Sign-Ins', url: '/guides/auth/auth-anonymous' }, - { name: 'Email Login', url: '/guides/auth/auth-email' }, + { name: 'Users', url: '/guides/auth/users' }, + { name: 'Identities', url: '/guides/auth/identities' }, { - name: 'Passwordless Login', - url: '/guides/auth/passwordless-login', + name: 'Sessions', + url: '/guides/auth/sessions', items: [ - { - name: 'Email Magic Link', - url: '/guides/auth/passwordless-login/auth-magic-link', - }, - { - name: 'Email OTP', - url: '/guides/auth/passwordless-login/auth-email-otp', - }, - { name: 'Phone OTP', url: '/guides/auth/phone-login' }, + { name: 'Implicit flow', url: '/guides/auth/sessions/implicit-flow' }, + { name: 'PKCE flow', url: '/guides/auth/sessions/pkce-flow' }, ], }, + ], + }, + { + name: 'Flows (How-tos)', + items: [ + { + name: 'Server-Side Rendering', + url: '/guides/auth/server-side', + items: [ + { name: 'Next.js guide', url: '/guides/auth/server-side/nextjs' }, + { + name: 'SvelteKit guide', + url: '/guides/auth/server-side/sveltekit', + }, + { name: 'Creating a client', url: '/guides/auth/server-side/creating-a-client' }, + { + name: 'Migrating from Auth Helpers', + url: '/guides/auth/server-side/migrating-to-ssr-from-auth-helpers', + }, + { + name: 'Advanced guide', + url: '/guides/auth/server-side/advanced-guide', + }, + ], + }, + { name: 'Password-based', url: '/guides/auth/passwords' }, + { name: 'Email (Magic Link or OTP)', url: '/guides/auth/auth-email-passwordless' }, { name: 'Phone Login', url: '/guides/auth/phone-login', - items: [...PhoneLoginsItems], }, { name: 'Social Login (OAuth)', url: '/guides/auth/social-login', - items: [ - { - name: 'Native Mobile OAuth', - url: '/guides/auth/native-mobile-deep-linking', - }, - ...SocialLoginItems, - ], - }, - { - name: 'Native Mobile Login', - url: '/guides/auth/native-mobile-login', - items: [ - ...NativeMobileLoginItems, - { - name: 'OAuth Deep Linking', - url: '/guides/auth/native-mobile-deep-linking', - }, - ], - }, - { - name: 'User Sessions', - url: '/guides/auth/sessions', - }, - { name: 'Passwords', url: '/guides/auth/passwords' }, - { - name: 'User Management', - url: '/guides/auth/auth-user-management', - items: [ - { - name: 'Identity Linking', - url: '/guides/auth/auth-identity-linking', - }, - ], + items: [...SocialLoginItems], }, { name: 'Enterprise SSO', @@ -596,57 +584,51 @@ export const auth = { }, ], }, - { name: 'Email Templates', url: '/guides/auth/auth-email-templates' }, - { name: 'Auth Hooks', url: '/guides/auth/auth-hooks' }, + { name: 'Anonymous Sign-Ins', url: '/guides/auth/auth-anonymous' }, + { name: 'Mobile Deep Linking', url: '/guides/auth/native-mobile-deep-linking' }, + { + name: 'Identity Linking', + url: '/guides/auth/auth-identity-linking', + }, + { name: 'Multi-Factor Authentication', url: '/guides/auth/auth-mfa' }, + { + name: 'Signout', + url: '/guides/auth/signout', + }, ], }, { - name: 'Authorization', - url: undefined, + name: 'Configuration', items: [ - { name: 'Enable Captcha Protection', url: '/guides/auth/auth-captcha' }, - { name: 'Configuring Custom SMTP', url: '/guides/auth/auth-smtp' }, - { name: 'Managing User Data', url: '/guides/auth/managing-user-data' }, - { name: 'Multi-Factor Authentication', url: '/guides/auth/auth-mfa' }, - { name: 'Row Level Security', url: '/guides/auth/row-level-security' }, + { + name: 'General Configuration', + url: '/guides/auth/general-configuration', + }, + { name: 'Email Templates', url: '/guides/auth/auth-email-templates' }, + { + name: 'Redirect URLs', + url: '/guides/auth/redirect-urls', + }, + { name: 'Auth Hooks', url: '/guides/auth/auth-hooks' }, + { name: 'Custom SMTP', url: '/guides/auth/auth-smtp' }, + { name: 'User Management', url: '/guides/auth/managing-user-data' }, + ], + }, + { + name: 'Security', + items: [ + { name: 'Password Security', url: '/guides/auth/password-security' }, + { name: 'Rate Limits', url: '/guides/auth/rate-limits' }, + { name: 'Bot Detection (CAPTCHA)', url: '/guides/auth/auth-captcha' }, + { name: 'JWTs', url: '/guides/auth/jwts' }, + { name: 'Row Level Security', url: '/guides/database/postgres/row-level-security' }, + { + name: 'Column Level Security', + url: '/guides/database/postgres/column-level-security', + }, { name: 'Custom Claims & RBAC', - url: '/guides/auth/custom-claims-and-role-based-access-control-rbac', - }, - ], - }, - { - name: 'Server-side Auth', - url: undefined, - items: [ - { name: 'Overview', url: '/guides/auth/server-side/overview' }, - { - name: 'Next.js guide', - url: '/guides/auth/server-side/nextjs', - }, - { - name: 'SvelteKit guide', - url: '/guides/auth/server-side/sveltekit', - }, - { - name: 'Creating a client', - url: '/guides/auth/server-side/creating-a-client', - }, - { - name: 'Email Auth with PKCE flow', - url: '/guides/auth/server-side/email-based-auth-with-pkce-flow-for-ssr', - }, - { - name: 'OAuth with PKCE flow', - url: '/guides/auth/server-side/oauth-with-pkce-flow-for-ssr', - }, - { - name: 'Server-side Rendering', - url: '/guides/auth/server-side-rendering', - }, - { - name: 'Migrating from Auth Helpers', - url: '/guides/auth/server-side/migrating-to-ssr-from-auth-helpers', + url: '/guides/database/postgres/custom-claims-and-role-based-access-control-rbac', }, ], }, @@ -661,29 +643,6 @@ export const auth = { }, ], }, - { - name: 'Deep Dive', - url: undefined, - items: [ - { - name: 'Part One: JWTs', - url: '/guides/auth/auth-deep-dive/auth-deep-dive-jwts', - }, - { - name: 'Part Two: Row Level Security', - url: '/guides/auth/auth-deep-dive/auth-row-level-security', - }, - { - name: 'Part Three: Policies', - url: '/guides/auth/auth-deep-dive/auth-policies', - }, - { name: 'Part Four: GoTrue', url: '/guides/auth/auth-deep-dive/auth-gotrue' }, - { - name: 'Part Five: Google OAuth', - url: '/guides/auth/auth-deep-dive/auth-google-oauth', - }, - ], - }, ], } @@ -770,6 +729,14 @@ export const database: NavMenuConstant = { name: 'Row Level Security', url: '/guides/database/postgres/row-level-security', }, + { + name: 'Column Level Security', + url: '/guides/database/postgres/column-level-security', + }, + { + name: 'Custom Claims & RBAC', + url: '/guides/database/postgres/custom-claims-and-role-based-access-control-rbac', + }, { name: 'Managing Postgres Roles', url: '/guides/database/postgres/roles', diff --git a/apps/docs/components/Navigation/NavigationMenu/TopNavBar.tsx b/apps/docs/components/Navigation/NavigationMenu/TopNavBar.tsx index ad1a9bdec4..7be6e32626 100644 --- a/apps/docs/components/Navigation/NavigationMenu/TopNavBar.tsx +++ b/apps/docs/components/Navigation/NavigationMenu/TopNavBar.tsx @@ -15,7 +15,7 @@ const TopNavBar: FC = () => { return (