mirror of
https://github.com/supabase/supabase.git
synced 2026-07-07 11:40:20 +08:00
Begin the process of moving our MDX files into their own content directory. Fixed a few minor bugs re: ToC and tabs not rerendering consistently on page navigation. (The ToC thing wasn't a problem before the refactor, the tabs thing is a problem on prod.) Moved MDX files can't import their own components, so everything they require needs to be back in the component prop for mdx-remote's serializer. Cleaned this up a bit and lazy-loaded heavy/rare stuff. Also, the component prop doesn't take arbitrary objects (only actual components), so imported data has to be wrapped in a component.
269 lines
7.6 KiB
Plaintext
269 lines
7.6 KiB
Plaintext
---
|
|
title: 'Use Supabase Auth with React Native'
|
|
subtitle: 'Learn how to use Supabase Auth with React Native'
|
|
breadcrumb: 'Auth Quickstarts'
|
|
hideToc: true
|
|
---
|
|
|
|
<StepHikeCompact>
|
|
|
|
<StepHikeCompact.Step step={1}>
|
|
<StepHikeCompact.Details title="Create a new Supabase project">
|
|
|
|
[Launch a new project](https://supabase.com/dashboard) in the Supabase Dashboard.
|
|
|
|
Your new database has a table for storing your users. You can see that this table is currently empty by running some SQL in the [SQL Editor](https://supabase.com/dashboard/project/_/sql).
|
|
|
|
</StepHikeCompact.Details>
|
|
|
|
<StepHikeCompact.Code>
|
|
|
|
```sql SQL_EDITOR
|
|
select * from auth.users;
|
|
````
|
|
|
|
</StepHikeCompact.Code>
|
|
|
|
</StepHikeCompact.Step>
|
|
|
|
<StepHikeCompact.Step step={2}>
|
|
|
|
<StepHikeCompact.Details title="Create a React app">
|
|
|
|
Create a React app using the `create-expo-app` command.
|
|
|
|
</StepHikeCompact.Details>
|
|
|
|
<StepHikeCompact.Code>
|
|
|
|
```bash Terminal
|
|
npx create-expo-app -t expo-template-blank-typescript my-app
|
|
```
|
|
|
|
</StepHikeCompact.Code>
|
|
|
|
</StepHikeCompact.Step>
|
|
|
|
<StepHikeCompact.Step step={3}>
|
|
<StepHikeCompact.Details title="Install the Supabase client library">
|
|
|
|
Install `supabase-js` and the required dependencies.
|
|
|
|
</StepHikeCompact.Details>
|
|
|
|
<StepHikeCompact.Code>
|
|
|
|
```bash Terminal
|
|
cd my-app && npx expo install @supabase/supabase-js @react-native-async-storage/async-storage react-native-elements react-native-url-polyfill
|
|
```
|
|
|
|
</StepHikeCompact.Code>
|
|
|
|
</StepHikeCompact.Step>
|
|
|
|
<StepHikeCompact.Step step={4}>
|
|
<StepHikeCompact.Details title="Set up your login component">
|
|
|
|
Create a helper file `lib/supabase.ts` that exports a Supabase client using your [Project URL and public API (anon) key](https://supabase.com/dashboard/project/_/settings/api).
|
|
|
|
</StepHikeCompact.Details>
|
|
<StepHikeCompact.Code>
|
|
|
|
|
|
```ts lib/supabase.ts
|
|
import { AppState } from 'react-native'
|
|
import 'react-native-url-polyfill/auto'
|
|
import AsyncStorage from '@react-native-async-storage/async-storage'
|
|
import { createClient } from '@supabase/supabase-js'
|
|
|
|
const supabaseUrl = YOUR_REACT_NATIVE_SUPABASE_URL
|
|
const supabaseAnonKey = YOUR_REACT_NATIVE_SUPABASE_ANON_KEY
|
|
|
|
export const supabase = createClient(supabaseUrl, supabaseAnonKey, {
|
|
auth: {
|
|
storage: AsyncStorage,
|
|
autoRefreshToken: true,
|
|
persistSession: true,
|
|
detectSessionInUrl: false,
|
|
},
|
|
})
|
|
|
|
// Tells Supabase Auth to continuously refresh the session automatically
|
|
// if the app is in the foreground. When this is added, you will continue
|
|
// to receive `onAuthStateChange` events with the `TOKEN_REFRESHED` or
|
|
// `SIGNED_OUT` event if the user's session is terminated. This should
|
|
// only be registered once.
|
|
AppState.addEventListener('change', (state) => {
|
|
if (state === 'active') {
|
|
supabase.auth.startAutoRefresh()
|
|
} else {
|
|
supabase.auth.stopAutoRefresh()
|
|
}
|
|
})
|
|
```
|
|
|
|
</StepHikeCompact.Code>
|
|
|
|
</StepHikeCompact.Step>
|
|
|
|
<StepHikeCompact.Step step={5}>
|
|
<StepHikeCompact.Details title="Create a login component">
|
|
|
|
Let's set up a React Native component to manage logins and sign ups.
|
|
|
|
</StepHikeCompact.Details>
|
|
|
|
<StepHikeCompact.Code>
|
|
|
|
```tsx components/Auth.tsx
|
|
import React, { useState } from 'react'
|
|
import { Alert, StyleSheet, View } from 'react-native'
|
|
import { supabase } from '../lib/supabase'
|
|
import { Button, Input } from 'react-native-elements'
|
|
|
|
export default function Auth() {
|
|
const [email, setEmail] = useState('')
|
|
const [password, setPassword] = useState('')
|
|
const [loading, setLoading] = useState(false)
|
|
|
|
async function signInWithEmail() {
|
|
setLoading(true)
|
|
const { error } = await supabase.auth.signInWithPassword({
|
|
email: email,
|
|
password: password,
|
|
})
|
|
|
|
if (error) Alert.alert(error.message)
|
|
setLoading(false)
|
|
}
|
|
|
|
async function signUpWithEmail() {
|
|
setLoading(true)
|
|
const {
|
|
data: { session },
|
|
error,
|
|
} = await supabase.auth.signUp({
|
|
email: email,
|
|
password: password,
|
|
})
|
|
|
|
if (error) Alert.alert(error.message)
|
|
if (!session) Alert.alert('Please check your inbox for email verification!')
|
|
setLoading(false)
|
|
}
|
|
|
|
return (
|
|
<View style={styles.container}>
|
|
<View style={[styles.verticallySpaced, styles.mt20]}>
|
|
<Input
|
|
label="Email"
|
|
leftIcon={{ type: 'font-awesome', name: 'envelope' }}
|
|
onChangeText={(text) => setEmail(text)}
|
|
value={email}
|
|
placeholder="email@address.com"
|
|
autoCapitalize={'none'}
|
|
/>
|
|
</View>
|
|
<View style={styles.verticallySpaced}>
|
|
<Input
|
|
label="Password"
|
|
leftIcon={{ type: 'font-awesome', name: 'lock' }}
|
|
onChangeText={(text) => setPassword(text)}
|
|
value={password}
|
|
secureTextEntry={true}
|
|
placeholder="Password"
|
|
autoCapitalize={'none'}
|
|
/>
|
|
</View>
|
|
<View style={[styles.verticallySpaced, styles.mt20]}>
|
|
<Button title="Sign in" disabled={loading} onPress={() => signInWithEmail()} />
|
|
</View>
|
|
<View style={styles.verticallySpaced}>
|
|
<Button title="Sign up" disabled={loading} onPress={() => signUpWithEmail()} />
|
|
</View>
|
|
</View>
|
|
)
|
|
}
|
|
|
|
const styles = StyleSheet.create({
|
|
container: {
|
|
marginTop: 40,
|
|
padding: 12,
|
|
},
|
|
verticallySpaced: {
|
|
paddingTop: 4,
|
|
paddingBottom: 4,
|
|
alignSelf: 'stretch',
|
|
},
|
|
mt20: {
|
|
marginTop: 20,
|
|
},
|
|
})
|
|
```
|
|
|
|
</StepHikeCompact.Code>
|
|
|
|
</StepHikeCompact.Step>
|
|
|
|
<StepHikeCompact.Step step={6}>
|
|
<StepHikeCompact.Details title="Add the Auth component to your app">
|
|
|
|
Add the `Auth` component to your `App.tsx` file. If the user is logged in, print the user id to the screen.
|
|
|
|
</StepHikeCompact.Details>
|
|
|
|
<StepHikeCompact.Code>
|
|
|
|
```tsx App.tsx
|
|
import 'react-native-url-polyfill/auto'
|
|
import { useState, useEffect } from 'react'
|
|
import { supabase } from './lib/supabase'
|
|
import Auth from './components/Auth'
|
|
import Account from './components/Account'
|
|
import { View, Text } from 'react-native'
|
|
import { Session } from '@supabase/supabase-js'
|
|
|
|
export default function App() {
|
|
const [session, setSession] = useState<Session | null>(null)
|
|
|
|
useEffect(() => {
|
|
supabase.auth.getSession().then(({ data: { session } }) => {
|
|
setSession(session)
|
|
})
|
|
|
|
supabase.auth.onAuthStateChange((_event, session) => {
|
|
setSession(session)
|
|
})
|
|
}, [])
|
|
|
|
return (
|
|
<View>
|
|
<Auth />
|
|
{session && session.user && <Text>{session.user.id}</Text>}
|
|
</View>
|
|
)
|
|
}
|
|
```
|
|
|
|
</StepHikeCompact.Code>
|
|
|
|
</StepHikeCompact.Step>
|
|
|
|
<StepHikeCompact.Step step={7}>
|
|
<StepHikeCompact.Details title="Start the app">
|
|
|
|
Start the app, and follow the instructions in the terminal.
|
|
|
|
</StepHikeCompact.Details>
|
|
|
|
<StepHikeCompact.Code>
|
|
|
|
```bash Terminal
|
|
npm start
|
|
```
|
|
|
|
</StepHikeCompact.Code>
|
|
|
|
</StepHikeCompact.Step>
|
|
</StepHikeCompact>
|