## Context
Table Editor - hide "Is unique" configuration for a column that's a
primary key - unnecessary to configure a column as unique if it's
already a primary key (redundant index is created)
## Changes involved
- TableEditor side panel: No longer shows is unique option under
configuration popover if column is a PK
- ColumnEditor side panel: Disable is unique + is nullable option if
column is a PK (Added tooltip)
<img width="810" height="151" alt="image"
src="https://github.com/user-attachments/assets/0f877706-1a56-44b7-864e-ba30efbb67f7"
/>
Also chucked in some minor refactors:
- Refactored some `any` types
- Refactored Column to use the latest Checkbox component
## Problem
The edge function logs table at
`/observability/logs/edge-functions-logs` did not show which edge
function was called. Users had to open individual log entries to find
the function name, even though the information is available in the log
data.
## Fix
- Added `request.pathname` to the SQL SELECT query for
`function_edge_logs` so the pathname is returned with each row.
- Added `extractEdgeFunctionName` utility that parses the last path
segment from the pathname (e.g. `/functions/v1/hello-world-1` becomes
`hello-world-1`).
- Updated `FunctionsEdgeColumnRender` to display the function name
between the HTTP method and the log ID columns.
- Added unit tests for `extractEdgeFunctionName` covering normal paths,
null/undefined, non-string values, and pathnames without slashes.
<img width="1472" height="776" alt="CleanShot 2026-03-19 at 13 18 47@2x"
src="https://github.com/user-attachments/assets/e437f7df-7aab-4ea5-b421-95bab3923605"
/>
## How to test
- Navigate to Logs and Analytics, then Edge Functions logs.
- Confirm each row now shows the function name (e.g. `hello-world-1`)
between the HTTP method and the log ID.
- Confirm rows without a pathname (e.g. non-platform or self-hosted)
still render without errors.
- Confirm clicking a row still opens the log detail panel correctly.
---------
Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
## Problem
We want `ui-patterns` to contain only visual components but
https://github.com/supabase/supabase/pull/43577 introduced a component
with logic about navigation
## Solution
Extract the logic part into a hook and use it in the component.
Next step will be to remove this component and use
`<DiscardChangesConfirmationDialog>` directly along the hook where
needed
## How to test
Check that the fixes from #43577 still work:
On staging, for each case:
- Authentication email templates
- Observability reports
- Edge functions creation
- Edge functions edition
Test:
- Modify the template/report/function
- Navigate away using either the sidebar link, the browser back button
or closing the tab
- Cancel navigation in the confirmation dialog
- Navigation should be prevented and you should not loose your changes
Test:
- Modify the template/report/function
- Navigate away using either the sidebar link, the browser back button
or closing the tab
- Confirm navigation in the confirmation dialog
- Navigation should not be prevented and you should have lost your
changes
## Problem
The database observability dashboard flattens critical spikes when
viewing the 7-day window. A spike clearly visible at the 3-hour view
(2-minute resolution) disappears completely at the 7-day view because
the Prometheus query step was 1 hour, averaging each spike into a
60-minute bucket and reducing its apparent magnitude to near zero.
## Fix
Increase the granularity in the 7 day window to prevent spikes from
being flattened.
Data point counts: 7-day view goes from ~168 to ~336 points per series,
more consistent with the existing 12-hour view (~360 points).
## How to test
- Open the observability database dashboard for a project that has had a
recent CPU, RAM, or connection spike
- Select the "Last 3 hours" time window and confirm the spike is visible
- Switch to "Last 7 days" and confirm the same spike is now visible
(previously it would disappear)
- Confirm all other time windows (10m, 30m, 1h, 24h) still load and
display correctly
---------
Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
## 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?
Issues described in this [Slack
thread](https://supabase.slack.com/archives/C02BJ2239GA/p1740408115511769)
## What is the new behavior?
- Full Storage Migration: Transfers all buckets and their contents.
- Bucket Configuration & Metadata Retention: Maintains settings like
public access, file size limits, MIME types, and file metadata.
- Conflict Resolution Options: Skip, merge (overwrite), or rename
buckets in the target project.
- Safety Measures: Requires user confirmation before destructive
actions.
- Efficient Processing: Batches files (10 per batch) and supports nested
directories.
- Progress & Reporting: Real-time updates, detailed migration summaries,
and error tracking for failed files.
---------
Co-authored-by: Illia Basalaiev <illiab@IMB3.local>
## Context
If you've got a queued operation on a table, then switch tables, the
dashboard stalls for a few seconds before finally rendering the selected
table.
This was caused by an infinite loop in a useEffect calling
`reapplyOptimisticUpdates` due to `dataUpdatedAt` being in the
dependency array (which comes from react query)
Removing `dataUpdatedAt` would resolve the issue, but then it won't
solve the following comment in the code:
`// This ensures pending changes remain visible when switching tabs or
after data refresh`
## Changes involved
Opting to refactor the logic for rendering data in the Grid instead
- Avoid manipulating the data directly from the query client
- Manual changes to the query client are hard to track when debugging
- Ideally the data in the query client are exactly what is coming from
the API
- Instead just compute the row data if there's operations applied, and
render that in the grid
```
const baseRows = data?.rows ?? EMPTY_ARR
const rows = formatGridDataWithOperationValues({ operations, rows:
baseRows })
```
- Simplifies operations logic + data in react query remains as the
source of truth
- This also improves perceived performance, as previously we'd need to
invalidate the query client if we're removing any operation.
- A lot more apparent with the undo operation introduced
[here](https://github.com/supabase/supabase/pull/43957)
- Whereas now, we'll just revert back to whatever's in the query client
(and still do the invalidation behind the scenes) so things feel faster
Upgrades `ai` from v5 to v6 and all related packages.
**Package bumps:**
- `ai`: `5.0.52` → `^6.0.116`
- `@ai-sdk/openai`: `2.0.32` → `^3.0.41`
- `@ai-sdk/react`: `2.0.52` → `^3.0.118`
- `@ai-sdk/provider`: `^2.0.0` → `^3.0.8`
- `@ai-sdk/provider-utils`: `^3.0.0` → `^4.0.19`
- `@ai-sdk/amazon-bedrock`: `^3.0.0` → `^4.0.81`
- `@ai-sdk/mcp`: N/A → `^1.0.25`
- `openai`: bumped to `^4.104.0`
- `braintrust`: `3.0.x` → `^3.4.0`
**Breaking change migrations:**
- `generateObject` removed in v6 — migrated 5 API routes to
`generateText` with `Output.object({ schema })`, returning
`result.output`
- `convertToModelMessages` is now async — added `await`
- MCP import path changed: `experimental_createMCPClient` from `ai` →
`createMCPClient` from `@ai-sdk/mcp`
- `openai()` defaults to Responses API — added `store: false` to
provider options for ZDR org compatibility
**Streaming fix:**
Added `Content-Encoding: none` header to `pipeUIMessageStreamToResponse`
calls. Without it, proxy middleware buffers the entire SSE response
before flushing, causing the full reply to appear at once.
**Zero Data Retention fix:**
In recent AI SDK versions, `openai()` default to Responses API instead
of the legacy chat completions API. This produces a 404 from OpenAI with
message `"Items are not persisted for Zero Data Retention organizations.
Remove this item from your input and try again."` The Responses API is
OpenAI's [recommended
endpoint](https://developers.openai.com/api/docs/guides/migrate-to-responses).
This PR adds `store: false` as mentioned in
https://github.com/vercel/ai/issues/10060 to avoid incompatible
persistence attempts.
**References:**
- https://ai-sdk.dev/docs/migration-guides/migration-guide-6-0
-
https://ai-sdk.dev/docs/troubleshooting/streaming-not-working-when-proxied
- https://github.com/vercel/ai/issues/10060
Closes AI-514
Related AI-509
## 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)
## 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?
Refactor
## What is the current behavior?
The `/incident-banner` endpoint is implemented using the Pages Router.
## What is the new behavior?
The `/incident-banner` endpoint is moved to the App Router, enabling
caching of the upstream fetch. This does not turn on the querying from
the frontend yet, making that a separate PR so we can revert easily if
needed.
## Additional context
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
<img width="1543" height="981" alt="image"
src="https://github.com/user-attachments/assets/8e6c37c5-15c7-4bc4-be87-477e36a62a65"
/>
Switches from two to one column layout for details page and removes an
inconsistent background colour in header. Moves critical detail
information from page into header (url and deploy dates/counts)
## What kind of change does this PR introduce?
- Bug fix that resolves DEPR-396
- Additional improvements to blog post image handling
## What is the current behavior?
Blog post Open Graph metadata often prefers `imgThumb` over `imgSocial`,
so social previews on X, iMessage, and similar surfaces can render the
on-site thumbnail instead of the intended social image.
The image selection and path-normalization rules are also duplicated
across blog surfaces, which makes the precedence rules easy to drift.
## What is the new behavior?
- Centralizes blog image handling in `apps/www/lib/blog-images.ts`
- Uses `imgSocial` first, then `imgThumb`, for blog OG/Twitter metadata
- Uses `imgThumb` first, then `imgSocial`, then the placeholder, for
blog thumbnails and post hero images
- Normalizes relative blog image paths into absolute URLs for metadata
- Adds warning-only validation during content reads/builds for partial
or malformed `imgSocial` / `imgThumb` config
- Updates a few recent blog posts so `imgThumb` is a thumbnail-only
asset instead of duplicating the social image
## Additional context
- Replaces #42319 with the additional above fixes
- Added unit coverage for the shared image helper
---------
Co-authored-by: Alan Daniel <stylesshjs@gmail.com>
## What kind of change does this PR introduce?
Bug fix. Resolves FE-2802. Fixes#43882.
## What is the current behavior?
Second-level foreign key side panels in Table Editor can be dismissed
while dirty without a discard confirmation. That makes accidental
dismissal easy and is inconsistent with the shared dirty-form dismissal
pattern from FE-2802.
## What is the new behavior?
- Adds `DiscardChangesConfirmationDialog` handling to
`ForeignKeySelector`
- Guards all selector close paths behind a local dirty-state check
- Normalizes foreign key state so derived type metadata does not create
false dirty prompts
- Clarifies in `modality.mdx` that route-driven/page-unload flows should
use a navigation guard rather than the dialog/sheet close guard
| Dirty State | Dialog |
| --- | --- |
| <img width="1502" height="899" alt="test Table Editor AWS Healthy
Toolshed Supabase-D1EA9D5F-46EB-4DB5-830D-7CEF36A55B7E"
src="https://github.com/user-attachments/assets/3d866850-d062-4fb7-9949-2fd713e6088f"
/> | <img width="1502" height="899" alt="test Table Editor AWS Healthy
Toolshed Supabase"
src="https://github.com/user-attachments/assets/1396361d-1d44-4206-862f-3379ea22be30"
/> |
## Additional context
Includes a focused unit test for foreign key dirty-state normalization.
## What kind of change does this PR introduce?
Bug fix.
## What is the current behavior?
Webhook endpoint validation is inconsistent across Studio forms. The
webhook sheet accepts incomplete hostnames like `https://webhook`, event
type validation is not surfaced clearly, and HTTP endpoint validation
differs between webhooks, log drains, cron jobs, and database hooks.
## What is the new behavior?
- Tightens webhook endpoint URL validation and rejects incomplete
hostnames while still allowing localhost and IP-based endpoints.
- Surfaces the Event types validation through the standard form error
styling and highlights the existing accordion item border when invalid.
- **Extracts a shared HTTP endpoint URL validator and reuses it in
webhooks, log drains, cron jobs, and database hooks.**
- Adds focused regression tests for the webhook sheet and the
shared/consumer validation paths.
| After |
| --- |
| <img width="1728" height="997" alt="Webhooks Settings AWS Healthy
Toolshed Supabase-CB0D999C-D0BF-47AA-A10F-342A2E328DF9"
src="https://github.com/user-attachments/assets/bcbe4876-f9a7-497a-b288-460087a65546"
/> |
## To test
Form behaviour (in particular URL validation) on:
- Webhook endpoint
- Log drains
- Cron jobs
- Database hooks
## 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
Noticed while working on #43913 that `copilot-instructions.md` is
currently at ~4,600 characters. Per [GitHub's docs on Copilot code
review](https://docs.github.com/en/copilot/how-tos/use-copilot-agents/request-a-code-review/use-code-review):
> Copilot code review only reads the first 4,000 characters of any
custom instruction file. Any instructions beyond this limit will not
affect the reviews generated by Copilot code review.
This means the testing section at the bottom of our current file isn't
being read during reviews.
## Proposal
Split the single file into path-specific instruction files under
`.github/instructions/`, following [GitHub's recommended pattern for
repository custom
instructions](https://docs.github.com/en/copilot/how-tos/configure-custom-instructions/add-repository-instructions):
> These are specified in one or more `NAME.instructions.md` files within
or below the `.github/instructions` directory.
> If the path you specify matches a file that Copilot is working on, and
a repository-wide custom instructions file also exists, then the
instructions from both files are used.
This gives us separate files that each stay under the 4K limit and get
combined automatically by Copilot during reviews:
| File | Size | Scope |
|------|------|-------|
| `copilot-instructions.md` | 929 chars | General repo context +
pointers |
| `instructions/studio-telemetry.instructions.md` | 3,570 chars |
Telemetry rules for `apps/studio/**` |
| `instructions/studio-testing.instructions.md` | 1,228 chars | Testing
rules for `apps/studio/**` |
Note: Copilot reads instructions from the **base branch** of a PR, not
the feature branch — so these won't take effect until merged to master.
### New telemetry guidance
The telemetry file adds guidance we've been missing — specifically
around feature-flagged rollouts:
- Flag PRs that use `usePHFlag`/`useFlag` to gate behavior but don't
capture the flag state in telemetry
- Flag rollouts that track flag state but not user response to the new
behavior
- Documents the raw flag pattern (read via `usePHFlag`, not coerced
wrapper hooks) to avoid the `undefined`→`false` data quality bug we hit
in #43913
### What didn't change
All existing telemetry and testing rules are preserved — nothing was
removed, just reorganized. The telemetry rules still reference
`.claude/skills/telemetry-standards/SKILL.md` as the authoritative
source.
## References
- [Adding repository custom instructions for GitHub
Copilot](https://docs.github.com/en/copilot/how-tos/configure-custom-instructions/add-repository-instructions)
— file structure, path-specific instructions, frontmatter format
- [Using Copilot code
review](https://docs.github.com/en/copilot/how-tos/use-copilot-agents/request-a-code-review/use-code-review)
— 4K character limit, base branch behavior
## Open questions
Would love the team's input on:
- Does the file split make sense, or would you prefer keeping everything
in one file (and trimming to fit)?
- Are there other topics that should get their own instruction file?
- Any concerns with the new feature flag telemetry guidance?
## 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
## What kind of change does this PR introduce?
Chore that resolves DEPR-399.
## What is the current behavior?
The cron jobs table in Studio uses a fixed-width `Name` column, which
can truncate long job titles and make them hard to read on
`/project/:ref/integrations/cron/jobs`.
## What is the new behavior?
The cron jobs table now allows resizing the informational columns,
including `Name`, `Schedule`, `Last run`, `Next run`, and `Command`,
while keeping the `Active` and `Actions` columns fixed-width.
This also gives the `Name` column a sensible minimum width so it can be
resized without collapsing.
## Additional context
Adds a small regression test around the cron jobs column configuration
to verify that:
- informational columns are resizable
- utility columns remain fixed
- the `Name` column has a non-zero minimum width
## 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?
- refactor navigation utils to pass in is_platform
- write unit tests for configuration returns
- default is always passed from constant IS_PLATFORM
## Context
Adds a source filter for the query performance advisor so you can filter
out queries from the dashboard, or not from the dashboard
<img width="309" height="217" alt="image"
src="https://github.com/user-attachments/assets/c1fab9af-e57e-482f-afdb-d77a6600edb3"
/>
For transparency how this works:
- Queries fired via the dashboard through the /query endpoint get
enriched with metadata from the API to include a comment like `--
source: dashboard`
- That's mainly how this filter works atm, to check if this comment
exists if the source "Dashboard" is selected, and the inverse if the
source "Non dashboard" is selected
## Summary
Adds `.github/copilot-instructions.md` to configure GitHub Copilot Code
Review with telemetry and testing guidelines. Replaces CodeRabbit as our
automated PR reviewer. Copilot will now advisory-comment when PRs touch
growth-oriented components (onboarding, upgrade CTAs, A/B experiments)
without telemetry tracking, or when Studio changes lack appropriate test
coverage.
## Changes
- Add `.github/copilot-instructions.md` with:
- Telemetry review rules: event naming (`[object]_[verb]`), property
conventions, `useTrack` enforcement, missing tracking suggestions for
growth surfaces
- Testing review rules: logic extraction to `.utils.ts`, test type
decision tree, file naming conventions
- Repo context and references to full Claude skill docs
## Testing
- [x] Verified `.github/copilot-instructions.md` is the correct path for
Copilot Code Review
- [x] Rules are condensed from existing Claude skills
(`telemetry-standards`, `studio-testing`) — verified alignment
## Linear
- fixes GROWTH-698
---------
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
This PR updates @supabase/*-js libraries to version 2.100.0-canary.0.
**Source**: manual
**Changes**:
- Updated @supabase/supabase-js to 2.100.0-canary.0
- Updated @supabase/auth-js to 2.100.0-canary.0
- Updated @supabase/realtime-js to 2.100.0-canary.0
- Updated @supabase/postgest-js to 2.100.0-canary.0
- Refreshed pnpm-lock.yaml
This PR was created automatically.
Co-authored-by: mandarini <6603745+mandarini@users.noreply.github.com>
## 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?
Refactor
## What is the current behavior?
`/incident-status` is handled via Pages Router.
## What is the new behavior?
`/incident-status` is handled via App Router, enabling use of Vercel
Data Cache to cache the upstream fetch.
## Additional context
Adding the first App Router route handler triggered `next typegen` (run
as `pretypecheck`) to generate `.next/dev/types/validator.ts`, which
imports all route files and expanded the type-checked graph. This
surfaced pre-existing `null`-safety errors in:
- `components/grid/SupabaseGrid.utils.ts` — `useSearchParams()` result
- `components/layouts/ProjectLayout/UpgradingState/index.tsx` —
`useSearchParams()` result
- `pages/project/[ref]/sql/quickstarts.tsx` — `useParams()` result
- `pages/project/[ref]/sql/templates.tsx` — `useParams()` result
These are fixed with optional chaining. The `tsconfig.json` change
(adding `.next/dev/types/**/*.ts` to `include`) is auto-generated by
Next.js and committed as correct behavior.