Skip to content

Commit

Permalink
Merge branch 'main' into tobbe-auth-method-option-types
Browse files Browse the repository at this point in the history
  • Loading branch information
Tobbe authored Mar 4, 2023
2 parents b5180cc + bc5b3e5 commit 880069a
Show file tree
Hide file tree
Showing 10 changed files with 1,866 additions and 1,165 deletions.
216 changes: 210 additions & 6 deletions docs/docs/auth/supabase.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ yarn rw setup auth supabase
This installs all the packages, writes all the files, and makes all the code modifications you need.
For a detailed explanation of all the api- and web-side changes that aren't exclusive to Supabase, see the top-level [Authentication](../authentication.md) doc. For now, let's focus on Supabase's side of things.

## Setup

If you don't have a Supabase account yet, now's the time to make one: navigate to https://supabase.com and click "Start your project" in the top right. Then sign up and create an organization and a project.

While Supabase creates your project, it thoughtfully shows your project's API keys.
Expand Down Expand Up @@ -42,8 +44,23 @@ Lastly, in `redwood.toml`, include `SUPABASE_URL` and `SUPABASE_KEY` in the list
includeEnvironmentVariables = ["SUPABASE_URL", "SUPABASE_KEY"]
```

That should be enough; now, things should just work.


## Authentication UI

Supabase doesn't redirect to a hosted sign-up page or open a sign-up modal.
In a real app, you'd build a form here, but we're going to hardcode an email and password.

### Basic Example

After you sign up, head to your inbox: there should be a confirmation email from Supabase waiting for you.

Click the link, then head back to your app.
Once you refresh the page, you should see `{"isAuthenticated":true}` on the page.


Let's make sure: if this is a brand new project, generate a home page.

There we'll try to sign up by destructuring `signUp` from the `useAuth` hook (import that from `'src/auth'`). We'll also destructure and display `isAuthenticated` to see if it worked:

```tsx title="web/src/pages/HomePage.tsx"
Expand All @@ -66,8 +83,195 @@ const HomePage = () => {
}
```

Supabase doesn't redirect to a hosted sign-up page or open a sign-up modal.
In a real app, you'd build a form here, but we're going to hardcode an email and password.
After you sign up, head to your inbox: there should be a confirmation email from Supabase waiting for you.
Click the link, then head back to your app.
Once you refresh the page, you should see `{"isAuthenticated":true}` on the page.
## Authentication Reference

You will notice that [Supabase Javascript SDK Auth API](https://supabase.com/docs/reference/javascript/auth-api) reference documentation presents methods to sign in with the various integrations Supabase supports: password, OAuth, IDToken, SSO, etc.

The RedwoodJS implementation of Supabase authentication supports these as well, but within the `logIn` method of the `useAuth` hook.

That means that you will see that Supabase documents sign in with email password as:

```ts
const { data, error } = await supabase.auth.signInWithPassword({
email: 'example@email.com',
password: 'example-password',
})
```

In RedwoodJS, you will always use `logIn` and pass the necessary credential options and also an `authenticationMethod` to declare how you want to authenticate.

```ts
const { logIn } = useAuth()

await logIn({
authenticationMethod: 'password',
email: 'example@email.com',
password: 'example-password',
})
```

### Sign Up with email and password

Creates a new user.

```ts
const { signUp } = useAuth()

await signUp({
email: 'example@email.com',
password: 'example-password',
})
```

### Sign in a user with email and password

Log in an existing user with an email and password or phone and password.

* Requires either an email and password or a phone number and password.

```ts
const { logIn } = useAuth()

await logIn({
authenticationMethod: 'password',
email: 'example@email.com',
password: 'example-password',
})
```

### Sign in a user through Passwordless/OTP

Log in a user using magiclink or a one-time password (OTP).

* Requires either an email or phone number.

* This method is used for passwordless sign-ins where a OTP is sent to the user's email or phone number.

```ts
const { logIn } = useAuth()

await logIn({
authenticationMethod: 'otp',
email: 'example@email.com',
options: {
emailRedirectTo: 'https://example.com/welcome'
}
})
```

### Sign in a user through OAuth

Log in an existing user via a third-party provider.

* This method is used for signing in using a third-party provider.

* Supabase supports many different [third-party providers](https://supabase.com/docs/guides/auth#providers).

```ts
const { logIn } = useAuth()

await logIn({
authenticationMethod: 'otp',
email: 'example@email.com',
options: {
emailRedirectTo: 'https://example.com/welcome'
}
})
```

### Sign in a user with IDToken

Log in a user using IDToken.

```ts
const { logIn } = useAuth()

await logIn({
authenticationMethod: 'id_token',
provider: 'apple',
token: 'cortland-apple-id-token',
})
```

### Sign in a user with SSO

Log in a user using IDToken.

```ts
const { logIn } = useAuth()

await logIn({
authenticationMethod: 'sso',
providerId: 'sso-provider-identity-uuid',
domain: 'example.com',
})
```

### Sign out a user

Inside a browser context, signOut() will remove the logged in user from the browser session and log them out - removing all items from localStorage and then trigger a "SIGNED_OUT" event.

In order to use the signOut() method, the user needs to be signed in first.

```ts
const { logOut } = useAuth()

