## Summary
The `connectSection` A/B experiment concluded as a true null (no effect
on activation or any downstream metric after 13 days at 50/50, ~153K
mature orgs). Saxon decided to ship the Connect section as the permanent
experience. This PR removes the Getting Started control variant, the old
Connect modal, all experiment flag gating, and related telemetry types.
## Changes
- Delete `GettingStarted/` directory (5 files: section component, types,
utils, progress hook)
- Delete old `Connect.tsx` dialog modal (replaced by ConnectSheet)
- Remove `connectSection` PostHog flag reads from `Home.tsx` and
`LayoutHeader.tsx`
- Remove `getSectionVisibility()` experiment logic and
`ConnectSectionVariant` type
- Remove `getting-started` from `DEFAULT_SECTION_ORDER`
- Always render `<ConnectSheet />` in header (no more conditional with
old `<Connect />` modal)
- Remove `variant` prop from `ConnectSection` component
- Remove 4 getting-started telemetry event interfaces from
`telemetry-constants.ts`
- Update `mergeSectionOrder` tests to reflect new section order
## Testing
Tested on Vercel preview:
- [x] Project homepage shows Connect section for new projects (< 10 days
old)
- [x] Connect section hidden for mature projects (> 10 days old)
- [x] Header Connect button opens ConnectSheet (not old modal)
- [x] Connect tiles open ConnectSheet with correct tab
- [x] Section drag-and-drop still works without getting-started in the
order
- [x] Existing users with `getting-started` in localStorage order don't
break (mergeSectionOrder strips it)
## Linear
- fixes GROWTH-730
---------
Co-authored-by: Alaister Young <alaister@users.noreply.github.com>
## Context
Related to marketplace integrations
Shifts Database Webhooks integration to the new Integrations UI. This
one's a bit different from the previous PRs as this involves a full SQL
installation query instead of only just a database extension. So am
tweaking `Integrations.constants` a little.
For context eventually all the integrations will be pulled remotely from
a database, so am still trying to figure out an optimal data structure,
but requirements will be clearer as we build out the UI
RE installing integrations:
- For now, if the integration has a provided SQL installation command,
that'll take precedence
- Else, if the integration has a provided SQL installation query, we'll
use that on the /query endpoint
- Otherwise, if the integration only requires database extensions,
dashboard will generate the queries to install the extensions
- In the case of the former tho, we won't allow users to choose which
schema to install the extension in too
Just ping me if any clarification's required!
## To test
- [ ] Verify that you can install the database webhooks with the new
integration UI
- [ ] Verify that behaviour is status quo without the new integration UI
## What kind of change does this PR introduce?
Component update.
## What is the current behaviour?
TanStack tables in the repo are split between the shared `TableHeadSort`
primitive and the older Studio-local `DataTableColumnHeader` helper,
which makes the sorting UI and integration path inconsistent.
If you were to just use `DataTableColumnHeader` in `ui-patterns/Table`,
you’d get a very different visual result to the `TableHeadSort` UI you
see in most other tables.
## What is the new behaviour?
Adds a shared `TanStackTableHeadSort` adapter in `ui-patterns/Table`,
backed by the existing `TableHeadSort` primitive, and switches the
webhook table plus the design-system TanStack demo to that canonical
path. `DataTableColumnHeader` stays as a deprecated wrapper for now,
Studio gets a lint guard to block new imports of it, and the table docs
now point TanStack tables at the shared adapter explicitly.
## To test
Check out column sorting on the Platform Webhook endpoint deliveries
table.
This PR moves several components which rely on `next` out of the `ui`
package to the `ui-patterns` package.
`ui-patterns` package is intented to be imported with specific imports
so it's ok if there are components reliant on `next` in there.
The `SonnerToaster` component has removed its dependency by requiring a
prop for `theme`.
## Context
Related to marketplace related work, just moves the Queues integration
to the new UI (Changes are feature flagged)
<img width="1145" height="584" alt="image"
src="https://github.com/user-attachments/assets/d3245889-597d-44e2-9850-f20907e42056"
/>
Installation is now in a side panel with the intention that it'll just
be a single click to install integrations that involve multiple parts
<img width="400" height="955" alt="image"
src="https://github.com/user-attachments/assets/71903b61-6bd2-486c-903e-b48ae2133887"
/>
## To test
- Verify that you can install the integration and everything else should
be status quo
- Verify that everything should be status quo if the flag is off
## What kind of change does this PR introduce?
UI update that resolves DEPR-114. Also resolves DEPR-113.
## What is the current behavior?
- The breadcrumbs on the file explorer have some rough edges in column
view
- Fancy hide/show behavior
- Hidden tap targets
- `FileExplorerHeader` actions can overflow on the x-axis
- The Navigate button is only shown on hover
- The inline Navigate flow does not work well on smaller screens
## What is the new behavior?
- Column view now shows the same in-explorer breadcrumb trail as list
view
- The active breadcrumb is visually emphasized, while inactive
breadcrumbs remain clickable
- The back affordance now uses a clearer arrow treatment with a stronger
separator from the breadcrumb trail
- The Navigate button is permanently visible and moved to the right-side
action group before Reload
- Navigate now opens a dialog on both desktop and mobile
- Added typed telemetry so we can measure `Navigate` usage before
deciding whether to keep or remove it
- Fixed header overflow by letting the full header contents scroll
horizontally together instead of visibly spilling out
| Before | After |
| --- | --- |
| <img width="947" height="997" alt="Buckets Storage AWS Healthy
Toolshed Supabase"
src="https://github.com/user-attachments/assets/fa53fdd4-954c-4832-bf9b-210b63ae020b"
/> | <img width="947" height="997" alt="Buckets Storage AWS Healthy
Toolshed Supabase"
src="https://github.com/user-attachments/assets/3689a0e5-97d1-4b36-a2dd-7adce23add5d"
/> |
| <img width="864" height="997" alt="Buckets Storage AWS Healthy
Toolshed Supabase"
src="https://github.com/user-attachments/assets/ad559118-205f-40e2-b3c5-97cef462d5f5"
/> | <img width="864" height="997" alt="Buckets Storage AWS Healthy
Toolshed Supabase"
src="https://github.com/user-attachments/assets/9c569b29-7c58-4a33-b809-34d6ed919008"
/> |
## Additional context
Also added a link to the `Buckets` portion of the `PageHeader`
breadcrumb:
```text
Files > Buckets > MyBucketName
```
It goes to the same place as Files because the root Files page lists
buckets, but having both links there feels more ergonomic in practice.
---------
Co-authored-by: Ali Waseem <waseema393@gmail.com>
## Problem
Follow-up to #44252. The previous fix handled the case where the user
waits on the page after accepting (GTM writes `ucData`), but there's a
second scenario: if the user accepts and navigates to another app
quickly (before GTM finishes), `ucData` hasn't been written yet. The SDK
on the new app overwrites `uc_user_interaction: "true"` with `"false"`
and shows the banner again.
## What changed
`hasPreviousConsentInUcData` is now `detectPriorConsent` and checks two
signals before `UC.init()` overwrites them:
1. **Slow navigation** (existing): `ucData` contains all services with
`consent: true`
2. **Fast navigation** (new): `uc_user_interaction` is `"true"` — the
SDK on the previous app wrote this but GTM hasn't had time to replace it
yet
Also adds unit tests covering both scenarios, edge cases (empty
services, malformed JSON, mixed signals), and the combined behavior.
## Testing
- 13 unit tests for `detectPriorConsent()` covering all localStorage
state combinations
- Can't fully reproduce on staging previews (CSP blocks GTM), verified
root cause via production console monitoring
Closes FE-2648
## 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?
Removes the control variant and replaces it with the test variant as
winner.
## What is the current behavior?
-
## What is the new behavior?
-
## Additional context
Add any other context or screenshots.
## Problem
After PR #43221 gated `TelemetryTagManager` behind consent, the EU
cookie consent banner started reappearing on every page load and when
navigating between apps (www, studio, docs).
Back in late February we changed `TelemetryTagManager` to only load when
the user has accepted consent. This was the right call for GDPR — don't
load tracking scripts before consent. But it created a chicken-and-egg
problem with how the Usercentrics SDK stores consent.
## What happened
When a user clicks Accept, the SDK writes `uc_settings` +
`uc_user_interaction: true` to localStorage. Then the GTM script loads
(now that consent is granted), and its Usercentrics integration
immediately replaces those keys with a compressed `ucString` + `ucData`
format — deleting the originals.
On the next page load, `UC.init()` only knows how to read `uc_settings`.
It can't find it (GTM deleted it), so it treats the user as brand new
and shows the banner again. Before #43221, GTM loaded on every page
unconditionally, so its integration was already present during
`UC.init()` and could interpret the compressed format.
Confirmed via production console monitoring — the exact sequence after
clicking Accept:
```
setItem("uc_settings", ...) // SDK writes consent
setItem("uc_user_interaction", "true") // SDK marks interaction
removeItem("uc_settings") // GTM deletes SDK format
removeItem("uc_user_interaction") // GTM deletes SDK format
setItem("ucString", ...) // GTM writes compressed format
setItem("ucData", ...) // GTM writes compressed format
```
## Changes
- Read `ucData` from localStorage **before** `UC.init()` to detect prior
consent in the compressed format
- If the SDK wants to show the banner but `ucData` shows all services
were previously accepted, silently re-accept instead of re-prompting
- Added try/catch around the SDK initialization (was fire-and-forget
with no error handling, any failure was completely silent)
- Error fallback also honors prior `ucData` consent if the SDK fails to
initialize
## Testing
Can't fully reproduce on staging previews because CSP blocks the GTM
script there (so the storage migration never fires). Verified the root
cause via production console monitoring with localStorage
monkey-patching, and confirmed the `ucData` format persists across page
loads on production.
Closes FE-2648
## Problem
- The auth providers forms still use `formik` and we want to remove it
in favour of `react-hook-form` to keep only one form library
- The auth providers forms do not follow the design system guidelines
## Solution
- Migrate to `react-hook-form`
- Apply the design system guidelines
## Screenshots
<img width="1530" height="1920" alt="image"
src="https://github.com/user-attachments/assets/04627e93-2aa5-4a7f-a24e-0ae41d6e6b10"
/>
---------
Co-authored-by: Danny White <3104761+dnywh@users.noreply.github.com>
## Context
Shifts all remaining dashboard queries into pg-meta so that we
centralize all manually written queries in one place
Having them in packages/pg-meta also allows us to write tests for them
## To test
Just needs a smoke test on
- Role Impersonation
- Lints
- Data API
- Database
- Enumerated Types
- Integrations
- Foreign Data Wrappers
- Vault
## Context
Edge functions code editor which uses the FileExplorerAndEditor
component doesn't resize when the viewport shrinks
This PR fixes that + also refactors the FileExplorerAndEditor a bit to
resolve the lint issue with `nodeRenderer` by refactoring the prop into
a renderer that uses `useCallback`
## What kind of change does this PR introduce?
Chore that references DEPR-394.
## What is the current behavior?
Key/value editors for headers are implemented separately in multiple
places.
## What is the new behavior?
DEPR-394 is consolidating repeated RHF field-array UIs across Studio and
the design system.
- adds a shared `KeyValueFieldArray` component in `ui-patterns`
- adds a shared `httpHeaderAddActions` helper for preset header rows
- migrates the key/value header editors in:
- Platform Webhooks
- Cron Jobs HTTP headers
- Database Webhooks HTTP headers
- documents the key/value pattern in the design system with:
- a dedicated fragment page
- updated forms guidance
- updated form pattern demos
| Preview |
| --- |
| <img width="1102" height="420" alt="CleanShot 2026-03-23 at 12 22
18@2x"
src="https://github.com/user-attachments/assets/f8d23ff9-7063-462f-8074-b400561f77e9"
/> |
## Additional context
This is PR 1 of a 3-PR stack for DEPR-394.
## 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?
This is a prototype for private apps UI. There are no endpoints at the
minute, just wanted to see what a potential flow could look like.
Adds `chatId` (the chat UUID) to the three assistant PostHog events so
we can count distinct chat sessions in PostHog. This naming is
consistent with how we name the field in Braintrust logs.
Also migrates from the deprecated `useSendEventMutation` hook to
`useTrack` — groups (project/org) are still sent automatically by
`useTrack`.
Closes AI-519
## Context
Shifting more dashboard queries into pg-meta so that we centralize all
manually written queries in one place
Having them in packages/pg-meta also allows us to write tests for them
## To test
Just needs a smoke test on
- Table Editor
- Fetching entities
- Viewing definition
- SQL Editor
- View ongoing queries
- Abort queries
- Integrations
- Queues
- Database
- Migrations
-Triggers (Updating)
Fixes#42089
Supersedes #43352 and
https://github.com/supabase/postgres-meta/pull/1049
## Problem
When creating a table in the Dashboard, if a column-specific error
occurs (e.g., invalid enum value or broken foreign key), the Dashboard
displays an error toast, but the side panel remains open. In the
background, the table is actually created (partially), leading to a
_42P07: relation already exists_ error if the user tries to click _Save_
again.
## Solution
We actually had nested transactions which is not supported by Postgres.
- [x] Allow generating SQL without transactions from `@supabase/pg-meta`
- [x] Fix the table creation
- [x] Fix some accessibility issues
- [x] Add tests
## How to test
1. Click _New table_ in the Table editor
2. Add a column with an _int8_ type and set its default value to
`bazinga`
3. Click _Save_
You should see an error.
4. Fix the default value by setting it to `10`
5. Click _Save_
Results:
- You should see a success message about the table creation
- The table should have the column with the correct default value
## Problem
PR #43704 added the `tableEditorApiAccessToggle` flag to revoke default
privileges on project creation, but there's no PostHog instrumentation
to measure the rollout or understand how users respond to the new
behavior.
## Changes
**1. Flag state on project creation**
(`project_creation_simple_version_submitted`)
Adds `tableEditorApiAccessToggleEnabled` property — reads the raw
PostHog flag via `usePHFlag` rather than going through
`useDataApiGrantTogglesEnabled`, which coerces `undefined` (flag still
loading) to `false` and would silently poison the data. When the flag
hasn't loaded, the property is omitted from the event entirely.
**2. Per-table toggle tracking** (`table_api_access_toggle_clicked`)
New event that fires when a user flips the Data API access switch in the
table editor side panel (new tables only — existing tables link out to
settings). Tracks `newState: 'enabled' | 'disabled'` and `schemaName` so
we can distinguish public-schema toggles from custom schemas.
Together these let us answer: what % of projects have the new defaults,
and how do those users respond (do they opt tables back in, and in which
schemas)?
Part of the Secure by Default initiative (#43704)
## Context
Similar to how we added a banner for the new table filter bar - mainly
to improve visibility for this feature preview as we'd like some
feedback from usage
<img width="313" height="314" alt="image"
src="https://github.com/user-attachments/assets/4cea6383-483a-42cf-b4a5-bb8c3918c00d"
/>
## Other changes
- Also adding some typing to the `addBanner` and `dismissBanner`
- Removed banner for table editor filter bar
When the `tableEditorApiAccessToggle` feature flag is enabled, project
creation now appends SQL to revoke default privileges for `anon`,
`authenticated`, and `service_role` on the `public` schema. This runs
after the base image init script's default grants. This is temporary
while we're still using a feature flag. Eventually it'll be moved into
the base image.
Applies to both the main project creation flow and the Vercel deploy
button flow.
Part of the "Secure by Default" initiative – new projects created under
this flag won't automatically expose tables/functions/sequences to the
Data API via default privileges. Users can still opt in at a table
level.
## Notes
Reusing the existing `useDataApiGrantTogglesEnabled()` flag here rather
than creating a new one – it's the same feature surface area and avoids
unnecessary flag proliferation.
## To test
1. **With flag enabled:**
- Enable the `tableEditorApiAccessToggle` flag in PostHog for your user
- Create a new project via the dashboard
- Create a new table
- Confirm in `/project/_/integrations/data_api/settings` that the new
table is not exposed by default
2. **With flag disabled:**
- Disable the flag (or use a different user without it)
- Create a new project
- Verify default privileges are intact and tables are accessible via the
Data API as usual
3. **With RLS event trigger enabled too:**
- Enable both the feature flag and the "enable RLS event trigger"
checkbox during project creation
- Verify both SQL statements run correctly on the new project
---------
Co-authored-by: Joshen Lim <joshenlimek@gmail.com>
Co-authored-by: Alaister Young <10985857+alaister@users.noreply.github.com>
### FAQ (`type: 'faq'`)
Accordion-style FAQ with expand/collapse. Each item has a `question` and
`answer`. Click to toggle — only one open at a time.
<img width="1309" height="610" alt="Screenshot 2026-03-13 at 17 31 31"
src="https://github.com/user-attachments/assets/289c8a12-3835-4f64-bbe6-fb7095df4e7c"
/>
### Code Block (`type: 'code-block'`)
Syntax-highlighted code display using shiki with custom Supabase
dark/light themes. Supports:
- **Single file** — `code` + optional `filename` + `language`
- **Multi-file** — `files: [{ filename, code, language }]` with
clickable tabs
- Line numbers via CSS counters
- All highlighting runs at build time (server component), only tab
switching is client-side
<img width="1283" height="415" alt="Screenshot 2026-03-13 at 17 32 07"
src="https://github.com/user-attachments/assets/9cc9a215-d5c9-47c9-8e21-c1dd3beca4ba"
/>
### Steps (`type: 'steps'`)
Numbered step-by-step guide with a vertical timeline connector. Each
item has `title` and either a plain `description` string or a `content`
slot accepting any React node (e.g. images, code blocks).
<img width="1119" height="810" alt="Screenshot 2026-03-13 at 17 32 20"
src="https://github.com/user-attachments/assets/cb67aaab-9ed4-42e2-bf1c-8d836024e469"
/>
### Quote (`type: 'quote'`)
Centered testimonial block with `quote`, `author`, optional `role`, and
optional `avatar` image.
<img width="1095" height="238" alt="Screenshot 2026-03-13 at 17 32 37"
src="https://github.com/user-attachments/assets/356a39ca-9f65-4414-bf77-6060993594a4"
/>