From 3ea6fcae90aca8876ca9ba178267909bc23eb645 Mon Sep 17 00:00:00 2001
From: Danny White <3104761+dnywh@users.noreply.github.com>
Date: Mon, 15 Jun 2026 21:40:52 -0600
Subject: [PATCH 001/488] chore(studio): remove unused API authorization layout
(#46962)
## What kind of change does this PR introduce?
Code cleanup. Resolves DEPR-570.
## What is the current behavior?
The old `APIAuthorizationLayout` component still exists in Studio even
though the API/OAuth, CLI, Stripe, invite, credits, and AWS connect
surfaces have moved onto the shared interstitial layout.
## What is the new behavior?
Removes the unused `APIAuthorizationLayout` component.
`IntegrationWindowLayout` and `VercelIntegrationWindowLayout` are still
required for upcoming Vercel connection UI clean up work.
## Summary by CodeRabbit
* **Refactor**
* Removed unused layout component from the API authorization flow,
streamlining the codebase and improving maintainability.
---
.../layouts/APIAuthorizationLayout.tsx | 57 -------------------
1 file changed, 57 deletions(-)
delete mode 100644 apps/studio/components/layouts/APIAuthorizationLayout.tsx
diff --git a/apps/studio/components/layouts/APIAuthorizationLayout.tsx b/apps/studio/components/layouts/APIAuthorizationLayout.tsx
deleted file mode 100644
index cbd890004c0..00000000000
--- a/apps/studio/components/layouts/APIAuthorizationLayout.tsx
+++ /dev/null
@@ -1,57 +0,0 @@
-import { useTheme } from 'next-themes'
-import Image from 'next/legacy/image'
-import Link from 'next/link'
-import type { PropsWithChildren } from 'react'
-import { Separator } from 'ui'
-
-import { Head, type HeadProvider } from '@/components/ui/Head'
-import { useCustomContent } from '@/hooks/custom-content/useCustomContent'
-import { BASE_PATH } from '@/lib/constants'
-
-export interface APIAuthorizationLayoutProps {
- HeadProvider: HeadProvider
-}
-
-export const APIAuthorizationLayout = ({
- HeadProvider,
- children,
-}: PropsWithChildren) => {
- const { resolvedTheme } = useTheme()
- const { appTitle } = useCustomContent(['app:title'])
-
- return (
- <>
-
-
-
- The destination type cannot be changed after creation.
-
-
-
+
+ This destination type is in alpha and may change while we iterate.{' '}
+
+ Leave feedback
+
+
+ )
+ }
+ >
-
- {selectedOption?.isAlpha && (
-
- This destination type is in alpha and may change while we iterate.{' '}
-
- Leave feedback
-
-
- )}
-
+
)
}
diff --git a/apps/studio/data/replication/validate-destination-mutation.ts b/apps/studio/data/replication/validate-destination-mutation.ts
index 1bd7aeaecd0..848879e6e50 100644
--- a/apps/studio/data/replication/validate-destination-mutation.ts
+++ b/apps/studio/data/replication/validate-destination-mutation.ts
@@ -8,13 +8,28 @@ import type { ResponseError, UseCustomMutationOptions } from '@/types'
type ValidateDestinationParams = {
projectRef: string
destinationConfig: DestinationConfig
+ sourceId?: number
+ publicationName?: string
+ maxFillMs?: number
+ maxTableSyncWorkers?: number
+ maxCopyConnectionsPerTable?: number
+ invalidatedSlotBehavior?: 'error' | 'recreate'
}
type ValidateDestinationResponse = components['schemas']['ValidateDestinationResponse']
export type ValidationFailure = ValidateDestinationResponse['validation_failures'][number]
async function validateDestination(
- { projectRef, destinationConfig }: ValidateDestinationParams,
+ {
+ projectRef,
+ destinationConfig,
+ sourceId,
+ publicationName,
+ maxFillMs,
+ maxTableSyncWorkers,
+ maxCopyConnectionsPerTable,
+ invalidatedSlotBehavior,
+ }: ValidateDestinationParams,
signal?: AbortSignal
): Promise {
if (!projectRef) throw new Error('projectRef is required')
@@ -108,9 +123,25 @@ async function validateDestination(
)
}
+ const batchConfig = maxFillMs !== undefined ? { max_fill_ms: maxFillMs } : undefined
+ const pipelineConfig =
+ publicationName === undefined
+ ? undefined
+ : {
+ publication_name: publicationName,
+ max_table_sync_workers: maxTableSyncWorkers,
+ max_copy_connections_per_table: maxCopyConnectionsPerTable,
+ invalidated_slot_behavior: invalidatedSlotBehavior,
+ batch: batchConfig,
+ }
+
const { data, error } = await post('/platform/replication/{ref}/destinations/validate', {
params: { path: { ref: projectRef } },
- body: { config },
+ body: {
+ config,
+ source_id: sourceId,
+ pipeline_config: pipelineConfig,
+ },
signal,
})
diff --git a/packages/api-types/types/platform.d.ts b/packages/api-types/types/platform.d.ts
index 1c0146a8ea0..71533fadd4a 100644
--- a/packages/api-types/types/platform.d.ts
+++ b/packages/api-types/types/platform.d.ts
@@ -12818,6 +12818,37 @@ export interface components {
user: string
}
}
+ /** @description Pipeline configuration */
+ pipeline_config?: {
+ /** @description Batch configuration */
+ batch?: {
+ /**
+ * @description Maximum fill time in milliseconds
+ * @example 200
+ */
+ max_fill_ms?: number
+ }
+ /**
+ * @description Behavior when the replication slot is invalidated
+ * @example error
+ * @enum {string}
+ */
+ invalidated_slot_behavior?: 'error' | 'recreate'
+ /** @description Maximum number of copy connections per table */
+ max_copy_connections_per_table?: number
+ /** @description Maximum number of table sync workers */
+ max_table_sync_workers?: number
+ /**
+ * @description Publication name
+ * @example pub_orders
+ */
+ publication_name: string
+ }
+ /**
+ * @description Source id
+ * @example 1
+ */
+ source_id?: number
}
ValidateReplicationPipelineBody: {
/** @description Pipeline configuration */
From 42ca11f89e7649402a303fd561bddaa9982c4107 Mon Sep 17 00:00:00 2001
From: Jordi Enric <37541088+jordienr@users.noreply.github.com>
Date: Tue, 16 Jun 2026 16:58:48 +0200
Subject: [PATCH 020/488] fix(support): handle rate-limited support submissions
gracefully (#46928)
## Problem
When a support ticket submission is rejected by the API's rate limiter,
the form surfaced the raw server exception text to the user and reported
every rejection as an application error. This produced a steady stream
of noisy error reports for what is actually expected, recoverable
behavior.
The rejections are not random: the submit endpoint allows only a small
number of requests in a short window, so a quick second submission (a
fast retry or a follow-up ticket moments later) gets rejected. The first
submission usually succeeds; it's the immediate follow-up that fails.
Surfacing the raw error and logging it made this look worse than it is.
Separately, the success screen had only top padding, leaving its actions
flush against the bottom edge of the card.
## Fix
- Detect the rate-limit response and show a clear, friendly message that
tells the user how long to wait before trying again, instead of the raw
exception text.
- Stop reporting rate-limit rejections as errors to our monitoring. They
are expected and recoverable, so they no longer add noise.
- Give the success state the same vertical padding as the rest of the
form so its actions are not flush against the card edge.
## How to test
- Open the support form and simulate a 429 from the submit endpoint.
- Expected: a friendly message telling the user when they can retry, and
no error reported to monitoring.
- Submit a ticket successfully and confirm the success screen has even
padding above and below its content.
## Notes
This covers the user-facing handling. The rate-limit threshold itself is
tuned conservatively on the API and can be revisited separately so that
ordinary, legitimate resubmissions are not caught.
## Summary by CodeRabbit
* **Bug Fixes**
* Improved support form handling for rate-limited (429) submissions by
suppressing unnecessary error reporting while still showing the error
and returning the form to editing.
* Fixed inconsistent support form spacing so padding is consistent
regardless of submission outcome.
* **Improvements**
* Propagated backend error `code` through the support-ticket submission
flow so the UI can react more intelligently to failures (including 429
retry-window messaging).
* Enhanced retry timing extraction for rate-limited errors by using
`Retry-After` with a fallback to rate-limit reset data.
---------
Co-authored-by: Claude Sonnet 4.6
---
.../interfaces/Support/SupportForm.state.ts | 4 +++-
.../interfaces/Support/SupportFormPage.tsx | 7 ++++---
.../interfaces/Support/SupportFormV2.tsx | 1 +
.../interfaces/Support/SupportFormV3.tsx | 1 +
.../interfaces/Support/SupportSidebarForm.tsx | 4 +++-
.../data/feedback/support-ticket-send.ts | 21 +++++++++++++++++--
apps/studio/data/fetchers.ts | 12 ++++++-----
7 files changed, 38 insertions(+), 12 deletions(-)
diff --git a/apps/studio/components/interfaces/Support/SupportForm.state.ts b/apps/studio/components/interfaces/Support/SupportForm.state.ts
index c9895322cbc..3caac18083d 100644
--- a/apps/studio/components/interfaces/Support/SupportForm.state.ts
+++ b/apps/studio/components/interfaces/Support/SupportForm.state.ts
@@ -32,6 +32,7 @@ export type SupportFormState =
| {
type: 'error'
message: string
+ code?: number
}
export type SupportFormActions =
@@ -45,7 +46,7 @@ export type SupportFormActions =
submittedRequest: SubmittedSupportRequest
debugSource?: string
}
- | { type: 'ERROR'; message: string; debugSource?: string }
+ | { type: 'ERROR'; message: string; code?: number; debugSource?: string }
| { type: 'RETURN_TO_EDITING'; debugSource?: string }
export function createInitialSupportFormState(): SupportFormState {
@@ -89,6 +90,7 @@ export function supportFormReducer(
return {
type: 'error',
message: action.message,
+ code: action.code,
}
}
console.warn(
diff --git a/apps/studio/components/interfaces/Support/SupportFormPage.tsx b/apps/studio/components/interfaces/Support/SupportFormPage.tsx
index 0f675c3f165..8181283f5b7 100644
--- a/apps/studio/components/interfaces/Support/SupportFormPage.tsx
+++ b/apps/studio/components/interfaces/Support/SupportFormPage.tsx
@@ -82,7 +82,9 @@ function SupportFormPageContent() {
useStateTransition(state, 'submitting', 'error', (_, curr) => {
toast.error(`Failed to submit support ticket: ${curr.message}`)
- Sentry.captureMessage(`Failed to submit Support Form: ${curr.message}`)
+ if (curr.code !== 429) {
+ Sentry.captureMessage(`Failed to submit Support Form: ${curr.message}`)
+ }
dispatch({ type: 'RETURN_TO_EDITING' })
})
@@ -258,8 +260,7 @@ function SupportFormBody({
return (
diff --git a/apps/studio/components/interfaces/Support/SupportFormV2.tsx b/apps/studio/components/interfaces/Support/SupportFormV2.tsx
index 5b60aa92a1d..17d6ad0e884 100644
--- a/apps/studio/components/interfaces/Support/SupportFormV2.tsx
+++ b/apps/studio/components/interfaces/Support/SupportFormV2.tsx
@@ -114,6 +114,7 @@ export const SupportFormV2 = ({ form, initialError, state, dispatch }: SupportFo
dispatch({
type: 'ERROR',
message: error.message,
+ code: error.code,
})
},
})
diff --git a/apps/studio/components/interfaces/Support/SupportFormV3.tsx b/apps/studio/components/interfaces/Support/SupportFormV3.tsx
index c86f463cc09..553dd433d88 100644
--- a/apps/studio/components/interfaces/Support/SupportFormV3.tsx
+++ b/apps/studio/components/interfaces/Support/SupportFormV3.tsx
@@ -122,6 +122,7 @@ export const SupportFormV3 = ({
dispatch({
type: 'ERROR',
message: error.message,
+ code: error.code,
})
},
})
diff --git a/apps/studio/components/interfaces/Support/SupportSidebarForm.tsx b/apps/studio/components/interfaces/Support/SupportSidebarForm.tsx
index 40b0288d6ea..fa910e1db52 100644
--- a/apps/studio/components/interfaces/Support/SupportSidebarForm.tsx
+++ b/apps/studio/components/interfaces/Support/SupportSidebarForm.tsx
@@ -70,7 +70,9 @@ export function SupportForm({ initialParams }: SupportFormProps) {
useStateTransition(state, 'submitting', 'error', (_, curr) => {
toast.error(`Failed to submit support ticket: ${curr.message}`)
- Sentry.captureMessage(`Failed to submit Support Form: ${curr.message}`)
+ if (curr.code !== 429) {
+ Sentry.captureMessage(`Failed to submit Support Form: ${curr.message}`)
+ }
dispatch({ type: 'RETURN_TO_EDITING' })
})
diff --git a/apps/studio/data/feedback/support-ticket-send.ts b/apps/studio/data/feedback/support-ticket-send.ts
index 8e14bf50b40..37957dce243 100644
--- a/apps/studio/data/feedback/support-ticket-send.ts
+++ b/apps/studio/data/feedback/support-ticket-send.ts
@@ -5,7 +5,8 @@ import { toast } from 'sonner'
import type { ExtendedSupportCategories } from '@/components/interfaces/Support/Support.constants'
import { handleError, post } from '@/data/fetchers'
-import type { ResponseError, UseCustomMutationOptions } from '@/types'
+import { ResponseError } from '@/types'
+import type { UseCustomMutationOptions } from '@/types'
export type sendSupportTicketVariables = {
subject: string
@@ -25,6 +26,8 @@ export type sendSupportTicketVariables = {
dashboardStudioVersion?: string
}
+const RATE_LIMIT_FALLBACK_SECONDS = 60
+
export async function sendSupportTicket({
subject,
message,
@@ -42,7 +45,7 @@ export async function sendSupportTicket({
dashboardLogs,
dashboardStudioVersion,
}: sendSupportTicketVariables) {
- const { data, error } = await post('/platform/feedback/send', {
+ const { data, error, response } = await post('/platform/feedback/send', {
body: {
subject,
message,
@@ -65,6 +68,20 @@ export async function sendSupportTicket({
})
if (error) {
+ const httpResponse: unknown = response
+ if (httpResponse instanceof Response && httpResponse.status === 429) {
+ const resetHeader =
+ httpResponse.headers.get('Retry-After') ?? httpResponse.headers.get('X-RateLimit-Reset')
+ const parsedReset = resetHeader ? parseInt(resetHeader, 10) : NaN
+ const waitSeconds = Number.isFinite(parsedReset) ? parsedReset : RATE_LIMIT_FALLBACK_SECONDS
+ throw new ResponseError(
+ `You have submitted too many support requests. Please try again in ${waitSeconds} second${waitSeconds === 1 ? '' : 's'}.`,
+ 429,
+ undefined,
+ waitSeconds
+ )
+ }
+
handleError(error, {
alwaysCapture: true,
sentryContext: {
diff --git a/apps/studio/data/fetchers.ts b/apps/studio/data/fetchers.ts
index 7e71e9dd686..1ce51f26e80 100644
--- a/apps/studio/data/fetchers.ts
+++ b/apps/studio/data/fetchers.ts
@@ -140,7 +140,8 @@ client.use(
body.requestId = request.headers.get('X-Request-Id')
- const retryAfterHeader = response.headers.get('Retry-After')
+ const retryAfterHeader =
+ response.headers.get('Retry-After') ?? response.headers.get('X-RateLimit-Reset')
body.retryAfter = retryAfterHeader ? parseInt(retryAfterHeader) : undefined
const requestUrl = new URL(request.url)
@@ -296,10 +297,11 @@ async function handleFetchError(response: unknown): Promise {
resJson.msg ??
resJson.error ??
`An error has occurred: ${status ?? 'Unknown error'}`
- const retryAfter =
- response instanceof Response && response.headers.get('Retry-After')
- ? parseInt(response.headers.get('Retry-After')!)
- : undefined
+ const retryAfterHeader =
+ response instanceof Response
+ ? (response.headers.get('Retry-After') ?? response.headers.get('X-RateLimit-Reset'))
+ : null
+ const retryAfter = retryAfterHeader ? parseInt(retryAfterHeader) : undefined
let error = new ResponseError(message, status, undefined, retryAfter)
From f70e9c49ff6af86c9d77295c6803f50e14a7fcfb Mon Sep 17 00:00:00 2001
From: mo khan
Date: Tue, 16 Jun 2026 09:03:15 -0600
Subject: [PATCH 021/488] docs: Add @xlgmokha to humans.txt (#46995)
## I have read the
[CONTRIBUTING.md](https://github.com/supabase/supabase/blob/master/CONTRIBUTING.md)
file.
YES
## What kind of change does this PR introduce?
docs update
## What is the current behavior?
N/A
## What is the new behavior?
N/A
## Additional context
Following the instructions from the onboarding guide.
## Summary by CodeRabbit
* **Chores**
* Updated team information.
---
apps/docs/public/humans.txt | 1 +
1 file changed, 1 insertion(+)
diff --git a/apps/docs/public/humans.txt b/apps/docs/public/humans.txt
index a2765dcef91..f419811b211 100644
--- a/apps/docs/public/humans.txt
+++ b/apps/docs/public/humans.txt
@@ -199,6 +199,7 @@ Mert Yerekapan
Michal Kleczek
Michelle Jubrey
Miranda Limonczenko
+Mo Khan
Monica Khoury
Mrinal Paliwal
Mykhailo Mischa Lieibenson
From 79ce3b4ec7c8426cae82c8b5eb7ff98c3eddf1da Mon Sep 17 00:00:00 2001
From: "kemal.earth" <606977+kemaldotearth@users.noreply.github.com>
Date: Tue, 16 Jun 2026 16:39:39 +0100
Subject: [PATCH 022/488] fix(studio): hide throughput row on review modal for
io2 (#46997)
## I have read the
[CONTRIBUTING.md](https://github.com/supabase/supabase/blob/master/CONTRIBUTING.md)
file.
YES
## What kind of change does this PR introduce?
When a user selects IO2 on compute upgrade, the `0/MB` isn't quite
correct, whilst the costa delta of $0 is correct. We will hide the row
as it adds noise.
## Summary by CodeRabbit
* **Bug Fixes**
* Fixed disk management UI to correctly display the throughput
configuration row only when selecting GP3 storage type, ensuring the
interface accurately reflects available options for the selected storage
type.
---
.../DiskManagementReviewAndSubmitDialog.hooks.ts | 9 +++++----
1 file changed, 5 insertions(+), 4 deletions(-)
diff --git a/apps/studio/components/interfaces/DiskManagement/DiskManagementReviewAndSubmitDialog/DiskManagementReviewAndSubmitDialog.hooks.ts b/apps/studio/components/interfaces/DiskManagement/DiskManagementReviewAndSubmitDialog/DiskManagementReviewAndSubmitDialog.hooks.ts
index 9505d1d6cbb..954a1ac0a5d 100644
--- a/apps/studio/components/interfaces/DiskManagement/DiskManagementReviewAndSubmitDialog/DiskManagementReviewAndSubmitDialog.hooks.ts
+++ b/apps/studio/components/interfaces/DiskManagement/DiskManagementReviewAndSubmitDialog/DiskManagementReviewAndSubmitDialog.hooks.ts
@@ -120,7 +120,6 @@ export function useDiskManagementReviewChanges(
// --- Derived predicates ---
- const storageTypeBefore = (form.formState.defaultValues?.storageType ?? '') as DiskType
const storageTypeAfter = form.getValues('storageType') as DiskType
// Show hero whenever any line-item price actually changes, not just compute
@@ -132,12 +131,14 @@ export function useDiskManagementReviewChanges(
// Show cooldown warning whenever any disk attribute that enforces the 4-hour lock changes
const anyDiskAttributeChange = hasIOPSChanges || hasStorageTypeChanges || hasTotalSizeChanges
- // Show throughput row whenever either the before or after storage type is GP3
- // (covers GP3→IO2 where the throughput charge drops to zero)
+ // Throughput is only a user-configurable, separately-billed attribute for GP3. For IO2 it is
+ // derived from provisioned IOPS (0.256 MiB/s per IOPS) and isn't surfaced as its own value, so
+ // the form clears it to 0 — rendering a misleading "→ 0 MB/s". Only show the row when the
+ // resulting storage type is GP3; any GP3→IO2 throughput price delta still lands in the total.
const showThroughputRow =
!isAwsK8sProject &&
!isAwsNimbus &&
- (storageTypeBefore === 'gp3' || storageTypeAfter === 'gp3') &&
+ storageTypeAfter === 'gp3' &&
(hasThroughputChanges || hasStorageTypeChanges)
const hasAnyBreakdownRows =
From 92e79e67d9f573157fd7f60869214db113e7d478 Mon Sep 17 00:00:00 2001
From: Ivan Vasilov
Date: Tue, 16 Jun 2026 19:18:17 +0300
Subject: [PATCH 023/488] feat: Add error state to charts (#46991)
This PR adds an error state to the usage charts on the Project home
page.
I also added an error state to the charts in the [design
system](https://design-system-git-feat-chart-error-state-supabase.vercel.app/design-system/docs/ui-patterns/charts#chart-states).
## Summary by CodeRabbit
* **New Features**
* Charts now display error states when data retrieval or processing
fails, providing users with clear feedback about issues.
* Improved error visibility and handling across analytics and charting
components for better transparency.
---
.../default/block/chart-composed-states.tsx | 31 ++++++-
.../ProjectHome/ProjectUsageSection.tsx | 78 +++++++++-------
.../analytics/useFillTimeseriesSorted.ts | 88 ++++++++++---------
packages/ui-patterns/src/Chart/index.tsx | 16 +++-
.../ui-patterns/src/LogsBarChart/index.tsx | 9 ++
5 files changed, 147 insertions(+), 75 deletions(-)
diff --git a/apps/design-system/registry/default/block/chart-composed-states.tsx b/apps/design-system/registry/default/block/chart-composed-states.tsx
index c4e25d545c2..2d3657cca2c 100644
--- a/apps/design-system/registry/default/block/chart-composed-states.tsx
+++ b/apps/design-system/registry/default/block/chart-composed-states.tsx
@@ -1,7 +1,7 @@
'use client'
import { BarChart2, ExternalLink } from 'lucide-react'
-import { Badge } from 'ui'
+import { Badge, CriticalIcon } from 'ui'
import {
Chart,
ChartActions,
@@ -44,6 +44,35 @@ export default function ChartComposedStates() {
+
+
+
+ Response Errors
+
+
+ }
+ title="Some error happened"
+ description="Error happened why trying to fetch data. Please try again later."
+ />
+ }
+ emptyState={
+ }
+ title="No data to show"
+ description="It may take up to 24 hours for data to refresh"
+ />
+ }
+ loadingState={}
+ >
+ My chart here...
+
+
+
+
diff --git a/apps/studio/components/interfaces/ProjectHome/ProjectUsageSection.tsx b/apps/studio/components/interfaces/ProjectHome/ProjectUsageSection.tsx
index 54c02299725..db61af89df2 100644
--- a/apps/studio/components/interfaces/ProjectHome/ProjectUsageSection.tsx
+++ b/apps/studio/components/interfaces/ProjectHome/ProjectUsageSection.tsx
@@ -3,15 +3,16 @@ import dayjs from 'dayjs'
import Link from 'next/link'
import { useRouter } from 'next/router'
import { useEffect, useMemo, useState } from 'react'
-import { Card, CardContent, CardHeader, CardTitle, Loading } from 'ui'
+import { Card, CardContent, CardHeader, CardTitle, Loading, WarningIcon } from 'ui'
import { Row } from 'ui-patterns'
+import { ChartEmptyState } from 'ui-patterns/Chart'
import { LogsBarChart } from 'ui-patterns/LogsBarChart'
import NoDataPlaceholder from '@/components/ui/Charts/NoDataPlaceholder'
import { ChartIntervalDropdown } from '@/components/ui/Logs/ChartIntervalDropdown'
import { CHART_INTERVALS } from '@/components/ui/Logs/logs.utils'
import { UsageApiCounts, useProjectLogStatsQuery } from '@/data/analytics/project-log-stats-query'
-import { useFillTimeseriesSorted } from '@/hooks/analytics/useFillTimeseriesSorted'
+import { fillTimeseriesSorted } from '@/hooks/analytics/useFillTimeseriesSorted'
import { useCheckEntitlements } from '@/hooks/misc/useCheckEntitlements'
import { useIsFeatureEnabled } from '@/hooks/misc/useIsFeatureEnabled'
import { useSelectedOrganizationQuery } from '@/hooks/misc/useSelectedOrganization'
@@ -71,33 +72,42 @@ export const ProjectUsageSection = () => {
}, [selectedInterval])
// Use V1 data fetching
- const { data: logStatsData, isPending: isLoading } = useProjectLogStatsQuery({
- projectRef,
- interval,
- })
+ const {
+ data: filledCharts,
+ isPending: isLoading,
+ error,
+ } = useProjectLogStatsQuery(
+ {
+ projectRef,
+ interval,
+ },
+ {
+ select: (data) => {
+ // Calculate date range for gap filling
+ const startDateLocal = dayjs().subtract(
+ selectedInterval.startValue,
+ selectedInterval.startUnit as dayjs.ManipulateType
+ )
+ const endDateLocal = dayjs()
- // Calculate date range for gap filling
- const startDateLocal = dayjs().subtract(
- selectedInterval.startValue,
- selectedInterval.startUnit as dayjs.ManipulateType
+ return fillTimeseriesSorted({
+ data: data.result,
+ timestampKey: 'timestamp',
+ valueKey: [
+ 'total_auth_requests',
+ 'total_rest_requests',
+ 'total_storage_requests',
+ 'total_realtime_requests',
+ ],
+ defaultValue: 0,
+ startDate: startDateLocal.toISOString(),
+ endDate: endDateLocal.toISOString(),
+ minPointsToFill: 5,
+ })
+ },
+ refetchOnWindowFocus: false,
+ }
)
- const endDateLocal = dayjs()
-
- // Fill gaps in timeseries data
- const { data: filledCharts } = useFillTimeseriesSorted({
- data: logStatsData?.result ?? [],
- timestampKey: 'timestamp',
- valueKey: [
- 'total_auth_requests',
- 'total_rest_requests',
- 'total_storage_requests',
- 'total_realtime_requests',
- ],
- defaultValue: 0,
- startDate: startDateLocal.toISOString(),
- endDate: endDateLocal.toISOString(),
- minPointsToFill: 5,
- })
const serviceBase: ServiceEntry[] = useMemo(
() => [
@@ -147,7 +157,7 @@ export const ProjectUsageSection = () => {
// Transform V1 data to LogsBarChart format
// Since V1 doesn't have error/warning breakdown, we show everything as "ok"
- const transformedData: LogsBarChartDatum[] = (filledCharts || []).map((item) => ({
+ const transformedData: LogsBarChartDatum[] = (filledCharts?.data || []).map((item) => ({
timestamp: item.timestamp,
error_count: 0,
warning_count: 0,
@@ -162,10 +172,10 @@ export const ProjectUsageSection = () => {
data: transformedData,
total,
isLoading,
- error: null,
+ error: error || filledCharts?.error || null,
}
}),
- [serviceBase, filledCharts, isLoading]
+ [serviceBase, filledCharts, isLoading, error]
)
const handleBarClick =
@@ -239,6 +249,7 @@ export const ProjectUsageSection = () => {
{
label: 'Requests',
},
}}
+ ErrorState={
+ }
+ title="Failed to load project usage"
+ description="Check our Status Page or try again later."
+ />
+ }
EmptyState={
(data: T[], timestampKey: stri
*/
export const useFillTimeseriesSorted = (
options: FillTimeseriesOptions
+): FillTimeseriesResult => {
+ return useMemo(() => {
+ return fillTimeseriesSorted(options)
+ }, [
+ JSON.stringify(options.data),
+ options.timestampKey,
+ JSON.stringify(options.valueKey),
+ options.defaultValue,
+ options.startDate,
+ options.endDate,
+ options.minPointsToFill,
+ options.interval,
+ ])
+}
+
+export const fillTimeseriesSorted = (
+ options: FillTimeseriesOptions
): FillTimeseriesResult => {
const {
data,
@@ -78,50 +95,39 @@ export const useFillTimeseriesSorted = (
interval,
} = options
- return useMemo(() => {
- // Early return if no valid timestamp
- if (!hasValidTimestamp(data, timestampKey)) {
- return {
- data,
- error: null,
- isError: false,
- }
+ // Early return if no valid timestamp
+ if (!hasValidTimestamp(data, timestampKey)) {
+ return {
+ data,
+ error: null,
+ isError: false,
}
+ }
- try {
- const filled = fillTimeseries(
- data,
- timestampKey,
- valueKey,
- defaultValue,
- startDate,
- endDate,
- minPointsToFill,
- interval
- ) as T[]
+ try {
+ const filled = fillTimeseries(
+ data,
+ timestampKey,
+ valueKey,
+ defaultValue,
+ startDate,
+ endDate,
+ minPointsToFill,
+ interval
+ ) as T[]
- const sorted = sortByTimestamp(filled, timestampKey)
+ const sorted = sortByTimestamp(filled, timestampKey)
- return {
- data: sorted,
- error: null,
- isError: false,
- }
- } catch (error: unknown) {
- return {
- data: [],
- error: error instanceof Error ? error : new Error(String(error)),
- isError: true,
- }
+ return {
+ data: sorted,
+ error: null,
+ isError: false,
}
- }, [
- JSON.stringify(data),
- timestampKey,
- JSON.stringify(valueKey),
- defaultValue,
- startDate,
- endDate,
- minPointsToFill,
- interval,
- ])
+ } catch (error: unknown) {
+ return {
+ data: [],
+ error: error instanceof Error ? error : new Error(String(error)),
+ isError: true,
+ }
+ }
}
diff --git a/packages/ui-patterns/src/Chart/index.tsx b/packages/ui-patterns/src/Chart/index.tsx
index ca9773a529a..3c0937a6159 100644
--- a/packages/ui-patterns/src/Chart/index.tsx
+++ b/packages/ui-patterns/src/Chart/index.tsx
@@ -43,11 +43,13 @@ export type ChartConfig = {
interface ChartContextValue {
isLoading?: boolean
isDisabled?: boolean
+ isErrored?: boolean
}
const ChartContext = React.createContext({
isLoading: false,
isDisabled: false,
+ isErrored: false,
})
export const useChart = () => {
@@ -59,15 +61,19 @@ interface ChartProps extends React.HTMLAttributes {
children: React.ReactNode
isLoading?: boolean
isDisabled?: boolean
+ isErrored?: boolean
className?: string
}
const chartTableClasses = `[&_tr]:border-b [&_tr]:border-border [&_thead_tr]:bg-transparent! [&_thead_th]:py-2! [&_thead_th]:!px-card [&_thead_th]:h-auto [&_tbody_td]:py-2.5 [&_tbody_td]:px-card [&_tbody_td]:text-xs [&_table]:mb-1 [&_table]:border-b [&_table]:border-border`
const Chart = React.forwardRef(
- ({ children, isLoading = false, isDisabled = false, className, ...props }, ref) => {
+ (
+ { children, isLoading = false, isDisabled = false, isErrored = false, className, ...props },
+ ref
+ ) => {
return (
-
+
{children}
@@ -306,6 +312,7 @@ interface ChartContentProps extends React.HTMLAttributes {
isEmpty?: boolean
emptyState?: React.ReactNode
loadingState?: React.ReactNode
+ errorState?: React.ReactNode
disabledState?: React.ReactNode
disabledActions?: ChartAction[]
}
@@ -318,19 +325,22 @@ const ChartContent = React.forwardRef(
isEmpty = false,
emptyState,
loadingState,
+ errorState,
disabledState,
disabledActions,
...props
},
ref
) => {
- const { isLoading, isDisabled } = useChart()
+ const { isLoading, isDisabled, isErrored } = useChart()
let content: React.ReactNode
if (isDisabled) {
content = disabledState
} else if (isLoading) {
content = loadingState
+ } else if (isErrored) {
+ content = errorState
} else if (isEmpty) {
content = emptyState
} else {
diff --git a/packages/ui-patterns/src/LogsBarChart/index.tsx b/packages/ui-patterns/src/LogsBarChart/index.tsx
index 20316fc438f..c0ad0476d8b 100644
--- a/packages/ui-patterns/src/LogsBarChart/index.tsx
+++ b/packages/ui-patterns/src/LogsBarChart/index.tsx
@@ -26,8 +26,10 @@ type LogsBarChartDatum = {
export const LogsBarChart = ({
data,
+ error,
onBarClick,
EmptyState,
+ ErrorState,
DateTimeFormat = 'MMM D, YYYY, hh:mma',
isFullHeight = false,
chartConfig,
@@ -36,8 +38,10 @@ export const LogsBarChart = ({
hideXAxis = false,
}: {
data: LogsBarChartDatum[]
+ error?: unknown | null
onBarClick?: (datum: LogsBarChartDatum, tooltipData?: CategoricalChartState) => void
EmptyState?: ReactNode
+ ErrorState?: ReactNode
DateTimeFormat?: string
isFullHeight?: boolean
chartConfig?: ChartConfig
@@ -47,6 +51,11 @@ export const LogsBarChart = ({
}) => {
const [focusDataIndex, setFocusDataIndex] = useState(null)
+ if (error) {
+ if (ErrorState) return ErrorState
+ return null
+ }
+
if (data.length === 0) {
if (EmptyState) return EmptyState
return null
From 6a6b7c90858b6b868c6d05bd3263a957357fa84a Mon Sep 17 00:00:00 2001
From: Danny White <3104761+dnywh@users.noreply.github.com>
Date: Tue, 16 Jun 2026 12:59:37 -0600
Subject: [PATCH 024/488] fix(docs): remove redundant icons (#47002)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
## What kind of change does this PR introduce?
UI fix. Resolves DOCS-1051.
## What is the current behavior?
Two unnecessary icons on docs homepage add more confusion than help.
## What is the new behavior?
Removed and tightened surrounding spacing + rhythm.
| Before | After |
| --- | --- |
| | |
| | |
## Summary by CodeRabbit
* **Style**
* Simplified documentation page header and section visuals by removing
icon-accented wrappers and using cleaner text-based layouts.
* **Accessibility / Content**
* Updated section heading hierarchy for improved structure (e.g.,
“Additional resources” and “Self-Hosting”) by promoting headings while
keeping existing context and styling.
* Refreshed the “Getting Started” section to be text-focused without the
prior play icon treatment.
---
apps/docs/app/page.tsx | 20 ++++++++------------
apps/docs/components/HomePageCover.tsx | 17 +++++++----------
2 files changed, 15 insertions(+), 22 deletions(-)
diff --git a/apps/docs/app/page.tsx b/apps/docs/app/page.tsx
index 186f3548a79..31eba97aef4 100644
--- a/apps/docs/app/page.tsx
+++ b/apps/docs/app/page.tsx
@@ -1,11 +1,10 @@
import { isFeatureEnabled } from 'common'
import { type Metadata, type ResolvingMetadata } from 'next'
import Link from 'next/link'
-import { cn, IconBackground } from 'ui'
+import { cn } from 'ui'
import { IconPanel } from 'ui-patterns/IconPanel'
import { TextLink } from 'ui-patterns/TextLink'
-import MenuIconPicker from '@/components/Navigation/NavigationMenu/MenuIconPicker'
import { MIGRATION_PAGES } from '@/components/Navigation/NavigationMenu/NavigationMenu.constants'
import { GlassPanelWithIconPicker } from '@/features/ui/GlassPanelWithIconPicker'
import { IconPanelWithIconPicker } from '@/features/ui/IconPanelWithIconPicker'
@@ -324,10 +323,10 @@ const HomePage = () => (
)}
+ Set up and connect a database in just a few minutes.
+
-
- Set up and connect a database in just a few minutes.
-
From c54168842b36835e50299ef8fd3700371b239e6a Mon Sep 17 00:00:00 2001
From: Matt Rossman <22670878+mattrossman@users.noreply.github.com>
Date: Tue, 16 Jun 2026 17:20:06 -0400
Subject: [PATCH 025/488] fix(assistant): prevent parallel approval-required
tool calls (#47008)
Addresses the issue of parallel tool approvals freezing Assistant and
causing UX ambiguity around what happens if only part of multiple
dependent invocations is approved.
Two layers at which this is addressed:
1. Tightens prompt to clarify approval tools must be issued one per
step, not in parallel.
2. In case something slips past the prompt, this also auto-denies all
but the first `approval-required` tool call when the model issues
multiple in the same step, so the model is forced to reissue them
sequentially.
**Demo**
The following chats demo me explicitly asking Assistant to run those
approval-gated tools in parallel, and the Assistant correctly invokes
them sequentially instead.
| Parallel `execute_sql` request | Parallel `deploy_edge_function`
request |
|--------|--------|
| | |
As shown in [this
trace](https://www.braintrust.dev/app/supabase.io/p/Assistant/trace?object_type=project_logs&object_id=5a8d02e5-b3b6-40cc-ba76-ecee286478f4&r=a3a37857-95df-4a95-a5a8-818ea305b2a5&s=a3a37857-95df-4a95-a5a8-818ea305b2a5),
parallel tool calls are still allowed for context gathering tools that
don't require approval:
Closes AI-803
## Summary by CodeRabbit
* **Improvements**
* Approval-required operations are now processed sequentially rather
than in parallel within the AI Assistant.
* **Tests**
* Added comprehensive test coverage for the parallel approval prevention
logic.
---
.../ui/AIAssistantPanel/AIAssistant.tsx | 13 ++++
apps/studio/lib/ai/message-utils.test.ts | 78 ++++++++++++++++++-
apps/studio/lib/ai/message-utils.ts | 16 +++-
apps/studio/lib/ai/prompts.ts | 2 +-
4 files changed, 105 insertions(+), 4 deletions(-)
diff --git a/apps/studio/components/ui/AIAssistantPanel/AIAssistant.tsx b/apps/studio/components/ui/AIAssistantPanel/AIAssistant.tsx
index 2184f94a8e0..6b8848e44d7 100644
--- a/apps/studio/components/ui/AIAssistantPanel/AIAssistant.tsx
+++ b/apps/studio/components/ui/AIAssistantPanel/AIAssistant.tsx
@@ -39,6 +39,7 @@ import { useLocalStorageQuery } from '@/hooks/misc/useLocalStorage'
import { useOrgAiOptInLevel } from '@/hooks/misc/useOrgOptedIntoAi'
import { useSelectedOrganizationQuery } from '@/hooks/misc/useSelectedOrganization'
import { useSelectedProjectQuery } from '@/hooks/misc/useSelectedProject'
+import { getParallelApprovalIdsToReject } from '@/lib/ai/message-utils'
import {
DEFAULT_ASSISTANT_BASE_MODEL_ID,
defaultAssistantModelId,
@@ -366,6 +367,18 @@ export const AIAssistant = ({ className }: AIAssistantProps) => {
}
}, [isResubmitting, chatStatus, error])
+ useEffect(() => {
+ // Approval-required tools can't run in parallel. Auto-deny extras so the model reissues them sequentially.
+ for (const id of getParallelApprovalIdsToReject(chatMessages)) {
+ addToolApprovalResponse?.({
+ id,
+ approved: false,
+ reason:
+ 'Only one approval-required tool call is allowed per turn. Please reissue this tool call after the current one completes.',
+ })
+ }
+ }, [chatMessages, addToolApprovalResponse])
+
useEffect(() => {
setValue(snap.initialInput || '')
if (inputRef.current && snap.initialInput) {
diff --git a/apps/studio/lib/ai/message-utils.test.ts b/apps/studio/lib/ai/message-utils.test.ts
index 34502f43d2a..0125996ddc7 100644
--- a/apps/studio/lib/ai/message-utils.test.ts
+++ b/apps/studio/lib/ai/message-utils.test.ts
@@ -1,7 +1,81 @@
-import type { UIMessage } from 'ai'
+import type { DynamicToolUIPart, UIMessage } from 'ai'
import { describe, expect, it } from 'vitest'
-import { prepareMessagesForAPI } from './message-utils'
+import { getParallelApprovalIdsToReject, prepareMessagesForAPI } from './message-utils'
+
+const makeApprovalPart = (id: string): DynamicToolUIPart => ({
+ type: 'dynamic-tool',
+ toolName: 'test_tool',
+ toolCallId: id,
+ state: 'approval-requested',
+ input: {},
+ approval: { id },
+})
+
+const makeResultPart = (id: string): DynamicToolUIPart => ({
+ type: 'dynamic-tool',
+ toolName: 'test_tool',
+ toolCallId: id,
+ state: 'output-available',
+ input: {},
+ output: {},
+})
+
+describe('getParallelApprovalIdsToReject', () => {
+ it('returns [] for empty messages', () => {
+ expect(getParallelApprovalIdsToReject([])).toEqual([])
+ })
+
+ it('returns [] when there are no assistant messages', () => {
+ const messages: UIMessage[] = [{ id: '1', role: 'user', parts: [] }]
+ expect(getParallelApprovalIdsToReject(messages)).toEqual([])
+ })
+
+ it('returns [] when last assistant message has no pending approvals', () => {
+ const messages: UIMessage[] = [{ id: '1', role: 'assistant', parts: [makeResultPart('r1')] }]
+ expect(getParallelApprovalIdsToReject(messages)).toEqual([])
+ })
+
+ it('returns [] when there is only one pending approval', () => {
+ const messages: UIMessage[] = [{ id: '1', role: 'assistant', parts: [makeApprovalPart('a1')] }]
+ expect(getParallelApprovalIdsToReject(messages)).toEqual([])
+ })
+
+ it('returns all but the first id when there are multiple pending approvals', () => {
+ const messages: UIMessage[] = [
+ {
+ id: '1',
+ role: 'assistant',
+ parts: [makeApprovalPart('a1'), makeApprovalPart('a2'), makeApprovalPart('a3')],
+ },
+ ]
+ expect(getParallelApprovalIdsToReject(messages)).toEqual(['a2', 'a3'])
+ })
+
+ it('only inspects the last assistant message', () => {
+ const messages: UIMessage[] = [
+ {
+ id: '1',
+ role: 'assistant',
+ parts: [makeApprovalPart('old1'), makeApprovalPart('old2')],
+ },
+ { id: '2', role: 'user', parts: [] },
+ { id: '3', role: 'assistant', parts: [makeApprovalPart('new1')] },
+ ]
+ expect(getParallelApprovalIdsToReject(messages)).toEqual([])
+ })
+
+ it('ignores non-approval tool parts', () => {
+ const messages: UIMessage[] = [
+ {
+ id: '1',
+ role: 'assistant',
+ parts: [makeResultPart('r1'), makeApprovalPart('a1'), makeApprovalPart('a2')],
+ },
+ ]
+ expect(getParallelApprovalIdsToReject(messages)).toEqual(['a2'])
+ })
+})
describe('prepareMessagesForAPI', () => {
it('should limit messages to last 7 entries', () => {
diff --git a/apps/studio/lib/ai/message-utils.ts b/apps/studio/lib/ai/message-utils.ts
index 2b0cbd62924..d04e25b5c1d 100644
--- a/apps/studio/lib/ai/message-utils.ts
+++ b/apps/studio/lib/ai/message-utils.ts
@@ -1,4 +1,4 @@
-import type { UIMessage } from 'ai'
+import { isToolUIPart, type UIMessage } from 'ai'
/**
* Prepares messages for API transmission by cleaning and limiting history
@@ -23,3 +23,17 @@ export function prepareMessagesForAPI(messages: UIMessage[]): UIMessage[] {
return cleanedMessages
}
+
+/**
+ * Returns approval IDs to auto-deny when the model issues multiple approval-required
+ * tool calls in the same turn — all but the first, so the model reissues them sequentially.
+ */
+export function getParallelApprovalIdsToReject(messages: UIMessage[]): string[] {
+ const lastMessage = messages.findLast((m) => m.role === 'assistant')
+ if (!lastMessage) return []
+
+ const pendingIds = (lastMessage.parts ?? []).flatMap((part) =>
+ isToolUIPart(part) && part.state === 'approval-requested' ? [part.approval.id] : []
+ )
+ return pendingIds.slice(1)
+}
diff --git a/apps/studio/lib/ai/prompts.ts b/apps/studio/lib/ai/prompts.ts
index 09f71fb4f5d..81c6f0435f6 100644
--- a/apps/studio/lib/ai/prompts.ts
+++ b/apps/studio/lib/ai/prompts.ts
@@ -733,7 +733,7 @@ export const CHAT_PROMPT = `
- On execution error, explain succinctly and attempt to correct if possible, validating each outcome briefly (1–2 lines) after execution.
- If a user skips execution, acknowledge and suggest alternatives.
- Use markdown code blocks (\`\`\`sql\`\`\`) for illustrative SQL only if requested by the user or when providing non-executable examples.
-- Execute multiple queries separately via \`execute_sql\` and briefly validate outcomes.
+- Never call \`execute_sql\` or \`deploy_edge_function\` in parallel within the same step. Each requires user approval, so issue one per step and wait for its result before calling the next.
- After execution, summarize outcomes concisely without duplicating results, as the client will present these.
## Edge Functions
- Deploy Edge Functions by calling \`deploy_edge_function\` directly with \`name\` and \`code\`; the client handles confirmation and result presentation.
From 608040b8cb3f553d142d43d3f91eb6de89624559 Mon Sep 17 00:00:00 2001
From: Miranda Limonczenko
Date: Tue, 16 Jun 2026 14:45:55 -0700
Subject: [PATCH 026/488] chore(docs) Resolve 'simple' style warnings where
applicable (#46966)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Contributes to DOCS-1052
## I have read the
[CONTRIBUTING.md](https://github.com/supabase/supabase/blob/master/CONTRIBUTING.md)
file.
YES
## What kind of change does this PR introduce?
Resolves MDX linting errors related to "simple" where it applies.
There was a couple cases that did not apply. For example, a product with
"Simple" in the name.
These changes are made in context, either by removing or using a more
descriptive synonym like "minimal" or "basic".
## Tophatting
1. Read each of the diffs.
2. See that the text still makes sense in context.
For extra due diligence, you can run `pnpm lint:mdx` locally and see the
'simple' errors that remain and whether they are worth addressing.
## Summary by CodeRabbit
## Summary by CodeRabbit
* **Documentation**
* Updated many guide, tutorial, and troubleshooting pages with clearer
“basic”/“minimal” wording across setup steps, local testing
instructions, security cautions, and RLS guidance.
* Refined headings, example descriptions, and inline comments for
consistency (including deployment, MCP, metrics API, and search/function
phrasing).
* Improved readability with small snippet formatting tweaks (whitespace
plus import/comment ordering) and added a self-hosting debugging note
for Envoy admin endpoints via a short-lived `curl` container.
---------
Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
Co-authored-by: Chris Chinchilla
Co-authored-by: Nik Richers
---
apps/docs/content/_partials/database_setup.mdx | 2 +-
apps/docs/content/_partials/kotlin_project_setup.mdx | 2 +-
apps/docs/content/_partials/metrics_access.mdx | 2 +-
apps/docs/content/guides/ai-tools/byo-mcp.mdx | 6 ++++--
apps/docs/content/guides/ai.mdx | 8 ++++----
apps/docs/content/guides/ai/engineering-for-scale.mdx | 4 ++--
.../guides/ai/examples/building-chatgpt-plugins.mdx | 2 +-
apps/docs/content/guides/ai/keyword-search.mdx | 2 +-
apps/docs/content/guides/ai/langchain.mdx | 2 +-
apps/docs/content/guides/ai/rag-with-permissions.mdx | 2 +-
apps/docs/content/guides/auth/auth-mfa.mdx | 2 +-
apps/docs/content/guides/auth/auth-mfa/totp.mdx | 2 +-
apps/docs/content/guides/auth/auth-smtp.mdx | 2 +-
apps/docs/content/guides/auth/server-side.mdx | 2 +-
.../connecting-to-postgres/serverless-drivers.mdx | 2 +-
apps/docs/content/guides/database/extensions/http.mdx | 4 ++--
.../docs/content/guides/database/extensions/hypopg.mdx | 2 +-
.../content/guides/database/extensions/postgis.mdx | 4 ++--
.../content/guides/database/extensions/timescaledb.mdx | 2 +-
apps/docs/content/guides/database/functions.mdx | 6 +++---
apps/docs/content/guides/database/partitions.mdx | 2 +-
apps/docs/content/guides/database/postgres/indexes.mdx | 2 +-
apps/docs/content/guides/database/tables.mdx | 2 +-
apps/docs/content/guides/database/testing.mdx | 2 +-
apps/docs/content/guides/deployment.mdx | 6 +++---
.../guides/deployment/shared-responsibility-model.mdx | 2 +-
apps/docs/content/guides/functions.mdx | 2 +-
apps/docs/content/guides/functions/architecture.mdx | 2 +-
.../content/guides/functions/examples/discord-bot.mdx | 5 +++--
.../guides/functions/examples/mcp-server-mcp-lite.mdx | 2 +-
.../content/guides/functions/recursive-functions.mdx | 4 ++--
apps/docs/content/guides/functions/routing.mdx | 2 +-
apps/docs/content/guides/functions/unit-test.mdx | 2 +-
apps/docs/content/guides/functions/wasm.mdx | 2 +-
apps/docs/content/guides/getting-started/api-keys.mdx | 2 +-
.../content/guides/getting-started/architecture.mdx | 4 ++--
apps/docs/content/guides/getting-started/features.mdx | 2 +-
.../guides/getting-started/quickstarts/laravel.mdx | 2 +-
.../guides/getting-started/quickstarts/sveltekit.mdx | 2 +-
.../getting-started/tutorials/with-redwoodjs.mdx | 9 ++++-----
.../guides/integrations/partner-integration-guide.mdx | 4 ++--
.../content/guides/integrations/vercel-marketplace.mdx | 2 +-
.../local-development/cli/testing-and-linting.mdx | 2 +-
.../guides/local-development/testing/overview.mdx | 4 ++--
.../local-development/testing/pgtap-extended.mdx | 4 ++--
apps/docs/content/guides/platform.mdx | 2 +-
apps/docs/content/guides/realtime/broadcast.mdx | 6 +++---
apps/docs/content/guides/realtime/protocol.mdx | 2 +-
.../realtime/subscribing-to-database-changes.mdx | 5 ++++-
apps/docs/content/guides/resources/glossary.mdx | 2 +-
apps/docs/content/guides/security.mdx | 2 +-
.../content/guides/self-hosting/self-hosted-envoy.mdx | 2 +-
.../guides/storage/uploads/standard-uploads.mdx | 4 +++-
apps/docs/content/guides/telemetry/logs.mdx | 2 +-
...xceeds-btree-version-4-maximum-for-index-LMmoeU.mdx | 2 +-
...rom-supabase-auth-helpers-to-ssr-package-5NRunM.mdx | 2 +-
apps/docs/content/troubleshooting/http-api-issues.mdx | 2 +-
...esponse-or-zgotmplz-in-magic-link-emails-433665.mdx | 2 +-
.../troubleshooting/prisma-error-management-Cm5P_o.mdx | 2 +-
.../troubleshooting/realtime-heartbeat-messages.mdx | 10 +++++-----
.../troubleshooting/soft-deletes-with-supabase-js.mdx | 2 +-
61 files changed, 95 insertions(+), 88 deletions(-)
diff --git a/apps/docs/content/_partials/database_setup.mdx b/apps/docs/content/_partials/database_setup.mdx
index 92112438ddc..09cac33af3c 100644
--- a/apps/docs/content/_partials/database_setup.mdx
+++ b/apps/docs/content/_partials/database_setup.mdx
@@ -1,6 +1,6 @@
## Project setup
-Let's create a new Postgres database. This is as simple as starting a new Project in Supabase:
+To create a new Postgres database, start a new Project in Supabase:
1. [Create a new project](https://database.new/) in the Supabase dashboard.
1. Enter your project details. Remember to store your password somewhere safe.
diff --git a/apps/docs/content/_partials/kotlin_project_setup.mdx b/apps/docs/content/_partials/kotlin_project_setup.mdx
index 1f32521eefd..91b95ad86ec 100644
--- a/apps/docs/content/_partials/kotlin_project_setup.mdx
+++ b/apps/docs/content/_partials/kotlin_project_setup.mdx
@@ -1,6 +1,6 @@
## Project setup
-Before we start building we're going to set up our Database and API. This is as simple as starting a new Project in Supabase and then creating a "schema" inside the database.
+Before building, you must set up your Database and API with a new Project in Supabase and then create a "schema" inside the database.
### Create a project
diff --git a/apps/docs/content/_partials/metrics_access.mdx b/apps/docs/content/_partials/metrics_access.mdx
index 853dcaac14a..2aa32d58aee 100644
--- a/apps/docs/content/_partials/metrics_access.mdx
+++ b/apps/docs/content/_partials/metrics_access.mdx
@@ -25,7 +25,7 @@ className="rounded-lg border border-foreground/10 bg-surface-100 text-foreground
- **Username**: `service_role`
- **Password**: a **Secret API key** (`sb_secret_...`). You can create/copy it in [**Project Settings → API Keys**](/dashboard/project/_/settings/api-keys). For more context, see [Understanding API keys](/docs/guides/getting-started/api-keys).
- Testing locally is as simple as running `curl` with your Secret API key:
+ To test locally, run `curl` with your Secret API key:
```bash
curl /customer/v1/privileged/metrics \
diff --git a/apps/docs/content/guides/ai-tools/byo-mcp.mdx b/apps/docs/content/guides/ai-tools/byo-mcp.mdx
index 88e708a8c4b..2df8f11ed23 100644
--- a/apps/docs/content/guides/ai-tools/byo-mcp.mdx
+++ b/apps/docs/content/guides/ai-tools/byo-mcp.mdx
@@ -75,7 +75,7 @@ const server = new McpServer({
version: '0.1.0',
})
-// Register a simple addition tool
+// Register an addition tool
server.registerTool(
'add',
{
@@ -218,7 +218,9 @@ After this step, you have a fully deployed MCP server accessible from anywhere.
You can find ready-to-use MCP server implementations here:
-- [Simple MCP server](https://github.com/supabase/supabase/tree/master/examples/edge-functions/supabase/functions/mcp/simple-mcp-server) - Basic unauthenticated example
+{/* supa-mdx-lint-disable-next-line Rule004ExcludeWords */}
+
+- [Simple MCP server](https://github.com/supabase/supabase/tree/master/examples/edge-functions/supabase/functions/mcp/simple-mcp-server) - Unauthenticated example
## Resources
diff --git a/apps/docs/content/guides/ai.mdx b/apps/docs/content/guides/ai.mdx
index 4fb8c15b66c..5226d8849aa 100644
--- a/apps/docs/content/guides/ai.mdx
+++ b/apps/docs/content/guides/ai.mdx
@@ -109,8 +109,8 @@ Check out all of the AI [templates and examples](https://github.com/supabase/sup
- OpenAI is an AI research and deployment company. Supabase provides a simple way to use
- OpenAI in your applications.
+ OpenAI is an AI research and deployment company. Supabase provides a way to use OpenAI in
+ your applications.
@@ -125,8 +125,8 @@ Check out all of the AI [templates and examples](https://github.com/supabase/sup
- Hugging Face is an open-source provider of NLP technologies. Supabase provides a simple way
- to use Hugging Face's models in your applications.
+ Hugging Face is an open-source provider of NLP technologies. Supabase provides a way to use
+ Hugging Face's models in your applications.
diff --git a/apps/docs/content/guides/ai/engineering-for-scale.mdx b/apps/docs/content/guides/ai/engineering-for-scale.mdx
index 55e8990507d..a9c74970bd7 100644
--- a/apps/docs/content/guides/ai/engineering-for-scale.mdx
+++ b/apps/docs/content/guides/ai/engineering-for-scale.mdx
@@ -8,9 +8,9 @@ sidebar_label: 'Engineering for Scale'
Content sources for vectors can be extremely large. As you grow you should run your Vector workloads across several secondary databases (sometimes called "pods"), which allows each collection to scale independently.
-## Simple workloads
+## Small workloads [#simple-workloads]
-For small workloads, it's typical to store your data in a single database.
+For small workloads, you can typically store your data in a single database.
If you've used [Vecs](/docs/guides/ai/vecs-python-client) to create 3 different collections, you can expose collections to your web or mobile application using [views](/docs/guides/database/tables#views):
diff --git a/apps/docs/content/guides/ai/examples/building-chatgpt-plugins.mdx b/apps/docs/content/guides/ai/examples/building-chatgpt-plugins.mdx
index b6dfa676b9d..8d6bc5eb3ee 100644
--- a/apps/docs/content/guides/ai/examples/building-chatgpt-plugins.mdx
+++ b/apps/docs/content/guides/ai/examples/building-chatgpt-plugins.mdx
@@ -20,7 +20,7 @@ It allows ChatGPT to dynamically pull relevant information into conversations fr
## Example: Chat with Postgres docs
-Let’s build an example where we can “ask ChatGPT questions” about the Postgres documentation. Although ChatGPT already knows about the Postgres documentation because it is publicly available, this is a simple example which demonstrates how to work with PDF files.
+Let’s build an example where we can “ask ChatGPT questions” about the Postgres documentation. Although ChatGPT already knows about the Postgres documentation because it is publicly available, this is a basic example which demonstrates how to work with PDF files.
This plugin requires several steps:
diff --git a/apps/docs/content/guides/ai/keyword-search.mdx b/apps/docs/content/guides/ai/keyword-search.mdx
index 9ee03877831..643fa08025f 100644
--- a/apps/docs/content/guides/ai/keyword-search.mdx
+++ b/apps/docs/content/guides/ai/keyword-search.mdx
@@ -8,7 +8,7 @@ sidebar_label: 'Keyword search'
Keyword search involves locating documents or records that contain specific words or phrases, primarily based on the exact match between the search terms and the text within the data. It differs from [semantic search](/docs/guides/ai/semantic-search), which interprets the meaning behind the query to provide results that are contextually related, even if the exact words aren't present in the text. Semantic search considers synonyms, intent, and natural language nuances to provide a more nuanced approach to information retrieval.
-In Postgres, keyword search is implemented using [full-text search](/docs/guides/database/full-text-search). It supports indexing and text analysis for data retrieval, focusing on records that match the search criteria. Postgres' full-text search extends beyond simple keyword matching to address linguistic nuances, making it effective for applications that require precise text queries.
+In Postgres, keyword search is implemented using [full-text search](/docs/guides/database/full-text-search). It supports indexing and text analysis for data retrieval, focusing on records that match the search criteria. Postgres' full-text search extends beyond keyword matching to address linguistic nuances, making it effective for applications that require precise text queries.
## When and why to use keyword search
diff --git a/apps/docs/content/guides/ai/langchain.mdx b/apps/docs/content/guides/ai/langchain.mdx
index b089cb4ab5e..09cf1c570fa 100644
--- a/apps/docs/content/guides/ai/langchain.mdx
+++ b/apps/docs/content/guides/ai/langchain.mdx
@@ -108,7 +108,7 @@ export const run = async () => {
}
```
-### Simple metadata filtering
+### Basic metadata filtering [#simple-metadata-filtering]
Given the above `match_documents` Postgres function, you can also pass a filter parameter to only return documents with a specific metadata field value. This filter parameter is a JSON object, and the `match_documents` function will use the Postgres JSONB Containment operator `@>` to filter documents by the metadata field values you specify. See details on the [Postgres JSONB Containment operator](https://www.postgresql.org/docs/current/datatype-json.html#JSON-CONTAINMENT) for more information.
diff --git a/apps/docs/content/guides/ai/rag-with-permissions.mdx b/apps/docs/content/guides/ai/rag-with-permissions.mdx
index 08c8ca7b021..4b2df595dce 100644
--- a/apps/docs/content/guides/ai/rag-with-permissions.mdx
+++ b/apps/docs/content/guides/ai/rag-with-permissions.mdx
@@ -231,7 +231,7 @@ order by document_sections.embedding <#> embedding;
{/* supa-mdx-lint-disable-next-line Rule004ExcludeWords */}
-You might be tempted to discard RLS completely and simply filter by user within the `where` clause. Though this will work, we recommend RLS as a general best practice since RLS is always applied even as new queries and application logic is introduced in the future.
+You might be tempted to discard RLS completely and filter by user within the `where` clause. Though this will work, we recommend RLS as a general best practice since RLS is always applied even as new queries and application logic is introduced in the future.
diff --git a/apps/docs/content/guides/auth/auth-mfa.mdx b/apps/docs/content/guides/auth/auth-mfa.mdx
index 1cb3576ef18..542884c5aa8 100644
--- a/apps/docs/content/guides/auth/auth-mfa.mdx
+++ b/apps/docs/content/guides/auth/auth-mfa.mdx
@@ -127,7 +127,7 @@ Unenrolling a factor will downgrade the assurance level from `aal2` to `aal1` on
```tsx
/**
- * UnenrollMFA shows a simple table with the list of factors together with a button to unenroll.
+ * UnenrollMFA shows a table with the list of factors together with a button to unenroll.
* When a user types in the factorId of the factor that they wish to unenroll and clicks unenroll
* the corresponding factor will be unenrolled.
*/
diff --git a/apps/docs/content/guides/auth/auth-mfa/totp.mdx b/apps/docs/content/guides/auth/auth-mfa/totp.mdx
index c645e15f681..c1869fbb097 100644
--- a/apps/docs/content/guides/auth/auth-mfa/totp.mdx
+++ b/apps/docs/content/guides/auth/auth-mfa/totp.mdx
@@ -75,7 +75,7 @@ Below is an example that creates a new `EnrollMFA` component that illustrates th
```tsx
/**
- * EnrollMFA shows a simple enrollment dialog. When shown on screen it calls
+ * EnrollMFA shows an enrollment dialog. When shown on screen it calls
* the `enroll` API. Each time a user clicks the Enable button it calls the
* `challenge` and `verify` APIs to check if the code provided by the user is
* valid.
diff --git a/apps/docs/content/guides/auth/auth-smtp.mdx b/apps/docs/content/guides/auth/auth-smtp.mdx
index 2e4d9fefd33..b43e261bda7 100644
--- a/apps/docs/content/guides/auth/auth-smtp.mdx
+++ b/apps/docs/content/guides/auth/auth-smtp.mdx
@@ -13,7 +13,7 @@ If you're using Supabase Auth with the following configuration:
You will need to set up a custom SMTP server to handle the delivery of messages to your users.
-To get you started and let you explore and set up email message templates for your application, Supabase provides a simple SMTP server for all projects. This server imposes a few important restrictions and is not meant for production use.
+To get you started and let you explore and set up email message templates for your application, Supabase provides an SMTP server for all projects. This server imposes a few important restrictions and is not meant for production use.
**Send messages only to pre-authorized addresses.**
diff --git a/apps/docs/content/guides/auth/server-side.mdx b/apps/docs/content/guides/auth/server-side.mdx
index 782db4bc501..81ae770cd4a 100644
--- a/apps/docs/content/guides/auth/server-side.mdx
+++ b/apps/docs/content/guides/auth/server-side.mdx
@@ -15,7 +15,7 @@ Make sure to use the PKCE flow instructions where those differ from the implicit
## `@supabase/ssr`
-We have developed an [`@supabase/ssr`](https://www.npmjs.com/package/@supabase/ssr) package to make setting up the Supabase client as simple as possible. This package is currently in beta. Adoption is recommended but be aware that the API is still unstable and may have breaking changes in the future.
+We have developed an [`@supabase/ssr`](https://www.npmjs.com/package/@supabase/ssr) package for setting up the Supabase client. This package is currently in beta. Adoption is recommended but be aware that the API is still unstable and may have breaking changes in the future.
## Framework quickstarts
diff --git a/apps/docs/content/guides/database/connecting-to-postgres/serverless-drivers.mdx b/apps/docs/content/guides/database/connecting-to-postgres/serverless-drivers.mdx
index 24591674340..87a78a6f926 100644
--- a/apps/docs/content/guides/database/connecting-to-postgres/serverless-drivers.mdx
+++ b/apps/docs/content/guides/database/connecting-to-postgres/serverless-drivers.mdx
@@ -35,7 +35,7 @@ Choose one of these Vercel Deploy Templates which use our [Vercel Deploy Integra
passHref
>
- Simple Next.js template that uses Supabase as the database and Kysely as the query builder.
+ Basic Next.js template that uses Supabase as the database and Kysely as the query builder.
diff --git a/apps/docs/content/guides/database/extensions/http.mdx b/apps/docs/content/guides/database/extensions/http.mdx
index ed4052e62e0..f987f35493c 100644
--- a/apps/docs/content/guides/database/extensions/http.mdx
+++ b/apps/docs/content/guides/database/extensions/http.mdx
@@ -88,7 +88,7 @@ A successful call to a web URL from the `http` extension returns a record with t
## Examples
-### Simple `GET` example
+### Basic `GET` example [#simple-get-example]
```sql
select
@@ -97,7 +97,7 @@ from
extensions.http_get('https://jsonplaceholder.typicode.com/todos/1');
```
-### Simple `POST` example
+### Basic `POST` example [#simple-post-example]
```sql
select
diff --git a/apps/docs/content/guides/database/extensions/hypopg.mdx b/apps/docs/content/guides/database/extensions/hypopg.mdx
index 3a3875ef139..6bea2618227 100644
--- a/apps/docs/content/guides/database/extensions/hypopg.mdx
+++ b/apps/docs/content/guides/database/extensions/hypopg.mdx
@@ -45,7 +45,7 @@ It's good practice to create the extension within a separate schema (like `exten
### Speeding up a query
-Given the following table and a simple query to select from the table by `id`:
+Given the following table and a basic query to select from the table by `id`:
{/* prettier-ignore */}
```sql
diff --git a/apps/docs/content/guides/database/extensions/postgis.mdx b/apps/docs/content/guides/database/extensions/postgis.mdx
index 599f65be591..61b14e05a4e 100644
--- a/apps/docs/content/guides/database/extensions/postgis.mdx
+++ b/apps/docs/content/guides/database/extensions/postgis.mdx
@@ -9,7 +9,7 @@ tocVideo: 'agFsGDJxjwA'
## Overview
-While you may be able to store simple lat/long geographic coordinates as a set of decimals, it does not scale very well when you try to query through a large data set. PostGIS comes with special data types that are efficient, and indexable for high scalability.
+While you may be able to store lat/long geographic coordinates as a set of decimals, it does not scale very well when you try to query through a large data set. PostGIS comes with special data types that are efficient, and indexable for high scalability.
The additional data types that PostGIS provides include [Point](https://postgis.net/docs/using_postgis_dbmanagement.html#Point), [Polygon](https://postgis.net/docs/using_postgis_dbmanagement.html#Polygon), [LineString](https://postgis.net/docs/using_postgis_dbmanagement.html#LineString), and many more to represent different types of geographical data. In this guide, we will mainly focus on how to interact with `Point` type, which represents a single set of latitude and longitude. If you are interested in digging deeper, you can learn more about different data types on the [data management section of PostGIS docs](https://postgis.net/docs/using_postgis_dbmanagement.html).
@@ -47,7 +47,7 @@ drop extension if exists postgis;
## Examples
-Now that we are ready to get started with PostGIS, let’s create a table and see how we can utilize PostGIS for some typical use cases. Let’s imagine we are creating a simple restaurant-searching app.
+Now that we are ready to get started with PostGIS, let’s create a table and see how we can use PostGIS for some typical use cases. Imagine we are creating a basic restaurant-searching app.
Let’s create our table. Each row represents a restaurant with its location stored in `location` column as a `Point` type.
diff --git a/apps/docs/content/guides/database/extensions/timescaledb.mdx b/apps/docs/content/guides/database/extensions/timescaledb.mdx
index a3aa0303646..abea2efc839 100644
--- a/apps/docs/content/guides/database/extensions/timescaledb.mdx
+++ b/apps/docs/content/guides/database/extensions/timescaledb.mdx
@@ -60,7 +60,7 @@ It's good practice to create the extension within a separate schema (like `exten
## Usage
-To demonstrate how `timescaledb` works, let's consider a simple example where we have a table that stores temperature data from different sensors. We will create a table named "temperatures" and store data for two sensors.
+To demonstrate how `timescaledb` works, consider a basic example where we have a table that stores temperature data from different sensors. We will create a table named "temperatures" and store data for two sensors.
First we create a hypertable, which is a virtual table that is partitioned into chunks based on time intervals. The hypertable acts as a proxy for the actual table and makes it easy to query and manage time-series data.
diff --git a/apps/docs/content/guides/database/functions.mdx b/apps/docs/content/guides/database/functions.mdx
index abea38ae77d..5dac1acaa3e 100644
--- a/apps/docs/content/guides/database/functions.mdx
+++ b/apps/docs/content/guides/database/functions.mdx
@@ -30,7 +30,7 @@ and run the SQL queries yourself.
3. Enter the SQL to create or replace your Database function.
4. Click "Run" or cmd+enter (ctrl+enter).
-## Simple functions
+## Basic functions [#simple-functions]
Let's create a basic Database Function which returns a string "hello world".
@@ -53,7 +53,7 @@ At it's most basic a function has the following parts:
2. `returns text`: The type of data that the function returns. If it returns nothing, you can `returns void`.
3. `language sql`: The language used inside the function body. This can also be a procedural language: `plpgsql`, `plpython`, etc.
4. `as $$`: The function wrapper. Anything enclosed inside the `$$` symbols will be part of the function body.
-5. `select 'hello world';`: A simple function body. The final `select` statement inside a function body will be returned if there are no statements following it.
+5. `select 'hello world';`: A basic function body. The final `select` statement inside a function body will be returned if there are no statements following it.
6. `$$;`: The closing symbols of the function wrapper.
@@ -290,7 +290,7 @@ data = supabase.rpc('get_planets').eq('id', 1).execute()
## Passing parameters
-Let's create a Function to insert a new planet into the `planets` table and return the new ID. Note that this time we're using the `plpgsql` language.
+Create a function to insert a new planet into the `planets` table and return the new ID. Note that this time we're using the `plpgsql` language.
```sql
create or replace function add_planet(name text)
diff --git a/apps/docs/content/guides/database/partitions.mdx b/apps/docs/content/guides/database/partitions.mdx
index 9019ea55e34..73e9f3a2903 100644
--- a/apps/docs/content/guides/database/partitions.mdx
+++ b/apps/docs/content/guides/database/partitions.mdx
@@ -105,7 +105,7 @@ There is no real threshold to determine when you should use partitions. Partitio
## Examples
-Here are simple examples for each of the partitioning types in Postgres.
+Here are basic examples for each of the partitioning types in Postgres.
### Range partitioning
diff --git a/apps/docs/content/guides/database/postgres/indexes.mdx b/apps/docs/content/guides/database/postgres/indexes.mdx
index d0b36b77bf0..a4a33e4ab6a 100644
--- a/apps/docs/content/guides/database/postgres/indexes.mdx
+++ b/apps/docs/content/guides/database/postgres/indexes.mdx
@@ -53,7 +53,7 @@ Seq Scan on persons (cost=0.00..22.75 rows=x width=y)
Filter: (age = 32)
```
-To add a simple B-Tree index you can run:
+To add a basic B-Tree index you can run:
```sql
create index idx_persons_age on persons (age);
diff --git a/apps/docs/content/guides/database/tables.mdx b/apps/docs/content/guides/database/tables.mdx
index 4f284bc1dd5..79c3a43e0fa 100644
--- a/apps/docs/content/guides/database/tables.mdx
+++ b/apps/docs/content/guides/database/tables.mdx
@@ -92,7 +92,7 @@ You must define the "data type" when you create a column.
### Data types
-Every column is a predefined type. Postgres provides many [default types](https://www.postgresql.org/docs/current/datatype.html), and you can even design your own (or use extensions) if the default types don't fit your needs. You can use any data type that Postgres supports via the SQL editor. We only support a subset of these in the Table Editor in an effort to keep the experience simple for people with less experience with databases.
+Every column is a predefined type. Postgres provides many [default types](https://www.postgresql.org/docs/current/datatype.html), and you can even design your own (or use extensions) if the default types don't fit your needs. You can use any data type that Postgres supports via the SQL editor. We only support a subset of these in the Table Editor in an effort to keep the experience focused for people with less experience with databases.
Show/Hide default data types
diff --git a/apps/docs/content/guides/database/testing.mdx b/apps/docs/content/guides/database/testing.mdx
index 8054ecc2b7f..a4e93b38eeb 100644
--- a/apps/docs/content/guides/database/testing.mdx
+++ b/apps/docs/content/guides/database/testing.mdx
@@ -34,7 +34,7 @@ touch ./supabase/tests/database/hello_world.test.sql
All `sql` files use [pgTAP](/docs/guides/database/extensions/pgtap) as the test runner.
-Let's write a simple test to check that our `auth.users` table has an ID column. Open `hello_world.test.sql` and add the following code:
+Write a test to check that our `auth.users` table has an ID column. Open `hello_world.test.sql` and add the following code:
```sql
begin;
diff --git a/apps/docs/content/guides/deployment.mdx b/apps/docs/content/guides/deployment.mdx
index cea5ad0ff4a..5fc4a55cf77 100644
--- a/apps/docs/content/guides/deployment.mdx
+++ b/apps/docs/content/guides/deployment.mdx
@@ -4,11 +4,11 @@ title: Deployment & Branching
Deploying your app makes it live and accessible to users. Most apps have at least two environments: a production environment for users and one or more staging or preview environments for development.
-Supabase provides flexible options for both simple and advanced deployment workflows.
+Supabase provides flexible options for deployment workflows of various complexity.
## Recommended workflow
-The simplest way to deploy your Supabase project is with GitHub (recommended, but not required):
+You can deploy your Supabase project with GitHub:
1. Develop locally using the [Supabase CLI](/docs/guides/local-development)
2. Push changes to your GitHub repository
@@ -41,7 +41,7 @@ You can automate deployments using:
### Is GitHub required?
-No. GitHub integration is recommended for the simplest setup, but you can deploy using the [Supabase CLI](/docs/guides/local-development) in your own CI/CD pipeline without connecting a GitHub repository.
+No. GitHub integration is recommended, but you can deploy using the [Supabase CLI](/docs/guides/local-development) in your own CI/CD pipeline without connecting a GitHub repository.
### Do you need a paid plan?
diff --git a/apps/docs/content/guides/deployment/shared-responsibility-model.mdx b/apps/docs/content/guides/deployment/shared-responsibility-model.mdx
index adc1ec62ebd..41c934fd008 100644
--- a/apps/docs/content/guides/deployment/shared-responsibility-model.mdx
+++ b/apps/docs/content/guides/deployment/shared-responsibility-model.mdx
@@ -69,7 +69,7 @@ If your application architecture relies on such integrations, you should monitor
## You choose your level of comfort with Postgres
-Our goal at Supabase is to make _all_ of Postgres easy to use. That doesn’t mean you have to use all of it. If you’re a Postgres veteran, you’ll probably love the tools that we offer. If you’ve never used Postgres before, then start smaller and grow into it. If you just want to treat Postgres like a simple table-store, that’s perfectly fine.
+Our goal at Supabase is to make _all_ of Postgres easy to use. That doesn’t mean you have to use all of it. If you’re a Postgres veteran, you’ll probably love the tools that we offer. If you’ve never used Postgres before, then start smaller and grow into it. If you want to treat Postgres like a basic table-store, that’s perfectly fine.
## You are in control of your database
diff --git a/apps/docs/content/guides/functions.mdx b/apps/docs/content/guides/functions.mdx
index 71839126532..87d1b7f42e4 100644
--- a/apps/docs/content/guides/functions.mdx
+++ b/apps/docs/content/guides/functions.mdx
@@ -25,7 +25,7 @@ Edge Functions are server-side TypeScript functions, distributed globally at the
## Quick technical notes
-- **Runtime:** Supabase Edge Runtime (Deno compatible runtime with TypeScript first). Functions are simple `.ts` files that export a handler.
+- **Runtime:** Supabase Edge Runtime (Deno compatible runtime with TypeScript first). Functions are `.ts` files that export a handler.
- **Local dev parity:** Use Supabase CLI for a local runtime similar to production for faster iteration (`supabase functions serve` command).
- **Global deployment:** Deploy your Edge Functions via Supabase Dashboard, CLI or MCP.
- **Cold starts & concurrency:** cold starts are possible — design for short-lived, idempotent operations. Heavy long-running jobs should be moved to [background workers](/docs/guides/functions/background-tasks).
diff --git a/apps/docs/content/guides/functions/architecture.mdx b/apps/docs/content/guides/functions/architecture.mdx
index 5bb5eb07f08..219233e37f6 100644
--- a/apps/docs/content/guides/functions/architecture.mdx
+++ b/apps/docs/content/guides/functions/architecture.mdx
@@ -24,7 +24,7 @@ To illustrate how edge functions operate, consider a photo-sharing app where use
- **Why Edge Functions?**:
- They handle compute-intensive tasks without burdening the client device or the database.
- Execution happens server-side but at the edge, ensuring speed and scalability.
- - Developers define the function in a simple JavaScript file within the Supabase functions directory.
+ - Developers define the function in a JavaScript file within the Supabase functions directory.
This example highlights edge functions as lightweight, on-demand code snippets that integrate seamlessly with Supabase services like Storage and Auth.
diff --git a/apps/docs/content/guides/functions/examples/discord-bot.mdx b/apps/docs/content/guides/functions/examples/discord-bot.mdx
index aa00105e557..085e109716b 100644
--- a/apps/docs/content/guides/functions/examples/discord-bot.mdx
+++ b/apps/docs/content/guides/functions/examples/discord-bot.mdx
@@ -43,12 +43,13 @@ This will register a Slash Command named `hello` that accepts a parameter named
```ts index.ts
// Sift is a small routing library that abstracts away details like starting a
-// listener on a port, and provides a simple function (serve) that has an API
+// listener on a port, and provides a function (serve) that has an API
// to invoke a function for a specific path.
-import { json, serve, validateRequest } from 'https://deno.land/x/sift@0.6.0/mod.ts'
+
// TweetNaCl is a cryptography library that we use to verify requests
// from Discord.
import nacl from 'https://cdn.skypack.dev/tweetnacl@v1.0.3?dts'
+import { json, serve, validateRequest } from 'https://deno.land/x/sift@0.6.0/mod.ts'
enum DiscordCommandType {
Ping = 1,
diff --git a/apps/docs/content/guides/functions/examples/mcp-server-mcp-lite.mdx b/apps/docs/content/guides/functions/examples/mcp-server-mcp-lite.mdx
index f81fe9b86f6..fc22b0f717a 100644
--- a/apps/docs/content/guides/functions/examples/mcp-server-mcp-lite.mdx
+++ b/apps/docs/content/guides/functions/examples/mcp-server-mcp-lite.mdx
@@ -21,7 +21,7 @@ This combination offers several advantages:
- **Direct database access**: Connect directly to your Supabase Postgres
- **Minimal footprint**: mcp-lite has zero runtime dependencies
- **Full type safety**: TypeScript support in Deno
-- **Simple deployment**: One command to production
+- **Basic deployment**: One command to production
## Prerequisites
diff --git a/apps/docs/content/guides/functions/recursive-functions.mdx b/apps/docs/content/guides/functions/recursive-functions.mdx
index ad28b050c1e..d661924efd1 100644
--- a/apps/docs/content/guides/functions/recursive-functions.mdx
+++ b/apps/docs/content/guides/functions/recursive-functions.mdx
@@ -256,7 +256,7 @@ export async function save(data: any) {
```typescript
// supabase/functions/process-data/index.ts
-import { validate, transform, save } from '../_shared/transform.ts'
+import { save, transform, validate } from '../_shared/transform.ts'
Deno.serve(async (req) => {
const data = await req.json()
@@ -284,7 +284,7 @@ async function processWithDelay(items: any[]) {
| Pattern | Budget consumption | Recommendation |
| ------------------------------- | ------------------ | ----------------- |
-| Simple chain (A to B to C) | Low | Generally safe |
+| Basic chain (A to B to C) | Low | Generally safe |
| Fan-out (A to B, C, D, E) | Moderate | Limit concurrency |
| Deep recursion (A to A to A...) | High | Set max depth |
| Unbounded loops | Very high | Avoid, use queues |
diff --git a/apps/docs/content/guides/functions/routing.mdx b/apps/docs/content/guides/functions/routing.mdx
index 3e112ee2d20..b6c084fe134 100644
--- a/apps/docs/content/guides/functions/routing.mdx
+++ b/apps/docs/content/guides/functions/routing.mdx
@@ -27,7 +27,7 @@ To combine multiple endpoints into a single Edge Function, you can use web appli
## Basic routing example
-Here's a simple hello world example using some popular web frameworks:
+Here's a basic hello world example using some popular web frameworks:
{
if (!supabaseUrl) throw new Error('supabaseUrl is required.')
if (!supabaseKey) throw new Error('supabaseKey is required.')
- // Test a simple query to the database
+ // Test a query to the database
const { data: table_data, error: table_error } = await client
.from('my_table')
.select('*')
diff --git a/apps/docs/content/guides/functions/wasm.mdx b/apps/docs/content/guides/functions/wasm.mdx
index c8377bc6e10..fe7e5f61ece 100644
--- a/apps/docs/content/guides/functions/wasm.mdx
+++ b/apps/docs/content/guides/functions/wasm.mdx
@@ -20,7 +20,7 @@ For example, libraries like [magick-wasm](/docs/guides/functions/examples/image-
### Writing a Wasm module
-You can use different languages and SDKs to write Wasm modules. For this tutorial, we will write a simple Wasm module in Rust that adds two numbers.
+You can use different languages and SDKs to write Wasm modules. For this tutorial, we will write a basic Wasm module in Rust that adds two numbers.
diff --git a/apps/docs/content/guides/getting-started/api-keys.mdx b/apps/docs/content/guides/getting-started/api-keys.mdx
index 696c9578bbe..3ca3976f52a 100644
--- a/apps/docs/content/guides/getting-started/api-keys.mdx
+++ b/apps/docs/content/guides/getting-started/api-keys.mdx
@@ -89,7 +89,7 @@ Never expose your secret keys publicly. Your data is at risk. **Do not:**
- Never use in a browser, even on `localhost`.
- Do not pass in URLs or query params, as these are often logged.
- Be careful passing them in request headers without prior log sanitization.
-- Take extra care logging even potentially **invalid API keys**. Simple typos might reveal the real key in the future.
+- Take extra care logging even potentially **invalid API keys**. Typos might reveal the real key in the future.
- Reveal, copy, use or manipulate on hardware devices without full disk encryption and which you do not directly own or control (such as public computers, friend's laptop, etc.)
Ensure you handle them with care and using [secure coding practices](https://owasp.org/www-project-secure-coding-practices-quick-reference-guide/stable-en/).
diff --git a/apps/docs/content/guides/getting-started/architecture.mdx b/apps/docs/content/guides/getting-started/architecture.mdx
index e75cd4ab38b..0e8767f5c3a 100644
--- a/apps/docs/content/guides/getting-started/architecture.mdx
+++ b/apps/docs/content/guides/getting-started/architecture.mdx
@@ -4,7 +4,7 @@ description: 'Supabase design and architecture'
tocVideo: 'T-qAtAKjqwc'
---
-Supabase is open source. We choose open source tools which are scalable and make them simple to use.
+Supabase is open source. We choose open source tools which are scalable and make them approachable.
Supabase is not a 1-to-1 mapping of Firebase. While we are building many of the features that Firebase offers, we are not going about it the same way:
our technological choices are quite different; everything we use is open source; and wherever possible, we use and support existing tools rather than developing from scratch.
@@ -13,7 +13,7 @@ Most notably, we use Postgres rather than a NoSQL store. This choice was deliber
## Choose your comfort level
-Our goal at Supabase is to make _all_ of Postgres easy to use. That doesn’t mean you have to use all of it. If you’re a Postgres veteran, you’ll probably love the tools that we offer. If you’ve never used Postgres before, then start smaller and grow into it. If you just want to treat Postgres like a simple table-store, that’s perfectly fine.
+Our goal at Supabase is to make _all_ of Postgres easy to use. That doesn’t mean you have to use all of it. If you’re a Postgres veteran, you’ll probably love the tools that we offer. If you’ve never used Postgres before, then start smaller and grow into it. If you want to treat Postgres like a basic table-store, that’s perfectly fine.
## Architecture
diff --git a/apps/docs/content/guides/getting-started/features.mdx b/apps/docs/content/guides/getting-started/features.mdx
index 8dcb43769e0..d27f2ca8a6d 100644
--- a/apps/docs/content/guides/getting-started/features.mdx
+++ b/apps/docs/content/guides/getting-started/features.mdx
@@ -128,7 +128,7 @@ Helpers for implementing user authentication in popular server-side languages an
### File storage
-Supabase Storage makes it simple to store and serve files. [Docs](/docs/guides/storage).
+Supabase Storage helps you store and serve files. [Docs](/docs/guides/storage).
### Content Delivery Network
diff --git a/apps/docs/content/guides/getting-started/quickstarts/laravel.mdx b/apps/docs/content/guides/getting-started/quickstarts/laravel.mdx
index 381caecf2e5..6e7744279bf 100644
--- a/apps/docs/content/guides/getting-started/quickstarts/laravel.mdx
+++ b/apps/docs/content/guides/getting-started/quickstarts/laravel.mdx
@@ -29,7 +29,7 @@ hideToc: true
- Install [Laravel Breeze](https://laravel.com/docs/10.x/starter-kits#laravel-breeze), a simple implementation of all of Laravel's [authentication features](https://laravel.com/docs/10.x/authentication).
+ Install [Laravel Breeze](https://laravel.com/docs/10.x/starter-kits#laravel-breeze), a basic implementation of all of Laravel's [authentication features](https://laravel.com/docs/10.x/authentication).
diff --git a/apps/docs/content/guides/getting-started/quickstarts/sveltekit.mdx b/apps/docs/content/guides/getting-started/quickstarts/sveltekit.mdx
index 16fff4527d8..30be6126edc 100644
--- a/apps/docs/content/guides/getting-started/quickstarts/sveltekit.mdx
+++ b/apps/docs/content/guides/getting-started/quickstarts/sveltekit.mdx
@@ -112,7 +112,7 @@ hideToc: true
- Use `load` method to fetch the data server-side and display the query results as a simple list.
+ Use `load` method to fetch the data server-side and display the query results as a list.
Create `+page.server.js` file in the `src/routes` directory with the following code.
diff --git a/apps/docs/content/guides/getting-started/tutorials/with-redwoodjs.mdx b/apps/docs/content/guides/getting-started/tutorials/with-redwoodjs.mdx
index 18f4af41521..36482c6e839 100644
--- a/apps/docs/content/guides/getting-started/tutorials/with-redwoodjs.mdx
+++ b/apps/docs/content/guides/getting-started/tutorials/with-redwoodjs.mdx
@@ -28,7 +28,7 @@ Important: When this guide refers to "API," that means the Supabase API and when
The **`api side`** is an implementation of a GraphQL API. The business logic is organized into "services" that represent their own internal API and can be called both from external GraphQL requests and other internal services.
-The **`web side`** is built with React. Redwood's router makes it simple to map URL paths to React "Page" components (and automatically code-split your app on each route).
+The **`web side`** is built with React. Redwood's router lets you map URL paths to React "Page" components (and automatically code-split your app on each route).
Pages may contain a "Layout" component to wrap content. They also contain "Cells" and regular React components.
Cells allow you to declaratively manage the lifecycle of a component that fetches and displays data.
@@ -249,8 +249,8 @@ Now, update the `Auth.js` component to contain:
<$CodeTabs>
```jsx name=/web/src/components/Auth/Auth.js
-import { useState } from 'react'
import { useAuth } from '@redwoodjs/auth'
+import { useState } from 'react'
const Auth = () => {
const { logIn } = useAuth()
@@ -326,8 +326,8 @@ And then update the file to contain:
<$CodeTabs>
```jsx name=web/src/components/Account/Account.js
-import { useState, useEffect } from 'react'
import { useAuth } from '@redwoodjs/auth'
+import { useEffect, useState } from 'react'
const Account = () => {
const { client: supabase, currentUser, logOut } = useAuth()
@@ -464,7 +464,6 @@ With all the components in place, update your `HomePage` page to use them:
```jsx name=web/src/pages/HomePage/HomePage.js
import { useAuth } from '@redwoodjs/auth'
import { MetaTags } from '@redwoodjs/web'
-
import Account from 'src/components/Account'
import Auth from 'src/components/Auth'
@@ -511,8 +510,8 @@ Now, update your Avatar component to contain the following widget:
<$CodeTabs>
```jsx name=web/src/components/Avatar/Avatar.js
-import { useEffect, useState } from 'react'
import { useAuth } from '@redwoodjs/auth'
+import { useEffect, useState } from 'react'
const Avatar = ({ url, size, onUpload }) => {
const { client: supabase } = useAuth()
diff --git a/apps/docs/content/guides/integrations/partner-integration-guide.mdx b/apps/docs/content/guides/integrations/partner-integration-guide.mdx
index 74ff3e28eeb..3cf4bd56726 100644
--- a/apps/docs/content/guides/integrations/partner-integration-guide.mdx
+++ b/apps/docs/content/guides/integrations/partner-integration-guide.mdx
@@ -9,12 +9,12 @@ This guide assumes you have already followed [the Build a Supabase Integration g
When a Supabase user clicks the **Install Integration** button in the Dashboard, they are redirected to your system to begin the OAuth flow. You can implement this redirect in one of two ways:
-- **[Simple redirect](#method-1-simple-redirect)**: Easier to build, but your system cannot verify that the incoming user was sent by Supabase.
+- **[Redirect](#method-1-redirect)**: Easier to build, but your system cannot verify that the incoming user was sent by Supabase.
- **[Signed redirect](#method-2-signed-redirect)**: More work to build, but cryptographically verifies that the redirect originated from Supabase. **Recommended for production integrations.**
Pick the method that fits your security requirements, then follow the matching section below.
-## Method 1: Simple redirect
+## Method 1: Redirect
In this method, you implement a single `GET` endpoint. Supabase redirects the user to this endpoint when they click **Install Integration**, and your endpoint kicks off the OAuth flow.
diff --git a/apps/docs/content/guides/integrations/vercel-marketplace.mdx b/apps/docs/content/guides/integrations/vercel-marketplace.mdx
index 8471fd1cdd4..35c554d1695 100644
--- a/apps/docs/content/guides/integrations/vercel-marketplace.mdx
+++ b/apps/docs/content/guides/integrations/vercel-marketplace.mdx
@@ -58,7 +58,7 @@ These variables ensure your applications can connect securely to the database an
## Studio support
-Accessing Supabase Studio is simple through the Vercel dashboard. You can open Supabase Studio from either the Integration installation page or the Vercel Storage page.
+Open Supabase Studio from the Vercel dashboard. You can access it from either the Integration installation page or the Vercel Storage page.
Depending on your entry point, you'll either land on the Supabase dashboard homepage or be redirected to the corresponding Supabase Project.
Supabase Studio provides tools such as:
diff --git a/apps/docs/content/guides/local-development/cli/testing-and-linting.mdx b/apps/docs/content/guides/local-development/cli/testing-and-linting.mdx
index 017961afb7c..2fc83fe1ee9 100644
--- a/apps/docs/content/guides/local-development/cli/testing-and-linting.mdx
+++ b/apps/docs/content/guides/local-development/cli/testing-and-linting.mdx
@@ -44,7 +44,7 @@ By default, Mailpit is available at [localhost:54324](http://localhost:54324) wh
### Going into production
-The "default" email provided by Supabase is only for development purposes. It is [heavily restricted](/docs/guides/platform/going-into-prod#auth-rate-limits) to ensure that it is not used for spam. Before going into production, you must configure your own email provider. This is as simple as enabling a new SMTP credentials in your [project settings](/dashboard/project/_/auth/smtp).
+The "default" email provided by Supabase is only for development purposes. It is [heavily restricted](/docs/guides/platform/going-into-prod#auth-rate-limits) to ensure that it is not used for spam. Before going into production, configure your own email provider by enabling SMTP credentials in your [project settings](/dashboard/project/_/auth/smtp).
## Linting your database
diff --git a/apps/docs/content/guides/local-development/testing/overview.mdx b/apps/docs/content/guides/local-development/testing/overview.mdx
index 8c4624a92a6..9b0e3ac7e09 100644
--- a/apps/docs/content/guides/local-development/testing/overview.mdx
+++ b/apps/docs/content/guides/local-development/testing/overview.mdx
@@ -17,12 +17,12 @@ Testing is a critical part of database development, especially when working with
- Functions and procedures
- Data integrity
-This example demonstrates setting up and testing RLS policies for a simple todo application:
+This example demonstrates setting up and testing RLS policies for a basic todo application:
1. Create a test table with RLS enabled:
```sql
- -- Create a simple todos table
+ -- Create a todos table
create table todos (
id uuid primary key default gen_random_uuid(),
task text not null,
diff --git a/apps/docs/content/guides/local-development/testing/pgtap-extended.mdx b/apps/docs/content/guides/local-development/testing/pgtap-extended.mdx
index b7bbefecbea..6401ab340f4 100644
--- a/apps/docs/content/guides/local-development/testing/pgtap-extended.mdx
+++ b/apps/docs/content/guides/local-development/testing/pgtap-extended.mdx
@@ -83,7 +83,7 @@ The test helpers package provides several advantages over writing raw pgTAP test
## Schema-wide Row Level Security testing
-When working with Row Level Security, it's crucial to ensure that RLS is enabled on all tables that need it. Create a simple test to verify RLS is enabled across an entire schema:
+When working with Row Level Security, it's crucial to ensure that RLS is enabled on all tables that need it. Create a basic test to verify RLS is enabled across an entire schema:
```sql
begin;
@@ -112,7 +112,7 @@ This setup file should contain:
1. All shared extensions and dependencies
2. Common test utilities
-3. A simple always green test to verify the setup
+3. A basic always-green test to verify the setup
Here's an example setup file:
diff --git a/apps/docs/content/guides/platform.mdx b/apps/docs/content/guides/platform.mdx
index f4c58fe84a0..3953d8a1862 100644
--- a/apps/docs/content/guides/platform.mdx
+++ b/apps/docs/content/guides/platform.mdx
@@ -5,7 +5,7 @@ description: 'Getting started with the Supabase Platform.'
sidebar_label: 'Overview'
---
-Supabase is a hosted platform which makes it very simple to get started without needing to manage any infrastructure.
+Supabase is a hosted platform that allows you to get started without needing to manage any infrastructure.
Visit [supabase.com/dashboard](/dashboard) and sign in to start creating projects.
diff --git a/apps/docs/content/guides/realtime/broadcast.mdx b/apps/docs/content/guides/realtime/broadcast.mdx
index 6714da11eca..41dc5b96aea 100644
--- a/apps/docs/content/guides/realtime/broadcast.mdx
+++ b/apps/docs/content/guides/realtime/broadcast.mdx
@@ -153,7 +153,7 @@ Binary payloads (`ArrayBuffer` / `ArrayBufferView`) are received automatically f
// Join a room/topic. Can be anything except for 'realtime'.
const myChannel = supabase.channel('test-channel')
- // Simple function to log any messages we receive
+ // Function to log any messages we receive
function messageReceived(payload) {
console.log(payload)
}
@@ -176,7 +176,7 @@ Binary payloads (`ArrayBuffer` / `ArrayBufferView`) are received automatically f
```dart
final myChannel = supabase.channel('test-channel');
- // Simple function to log any messages we receive
+ // Log any messages we receive
void messageReceived(payload) {
print(payload);
}
@@ -241,7 +241,7 @@ Binary payloads (`ArrayBuffer` / `ArrayBufferView`) are received automatically f
# Join a room/topic. Can be anything except for 'realtime'.
my_channel = supabase.channel('test-channel')
- # Simple function to log any messages we receive
+ # Function to log any messages we receive
def message_received(payload):
print(f"Broadcast received: {payload}")
diff --git a/apps/docs/content/guides/realtime/protocol.mdx b/apps/docs/content/guides/realtime/protocol.mdx
index 5170749dfc2..05c524e642b 100644
--- a/apps/docs/content/guides/realtime/protocol.mdx
+++ b/apps/docs/content/guides/realtime/protocol.mdx
@@ -35,7 +35,7 @@ Messages can be serialized in different formats. The Realtime protocol supports
## 1.0.0
-Version 1.0.0 is extremely simple. It uses JSON as the serialization format for messages. The underlying WebSocket messages are all text frames.
+Version 1.0.0 is minimal. It uses JSON as the serialization format for messages. The underlying WebSocket messages are all text frames.
Messages contain the following fields:
diff --git a/apps/docs/content/guides/realtime/subscribing-to-database-changes.mdx b/apps/docs/content/guides/realtime/subscribing-to-database-changes.mdx
index 9984e94d6c2..a32e5609e26 100644
--- a/apps/docs/content/guides/realtime/subscribing-to-database-changes.mdx
+++ b/apps/docs/content/guides/realtime/subscribing-to-database-changes.mdx
@@ -73,6 +73,7 @@ Finally, on the client side, listen to the topic `topic:` to receive
```js
import { createClient } from '@supabase/supabase-js'
+
const supabase = createClient('your_project_url', 'your_supabase_api_key')
// ---cut---
@@ -90,7 +91,7 @@ const changes = supabase
## Using Postgres Changes
-Postgres Changes are simple to use, but have some [limitations](/docs/guides/realtime/postgres-changes#limitations) as your application scales. We recommend using Broadcast for most use cases.
+Postgres Changes require minimal setup, but have some [limitations](/docs/guides/realtime/postgres-changes#limitations) as your application scales. We recommend using Broadcast for most use cases.
diff --git a/apps/design-system/registry/default/example/copy-loading-states.tsx b/apps/design-system/registry/default/example/copy-loading-states.tsx
index db1259dc196..54c053276d5 100644
--- a/apps/design-system/registry/default/example/copy-loading-states.tsx
+++ b/apps/design-system/registry/default/example/copy-loading-states.tsx
@@ -8,13 +8,13 @@ export default function CopyLoadingStates() {
Bad Example
-
@@ -22,13 +22,13 @@ export default function CopyLoadingStates() {
diff --git a/apps/design-system/registry/default/example/inner-side-menu-empty.tsx b/apps/design-system/registry/default/example/inner-side-menu-empty.tsx
index bf4bf8b2fe8..0dfb4c6d029 100644
--- a/apps/design-system/registry/default/example/inner-side-menu-empty.tsx
+++ b/apps/design-system/registry/default/example/inner-side-menu-empty.tsx
@@ -34,7 +34,7 @@ export default function InnerSideMenuEmpty() {
description="Create your first serverless function to get started."
illustration={
- Save changes
+ Save changes
diff --git a/apps/design-system/registry/default/example/sheet-nonmodal.tsx b/apps/design-system/registry/default/example/sheet-nonmodal.tsx
index 203b68fe4bc..fb0bbf2871e 100644
--- a/apps/design-system/registry/default/example/sheet-nonmodal.tsx
+++ b/apps/design-system/registry/default/example/sheet-nonmodal.tsx
@@ -14,7 +14,7 @@ export default function SheetNonmodal() {
return (
- Show Sheet
+ Show Sheet
@@ -29,7 +29,7 @@ export default function SheetNonmodal() {
- Close
+ Close
diff --git a/apps/design-system/registry/default/example/sheet-side.tsx b/apps/design-system/registry/default/example/sheet-side.tsx
index aee3e308180..85011f61b49 100644
--- a/apps/design-system/registry/default/example/sheet-side.tsx
+++ b/apps/design-system/registry/default/example/sheet-side.tsx
@@ -24,7 +24,7 @@ export default function SheetSide() {
{SHEET_SIDES.map((side) => (
- From {side}
+ From {side}
@@ -49,7 +49,7 @@ export default function SheetSide() {
-
+
Save changes
diff --git a/apps/design-system/registry/default/example/single-value-field-array-demo.tsx b/apps/design-system/registry/default/example/single-value-field-array-demo.tsx
index 9c30dc9dbf7..fa7c94c5339 100644
--- a/apps/design-system/registry/default/example/single-value-field-array-demo.tsx
+++ b/apps/design-system/registry/default/example/single-value-field-array-demo.tsx
@@ -45,7 +45,7 @@ export default function SingleValueFieldArrayDemo() {
-
+
Submit
diff --git a/apps/design-system/registry/default/example/sonner-demo.tsx b/apps/design-system/registry/default/example/sonner-demo.tsx
index d2687e6071e..60df9fe7902 100644
--- a/apps/design-system/registry/default/example/sonner-demo.tsx
+++ b/apps/design-system/registry/default/example/sonner-demo.tsx
@@ -4,7 +4,7 @@ import { Button } from 'ui'
export default function SonnerDemo() {
return (
toast('Event has been created', {
description: 'Sunday, December 03, 2023 at 9:00 AM',
diff --git a/apps/design-system/registry/default/example/sonner-types.tsx b/apps/design-system/registry/default/example/sonner-types.tsx
index 0fc1212baee..90720d275b9 100644
--- a/apps/design-system/registry/default/example/sonner-types.tsx
+++ b/apps/design-system/registry/default/example/sonner-types.tsx
@@ -7,11 +7,11 @@ export default function SonnerDemo() {
return (
- toast('Event has been created')}>
+ toast('Event has been created')}>
Default
toast.message('Event has been created', {
description: 'Monday, January 3rd at 6:00pm',
@@ -21,7 +21,7 @@ export default function SonnerDemo() {
description
toast.success('Event has been created', {
description: 'Sunday, December 03, 2023 at 9:00 AM',
@@ -30,26 +30,26 @@ export default function SonnerDemo() {
>
Success
- toast.success('Event has been created')}>
+ toast.success('Event has been created')}>
Show Toast
toast.info('Be at the area 10 minutes before the event time')}
>
Info
toast.warning('Event start time cannot be earlier than 8am')}
>
Warning
- toast.error('Event has not been created')}>
+ toast.error('Event has not been created')}>
Error
toast('Event has been created', {
action: {
@@ -61,11 +61,11 @@ export default function SonnerDemo() {
>
Action
- toast.loading('Event has been created')}>
+ toast.loading('Event has been created')}>
Loading
toast.promise(promise, {
loading: 'Loading...',
@@ -80,12 +80,12 @@ export default function SonnerDemo() {
Promise
toast(
<>
A custom toast with default styling
- Hello world
+ Hello world
>
)
}
diff --git a/apps/design-system/registry/default/example/sonner-upload.tsx b/apps/design-system/registry/default/example/sonner-upload.tsx
index 5d2fcc38b1b..6ccffee9a3b 100644
--- a/apps/design-system/registry/default/example/sonner-upload.tsx
+++ b/apps/design-system/registry/default/example/sonner-upload.tsx
@@ -60,7 +60,7 @@ export default function SonnerUpload() {
return (
{
// random id
const toastId = Math.random()
diff --git a/apps/design-system/registry/default/example/switch-form.tsx b/apps/design-system/registry/default/example/switch-form.tsx
index f0b4a29b0a7..172b5c1f76f 100644
--- a/apps/design-system/registry/default/example/switch-form.tsx
+++ b/apps/design-system/registry/default/example/switch-form.tsx
@@ -83,7 +83,7 @@ export default function SwitchForm() {
/>
{/* TODO: this should be a configure integration where it would show the sheet and the user can disable or delete the integration
but there's no "edit integration" endpoing for now. */}
- onDelete()}>
+ onDelete()}>
Delete integration
diff --git a/apps/studio/components/interfaces/Connect/ConnectDropdown.tsx b/apps/studio/components/interfaces/Connect/ConnectDropdown.tsx
index a2a0b30e9b0..e56f50097a8 100644
--- a/apps/studio/components/interfaces/Connect/ConnectDropdown.tsx
+++ b/apps/studio/components/interfaces/Connect/ConnectDropdown.tsx
@@ -53,7 +53,7 @@ export const ConnectDropdown = ({
}
>
diff --git a/apps/studio/components/interfaces/Connect/ConnectionPanel.tsx b/apps/studio/components/interfaces/Connect/ConnectionPanel.tsx
index 1ca2def2dd5..acbffe37825 100644
--- a/apps/studio/components/interfaces/Connect/ConnectionPanel.tsx
+++ b/apps/studio/components/interfaces/Connect/ConnectionPanel.tsx
@@ -152,7 +152,7 @@ export const ConnectionPanel = ({
title="Transaction pooler is unavailable as pool mode is set to Session"
description="If you'd like to use transaction mode, update your pool mode to Transaction for the connection pooler in your project's Database Settings."
>
-
+
0 && (