logOut()
```


### Verify and log in through OTP

Log in a user given a User supplied OTP received via mobile.

* The verifyOtp method takes in different verification types. If a phone number is used, the type can either be sms or phone_change. If an email address is used, the type can be one of the following: signup, magiclink, recovery, invite or email_change.

* The verification type used should be determined based on the corresponding auth method called before verifyOtp to sign up / sign-in a user.


The RedwoodJS auth provider doesn't expose the `veriftyOtp` method from the Supabase SDK directly.

Instead, since you always have access the the Supabase Auth client, you can access any method it exposes.

So, in order to use the `verifyOtp` method, you would:

```ts
const { client } = useAuth()

const { data, error } = await client.verifyOtp({ phone, token, type: 'sms'})
```

### Access the Supabase Auth Client

Sometimes you may need to access the Supabase Auth client directly.

```ts
const { client } = useAuth()
```

You can then use it to work with Supabase sessions, or auth events.


### Retrieve a session

Returns the session, refreshing it if necessary. The session returned can be null if the session is not detected which can happen in the event a user is not signed-in or has logged out.

```ts
const { client } = useAuth()

const { data, error } = await client.getSession()
```

### Listen to auth events

Receive a notification every time an auth event happens.

* Types of auth events: `SIGNED_IN`, `SIGNED_OUT`, `TOKEN_REFRESHED`, `USER_UPDATED`, `PASSWORD_RECOVERY`

```ts
const { client } = useAuth()

client.onAuthStateChange((event, session) => {
console.log(event, session)
})
```
2 changes: 1 addition & 1 deletion docs/docs/typescript/utility-types.md
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,7 @@ It takes three generic parameters:
|:--------|:---------------------------------------------------------------------------------|
| `TData` | The Prisma model that'll be returned |
| `TName` | (Optional) the name of the model. ("post" in the example below) |
| `TKeys` | (optional) the keys(s) used to define the scenario. ("one" in the example below) |
| `TKeys` | (optional) the key(s) used to define the scenario. ("one" in the example below) |

We know this is a lot of generics, but that's so you get to choose how specific you want to be with the types!

Expand Down
6 changes: 3 additions & 3 deletions docs/yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -4636,11 +4636,11 @@ __metadata:
linkType: hard

"dns-packet@npm:^5.2.2":
version: 5.3.1
resolution: "dns-packet@npm:5.3.1"
version: 5.4.0
resolution: "dns-packet@npm:5.4.0"
dependencies:
"@leichtgewicht/ip-codec": ^2.0.1
checksum: 5e74ccd47437f936b81c1d93363c2a57ce78374159ea4893435b95961f09685adb048f72e6e09fcc5c38a08550e20b67dfbbd7c7fd9c2c9f24c8cf88c592fe46
checksum: bd5ecfd7d8b9cacd4d0029819699051c4e231d8fa6ed96e1573f7fee4b9147c3406207a260adbd7fb5c6d08a7db7641836467f450fa88e2ec5075f482e39ed77
languageName: node
linkType: hard

Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@
"@babel/runtime-corejs3": "7.21.0",
"@npmcli/arborist": "6.2.4",
"@nrwl/nx-cloud": "15.1.1",
"@playwright/test": "1.31.1",
"@playwright/test": "1.31.2",
"@replayio/playwright": "0.3.24",
"@testing-library/jest-dom": "5.16.5",
"@testing-library/react": "14.0.0",
Expand Down
4 changes: 2 additions & 2 deletions packages/auth-providers/firebase/web/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,13 +30,13 @@
"@babel/cli": "7.21.0",
"@babel/core": "7.21.0",
"@types/react": "18.0.28",
"firebase": "9.17.1",
"firebase": "9.17.2",
"jest": "29.4.3",
"react": "18.2.0",
"typescript": "4.9.5"
},
"peerDependencies": {
"firebase": "9.17.1"
"firebase": "9.17.2"
},
"gitHead": "3905ed045508b861b495f8d5630d76c7a157d8f1"
}
2 changes: 1 addition & 1 deletion packages/auth-providers/supabase/setup/src/setupHandler.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ export const handler = async ({ force: forceArg }: Args) => {
apiPackages: [`@redwoodjs/auth-supabase-api@${version}`],
webPackages: [
`@redwoodjs/auth-supabase-web@${version}`,
'@supabase/supabase-js@^1',
'@supabase/supabase-js@^2',
],
notes: [
"You'll need to add two env vars to your .env file:",
Expand Down
4 changes: 2 additions & 2 deletions packages/auth-providers/supabase/web/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,14 @@
"devDependencies": {
"@babel/cli": "7.21.0",
"@babel/core": "7.21.0",
"@supabase/supabase-js": "1.35.7",
"@supabase/supabase-js": "2.8.0",
"@types/react": "18.0.28",
"jest": "29.4.3",
"react": "18.2.0",
"typescript": "4.9.5"
},
"peerDependencies": {
"@supabase/supabase-js": "1.35.7"
"@supabase/supabase-js": "2.8.0"
},
"gitHead": "3905ed045508b861b495f8d5630d76c7a157d8f1"
}
Loading

0 comments on commit 880069a

Please sign in to comment.