Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion apps/docs/content/guides/auth/social-login/auth-google.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -712,7 +712,7 @@ val supabaseClient = createSupabaseClient(
**Use the Compose Auth plugin in your Auth Screen**

```kotlin
val authState = supabaseClient.composeAuth.rememberLoginWithGoogle(
val authState = supabaseClient.composeAuth.rememberSignInWithGoogle(
onResult = {
when(it) { //handle errors
NativeSignInResult.ClosedByUser -> TODO()
Expand Down
5 changes: 4 additions & 1 deletion apps/docs/spec/api_v1_openapi.json
Original file line number Diff line number Diff line change
Expand Up @@ -4950,7 +4950,10 @@
"items": {
"type": "object",
"properties": {
"postgres_version": { "type": "string", "enum": ["15", "17", "17-oriole"] },
"postgres_version": {
"type": "string",
"enum": ["13", "14", "15", "17", "17-oriole"]
},
"release_channel": {
"type": "string",
"enum": ["internal", "alpha", "beta", "ga", "withdrawn", "preview"]
Expand Down
2 changes: 1 addition & 1 deletion apps/docs/spec/cli_v1_commands.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@ flags:
name: --workdir <string>
description: path to a Supabase project directory
default_value: ''
- id: "yes"
- id: 'yes'
name: --yes
description: answer yes to all prompts
default_value: 'false'
Expand Down
12 changes: 10 additions & 2 deletions apps/docs/spec/supabase_js_v2.yml
Original file line number Diff line number Diff line change
Expand Up @@ -1095,7 +1095,15 @@ functions:
title: 'verifyOtp()'
$ref: '@supabase/auth-js.GoTrueClient.verifyOtp'
notes: |
- 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: `email`, `recovery`, `invite` or `email_change` (`signup` and `magiclink` types are deprecated).
- The `verifyOtp` method takes in different verification types.
- If a phone number is used, the type can either be:
1. `sms` – Used when verifying a one-time password (OTP) sent via SMS during sign-up or sign-in.
2. `phone_change` – Used when verifying an OTP sent to a new phone number during a phone number update process.
- If an email address is used, the type can be one of the following (note: `signup` and `magiclink` types are deprecated):
1. `email` – Used when verifying an OTP sent to the user's email during sign-up or sign-in.
2. `recovery` – Used when verifying an OTP sent for account recovery, typically after a password reset request.
3. `invite` – Used when verifying an OTP sent as part of an invitation to join a project or organization.
4. `email_change` – Used when verifying an OTP sent to a new email address during an email update process.
- The verification type used should be determined based on the corresponding auth method called before `verifyOtp` to sign up / sign-in a user.
- The `TokenHash` is contained in the [email templates](/docs/guides/auth/auth-email-templates) and can be used to sign in. You may wish to use the hash with Magic Links for the PKCE flow for Server Side Auth. See [this guide](/docs/guides/auth/server-side/email-based-auth-with-pkce-flow-for-ssr) for more details.
examples:
Expand Down Expand Up @@ -1653,7 +1661,7 @@ functions:
- Resends a signup confirmation, email change or phone change email to the user.
- Passwordless sign-ins can be resent by calling the `signInWithOtp()` method again.
- Password recovery emails can be resent by calling the `resetPasswordForEmail()` method again.
- This method will only resend an email or phone OTP to the user if there was an initial signup, email change or phone change request being made.
- This method will only resend an email or phone OTP to the user if there was an initial signup, email change or phone change request being made(note: For existing users signing in with OTP, you should use `signInWithOtp()` again to resend the OTP).
- You can specify a redirect url when you resend an email link using the `emailRedirectTo` option.
examples:
- id: resend-email-signup-confirmation
Expand Down
4 changes: 2 additions & 2 deletions apps/docs/spec/transforms/api_v1_openapi_deparsed.json
Original file line number Diff line number Diff line change
Expand Up @@ -4935,7 +4935,7 @@
"properties": {
"postgres_version": {
"type": "string",
"enum": ["15", "17", "17-oriole"]
"enum": ["13", "14", "15", "17", "17-oriole"]
},
"release_channel": {
"type": "string",
Expand Down Expand Up @@ -15541,7 +15541,7 @@
"properties": {
"postgres_version": {
"type": "string",
"enum": ["15", "17", "17-oriole"]
"enum": ["13", "14", "15", "17", "17-oriole"]
},
"release_channel": {
"type": "string",
Expand Down
84 changes: 40 additions & 44 deletions apps/studio/components/interfaces/Database/Hooks/EditHookPanel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -42,12 +42,48 @@ export const EditHookPanel = ({ visible, selectedHook, onClose }: EditHookPanelP

// [Joshen] There seems to be some bug between Checkbox.Group within the Form component
// hence why this external state as a temporary workaround
const [events, setEvents] = useState<string[]>([])
const [events, setEvents] = useState<string[]>(selectedHook?.events ?? [])
const [eventsError, setEventsError] = useState<string>()

// For HTTP request
const [httpHeaders, setHttpHeaders] = useState<HTTPArgument[]>([])
const [httpParameters, setHttpParameters] = useState<HTTPArgument[]>([])
const [httpHeaders, setHttpHeaders] = useState<HTTPArgument[]>(() => {
if (typeof selectedHook === `undefined`) {
return [{ id: uuidv4(), name: 'Content-type', value: 'application/json' }]
}
const [_, __, headers] = selectedHook.function_args
let parsedHeaders: Record<string, string> = {}

try {
parsedHeaders = JSON.parse(headers.replace(/\\"/g, '"'))
} catch (e) {
parsedHeaders = {}
}

return Object.entries(parsedHeaders).map(([name, value]) => ({
id: uuidv4(),
name,
value,
}))
})
const [httpParameters, setHttpParameters] = useState<HTTPArgument[]>(() => {
if (typeof selectedHook === `undefined`) {
return [{ id: uuidv4(), name: '', value: '' }]
}
const [_, __, ___, parameters] = selectedHook.function_args
let parsedParameters: Record<string, string> = {}

try {
parsedParameters = JSON.parse(parameters.replace(/\\"/g, '"'))
} catch (e) {
parsedParameters = {}
}

return Object.entries(parsedParameters).map(([name, value]) => ({
id: uuidv4(),
name,
value,
}))
})

const { project } = useProjectContext()
const { data } = useTablesQuery({
Expand Down Expand Up @@ -100,48 +136,8 @@ export const EditHookPanel = ({ visible, selectedHook, onClose }: EditHookPanelP
if (visible) {
setIsEdited(false)
setIsClosingPanel(false)

if (selectedHook !== undefined) {
setEvents(selectedHook.events)

const [_, __, headers, parameters] = selectedHook.function_args

let parsedParameters: Record<string, string> = {}

// Try to parse the parameters with escaped quotes
try {
parsedParameters = JSON.parse(parameters.replace(/\\"/g, '"'))
} catch (e) {
// If parsing still fails, fallback to an empty object
parsedParameters = {}
}

let parsedHeaders: Record<string, string> = {}
try {
parsedHeaders = JSON.parse(headers.replace(/\\"/g, '"'))
} catch (e) {
// If parsing still fails, fallback to an empty object
parsedHeaders = {}
}

setHttpHeaders(
Object.keys(parsedHeaders).map((key) => {
return { id: uuidv4(), name: key, value: parsedHeaders[key] }
})
)

setHttpParameters(
Object.keys(parsedParameters).map((key) => {
return { id: uuidv4(), name: key, value: parsedParameters[key] }
})
)
} else {
setEvents([])
setHttpHeaders([{ id: uuidv4(), name: 'Content-type', value: 'application/json' }])
setHttpParameters([{ id: uuidv4(), name: '', value: '' }])
}
}
}, [visible, selectedHook])
}, [visible])

const onClosePanel = () => {
if (isEdited) setIsClosingPanel(true)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ export const WebhooksListTab = () => {
<div className="p-10">
<HooksList createHook={createHook} editHook={editHook} deleteHook={deleteHook} />
<EditHookPanel
key={selectedHook?.id}
visible={showCreateHookForm}
selectedHook={selectedHook}
onClose={() => setShowCreateHookForm(false)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,14 @@ const EntityListItem: ItemRenderer<Entity, EntityListItemProps> = ({
selectedSchema
).hasLint

const foreignTableHasLints: boolean = getEntityLintDetails(
entity.name,
'foreign_table_in_api',
['ERROR', 'WARN'],
lints,
selectedSchema
).hasLint

const formatTooltipText = (entityType: string) => {
return Object.entries(ENTITY_TYPE)
.find(([, value]) => value === entityType)?.[0]
Expand Down Expand Up @@ -270,6 +278,7 @@ const EntityListItem: ItemRenderer<Entity, EntityListItemProps> = ({
tableHasLints={tableHasLints}
viewHasLints={viewHasLints}
materializedViewHasLints={materializedViewHasLints}
foreignTableHasLints={foreignTableHasLints}
/>
</div>
</div>
Expand Down Expand Up @@ -427,11 +436,13 @@ const EntityTooltipTrigger = ({
tableHasLints,
viewHasLints,
materializedViewHasLints,
foreignTableHasLints,
}: {
entity: Entity
tableHasLints: boolean
viewHasLints: boolean
materializedViewHasLints: boolean
foreignTableHasLints: boolean
}) => {
let tooltipContent = ''
const accessWarning = 'Data is publicly accessible via API'
Expand All @@ -453,7 +464,9 @@ const EntityTooltipTrigger = ({
}
break
case ENTITY_TYPE.FOREIGN_TABLE:
tooltipContent = `${accessWarning} as RLS via is not enforced on foreign tables`
if (foreignTableHasLints) {
tooltipContent = `${accessWarning} as RLS is not enforced on foreign tables`
}
break
default:
break
Expand Down
Loading