mirror of
https://github.com/supabase/supabase.git
synced 2026-10-09 19:35:06 +03:00
master
10
Commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
|
|
a8b2f23091 |
fix(studio): restore deployment update metadata (#51048)
Deployment update checks now receive a timestamp from GitHub’s documented commit API instead of silently falling back to `unknown` when its website response changes. Valid deployment metadata is cached for ten minutes; development and failed lookups are uncached so they can recover. **Changed:** - Validate and normalize the committer date in the shared Next/TanStack handler, preserving the existing response shape and `unknown` fallback. - Exclude only the exact deployment-metadata endpoint from TanStack’s private API cache default; authenticated APIs and server functions retain it. - Keep the client update query unpinned and its existing toast threshold unchanged. **Added:** - Shared-handler tests through both Next and the TanStack adapter for dates, malformed payloads, upstream failures, and recovery. - Tests using the installed Vercel route compiler for root and `/dashboard` cache rules, security headers, and empty Next configuration. ## To test - On the TanStack preview, request `/dashboard/api/get-deployment-commit`; compare its SHA and UTC timestamp with the deployed commit’s GitHub committer date. - Repeat the request to check CDN caching. Vercel consumes `s-maxage`, so use cache-hit/age evidence as well as client-visible headers. - Confirm another API route and a server-function path retain `private, no-store`. - Open an existing project, reload it while clean, and inspect the untouched support form for metadata-related errors. Validation: 60 focused tests, Studio typecheck, scoped ESLint, formatting, knip, and both framework production builds passed. Live unauthenticated GitHub lookup with the configured API version returned the expected committer date. Full source lint ratchet also passed, excluding only generated build directories. Local TanStack browser checks passed for clean project/reload, general settings, untouched support form, and naturally emitted development metadata formatting; no errors or unexpected update toast appeared. The positive two-deployment toast and submitted support-version formatting were not exercised. Deployed native Next previews returned the exact commit SHA and expected UTC timestamp; repeated metadata requests produced CDN HIT responses (ages 26 and 100 seconds). Build logs establish that the staging preview also ran Next, so it does not validate TanStack edge header behavior. A separate preview-only redeployment with a deployment-scoped TanStack override was confirmed to run Vite. It returned the same correct SHA/timestamp, a repeat CDN cache HIT, and private, no-store on the neighboring UTC API. No project settings or production aliases were changed. Installed Vercel compiler tests cover the remaining root/base-path and server-function rules. No new environment variable, token, or dependency is required. Co-authored-by: Alaister Young <10985857+alaister@users.noreply.github.com> |
||
|
|
1966209483 |
chore(deps): upgrade vitest to v5 (#49994)
Upgrades Vitest from 4.1.4 to 5.0.0 across the monorepo, fixes the handful of things v5 turned into hard errors, and drops the `vi.clearAllMocks()` boilerplate that v5's `clearMocks` default makes redundant. **Changed:** - `vitest`, `@vitest/ui`, `@vitest/coverage-v8` 4.1.4 → 5.0.0 (catalog) - `vi.mock` calls that lived inside `beforeAll`/`beforeEach`/test bodies moved to module scope (v5 throws on nested calls). Affects the Studio and docs setup files and four Studio tests. - `detectBrowser` test restores `navigator` via `vi.unstubAllGlobals()` instead of assigning `global.navigator`, which now reaches jsdom's getter-only property. - `RowEditor.utils.test.ts` restores its `JSON.stringify` spy. It used to leak a throwing mock for the rest of the file, which v5's coverage provider now trips over. A later test in the same file had been asserting the leak's side effect (valid JSON reported as invalid) and now asserts the correct behavior. - `@testing-library/jest-dom` 6.6 → 7.0.1. Its vitest type augmentation resolves through a peer now, so it lands on each package's own `vitest` instead of whichever copy pnpm hoisted. Fixes `toBeInTheDocument` type errors in dev-tools after the reshuffle. - `@testing-library/react` 16.0.0 → 16.3.3 for the React 19 peer range. - `vite: catalog:` added to dev-tools, www, and common. Without it they resolved a newer vite than the catalog pin, which forked a second vitest instance in the lockfile. There's now one. - ai-commands custom matcher types use v5's `Matchers<R, T>` form. - 110 test files: `vi.clearAllMocks()` removed from `beforeEach`/`afterEach` hooks, along with hooks that only did that and the imports they left unused. Calls that also reset/restore mocks are untouched. Second commit, mechanical. **Added:** - `.vitest/` to the root gitignore (v5 writes JSON/JUnit/HTML reporter output there) **Removed:** - `vite-tsconfig-paths` catalog entry and deps. Vitest 5 resolves tsconfig paths itself. Release-age note: this sat in draft with a temporary `minimumReleaseAgeExclude` entry for `vitest` and `@vitest/*` while 5.0.0 was inside the workspace's 3-day `minimumReleaseAge` window. That window has closed, so the exclusion is gone and nothing bypasses the release-age gate. **Perf** (local, medians of 3 runs, same machine): | Suite | v4.1.4 | v5.0.0 | |---|---|---| | studio | 144.1s | 141.7s (-2%) | | studio `--coverage` | 156.9s | 146.4s (-7%) | | ui-patterns | 6.27s | 5.07s (-19%) | | ui `--coverage` | 3.35s | 2.14s (-36%) | | www | 0.89s | 0.47s (-47%) | Studio is dominated by jsdom environment setup per file, which v5 doesn't change. `vitest doctor` recommends keeping the current pool config: the vm pools and `isolate: false` all break tests. ## To test - `pnpm install --frozen-lockfile` succeeds with no `minimumReleaseAgeExclude` entry for vitest. - CI: Studio unit tests, ui, ui-patterns, www, docs, and typecheck/lint should all be green. The lint ratchet was checked locally: warning counts on touched Studio files are identical to master. - `pnpm test:studio` locally passes with coverage (588 files, 6240 tests). - Open a Studio test that uses `toBeInTheDocument` in your editor and confirm no type errors on jest-dom matchers, in Studio and in `packages/dev-tools`. - Known pre-existing failures unrelated to this PR: one dev-tools test (`getEventCountBadge` capped pill) fails on master too. <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit ## Tests - Improved test coverage for JSON validation and mobile navigation behavior. - Updated test setup, cleanup, environment configuration, and matcher support across application and shared package suites. - Removed obsolete coverage for alternate MCP transport selection. ## Chores - Streamlined TypeScript path resolution and Vitest reporter output handling. - Updated testing libraries and Vitest tooling across documentation, Studio, website, and shared packages. - Added Vitest reporter output to ignored files. <!-- end of auto-generated comment: release notes by coderabbit.ai --> --------- Co-authored-by: Alaister Young <10985857+alaister@users.noreply.github.com> Co-authored-by: Ivan Vasilov <vasilov.ivan@gmail.com> |
||
|
|
058b546b56 |
fix(studio): send API keys on the apikey header in the edge function tester (#49650)
<!-- ccr-slack-attribution --> _Requested by **Kalleby Santos** · [Slack thread](https://supabase.slack.com/archives/C0AQ3UHCCKW/p1787840441551609?thread_ts=1787840441.551609&cid=C0AQ3UHCCKW)_ **Before:** you deploy the editor's default template ("Deploy a new function" → "Via Editor"), which wraps its handler in `withSupabase({ auth: ["publishable", "secret"] })`. You click **Test** and get `401 {"message":"Invalid credentials","code":"INVALID_CREDENTIALS"}` — from the function's own middleware, with an empty Headers section. Studio was quietly setting `Authorization` to a legacy `service_role` JWT (and, before that, to your dashboard session token), routed through a private `x-test-authorization` header that the proxy route renamed to `Authorization`. A legacy JWT is neither a publishable nor a secret key, so the middleware rejected it. Pasting your own `Authorization` row did not help: the route overwrote it unconditionally. On a project with legacy keys disabled there was no `service_role` key at all and the literal string `Bearer undefined` went out. **After:** the tester sends your publishable key on the `apikey` header, where new-format keys belong, and never generates an `Authorization` header. `Authorization` only ever comes from your own header rows — typed by hand, or prefilled for you by the role selector. The editor's default template works on the first click, a header you paste is actually sent, and an **Add secret key** action in the "Add header" dropdown gives you one-click access to a secret key, the same affordance the database webhooks and cron job screens already have. **How:** header construction moves into `buildEdgeFunctionTestHeaders` (`EdgeFunctionTesterSheet.utils.ts`), which sets `Content-Type` and `apikey` and then applies the user's rows last. The `x-test-authorization` hop is gone from both the component and `pages/api/edge-functions/test.ts`; the route now forwards the supplied headers as given. Both sides merge on the lowercased header name, so a row typed `authorization` or `apikey` replaces the generated one instead of sitting beside it and being comma-joined by `fetch`. The Headers and Query Parameters sections now use the shared `KeyValueFieldArray`, which is what makes `buildEdgeFunctionHeaderAddActions` reusable here. ## 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? Bug fix. ## What is the current behavior? Fixes #42755. - `EdgeFunctionTesterSheet.tsx` sent the legacy `service_role` JWT (or a role-impersonation JWT) as the value of `x-test-authorization` on every request, plus the dashboard session access token as `Authorization`. - `pages/api/edge-functions/test.ts` then overwrote `Authorization` with `x-test-authorization` whenever that header was present, discarding any `Authorization` the user had entered. - No `apikey` header was ever sent, so `withSupabase` in `publishable` or `secret` auth mode — the modes used by the editor's own templates — could never succeed. - Header merging was case-sensitive on both sides of the proxy, so a row typed in the conventional lowercase form produced two entries that `fetch` comma-joined into one malformed value. - The API keys query did not pass `reveal: true`, unlike the webhooks and cron job UIs. ## What is the new behavior? - `apikey` carries the publishable key, falling back to the legacy `anon` key. This mirrors the example snippets on the function details page, which already prefer `publishableKey ?? anonKey`. Defaulting to the least-privileged key means a secret key is only ever sent when the user explicitly adds it. - `Authorization` is never generated. The `useSessionAccessTokenQuery` call is removed from this component entirely — the dashboard user's own session token has no business being forwarded to a project's function. - `x-test-authorization` is removed from both files. The proxy route stays, because it is what reads the raw upstream response for the response panel (`redirect: 'manual'`, full status/header/body capture), keeps the request off the browser's CORS path, and holds the `isValidEdgeFunctionURL` guard and the local-dev URL rewrite. Only the header rewriting is gone. - Role impersonation keeps working, but as a visible, editable `Authorization` row rather than a hidden injected header, so what is sent is always what is displayed. Two details worth reviewing: the selector tracks the value it last wrote, so clearing the role removes only that row and leaves an `Authorization` row you typed by hand alone; and an incrementing request id discards a JWT that resolves after a newer role has already been picked. - Headers merge case-insensitively, user rows winning. - `reveal: true` is passed on the API keys query, matching `Database/Hooks/HTTPHeaders.tsx`. ## Additional context **Relationship to #47159.** #47159 identified the same root cause independently and got the important part right: the key belongs on `apikey`, and neither the legacy service-role JWT nor the dashboard session token should be forwarded. Its extraction of a testable header builder is a good shape, and this PR keeps it — including the spirit of its test suite. The differences are in scope rather than direction. This PR also removes the `x-test-authorization` hop and the route's unconditional `Authorization` overwrite (#47159 leaves the route untouched); drops the remaining legacy service-role fallback rather than keeping it for projects without a publishable key; adds `reveal: true`, secret-key support and the shared "Add secret key" affordance; and normalizes header casing for every header rather than only `x-test-authorization`. Whether to land that PR first and layer this on top, or take this one, is the maintainers' call — either way the credit for spotting it belongs there too. **Overlap with #48143.** That open PR fixes the same case-sensitivity defect for `Content-Type` in these two files. It is not addressed separately here, but the case-insensitive merge in this PR covers `Content-Type` as a side effect, so the two will conflict textually. Happy to rebase on whichever lands first. **A note on `verify_jwt`.** The gateway creates a temporary token when `apikey` is present, so `verify_jwt` does not affect this path and a request with `apikey` and no `Authorization` reaches the function normally. No deploy defaults are changed here. **Compatibility.** One behaviour gets worse and is worth an explicit decision: a function that expects a legacy JWT on `Authorization` used to "just work" in the tester because Studio injected the service-role key. It now needs an `Authorization` row, which the **Add secret key** action produces in one click — the shared helper already emits an `Authorization: Bearer` row for legacy-format keys. Projects with legacy keys disabled strictly improve: they used to receive `Bearer undefined`. Functions using `auth: "user"` are unchanged — the tester never had a real end-user JWT, only the impersonation token. ## Testing `apps/studio` dependencies could not be installed in the environment this was written in (`pnpm install` fails on a 403 from `npm.jsr.io`), so `vitest`, `tsc --noEmit` and `eslint` were not run. What was run instead: - Prettier with the repo's config, including `@ianvs/prettier-plugin-sort-imports`: clean on all five files. - `tsc` parse of the changed files: no syntax or type errors beyond pre-existing unresolved-module noise. - Both new test suites transpiled and executed as plain Node assertions: 7/7 for `buildEdgeFunctionTestHeaders`, 4/4 driving the API route handler with a stubbed `fetch`. Please run the real suites in CI. `pnpm --filter studio exec vitest --run tests/components/Functions/EdgeFunctionTesterSheet.utils.test.ts tests/pages/api/edge-functions/test.test.ts` covers the added tests. A component-level test of the impersonation prefill is not included and would be a reasonable follow-up. 🤖 Generated with [Claude Code](https://claude.com/claude-code) --------- Co-authored-by: Claude <noreply@anthropic.com> Co-authored-by: Kalleby Santos <105971119+kallebysantos@users.noreply.github.com> |
||
|
|
83e6552d71 |
fix: preserve function responses (#47920)
- adds up to: https://github.com/supabase/cli/pull/5862 <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit * **New Features** * Added an “Error docs” link in Edge Function testing UI when an `sb-error-code` header is present. * **Bug Fixes** * Improved the Edge Function test proxy to consistently preserve upstream status, headers (including repeated headers), and response bodies without transformation. * Enhanced handling for invalid function URLs and upstream fetch failures. * **Tests** * Added unit, API, and Playwright E2E coverage for error docs linking and response proxy behavior. <!-- end of auto-generated comment: release notes by coderabbit.ai --> |
||
|
|
b28f91741f | fix(self-hosted): reveal and copy secret api key in project settings (#46592) | ||
|
|
c1276c8e9a | feat(self-hosted): add new API keys to self-hosted Studio and MCP server (#46173) | ||
|
|
1b1d05ff96 |
chore: upgrade vite to v8 and vitest to v4 (#44833)
Upgrade vite and vitest to their latest major versions across the
monorepo, along with related packages.
**Changed:**
- `vite` catalog: `^7.3.2` → `^8.0.8` (Rolldown replaces esbuild/Rollup)
- `vitest` catalog: `^3.2.0` → `^4.1.4`
- `@vitejs/plugin-react`: `^4.3.4` → `^6.0.1`
- `@vitest/coverage-v8`: `^3.2.0` → `^4.1.4`
- `@vitest/ui`: `^3.2.0` → `^4.1.4`
- `vite-tsconfig-paths`: `^4.3.2` / `^5.1.4` → `^6.1.1`
**Pinned to vite 7:**
- `apps/lite-studio` — `@react-router/dev` hasn't declared vite 8
support yet
- `blocks/vue` — Nuxt plugins (`vite-plugin-inspect`, `vite-dev-rpc`,
`vite-hot-client`, `vite-plugin-vue-tracer`) haven't declared vite 8
support yet
**Test fixes for vitest 4 breaking changes:**
- **`apps/studio/lib/api/snippets.utils.test.ts`** — Replaced
`vi.mock('fs/promises')` automock with an explicit factory. Vitest 4's
automocking doesn't create mock functions for getter-based exports on
Node built-ins, so `mockedFS.access.mockResolvedValue` etc. were
`undefined`.
- **`apps/studio/lib/api/self-hosted/functions/index.test.ts`** —
Changed `mockReturnValue` to `mockImplementation(function() { ... })`
for a constructor mock. Vitest 4 no longer allows `mockReturnValue` when
the mock is called with `new`.
- **`apps/studio/tests/pages/api/mcp/index.test.ts`** — Changed arrow
function to regular `function` in `mockImplementation` for
`StreamableHTTPServerTransport`. Arrow functions can't be constructors,
and vitest 4 now enforces this.
- **`packages/ui-patterns/vitest.setup.ts`** — Changed `ResizeObserver`
mock from arrow function to regular `function` for the same constructor
enforcement reason. This was crashing Radix popover rendering in jsdom.
## To test
- `pnpm test:studio` — all 226 test files should pass
- `pnpm --filter ui-patterns vitest run` — all 183 tests should pass
- `pnpm --filter www test -- --run` — all 19 tests should pass
- `pnpm --filter ui vitest run` — all tests should pass
- `pnpm --filter dev-tools vitest run` — all tests should pass
- `pnpm --filter ai-commands vitest run` — all tests should pass
<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit
* **Chores**
* Standardized and updated development tooling versions and version
sources for consistent installs across the repo (Vite, Vitest,
vite-tsconfig-paths and related plugins/catalog entries).
* **Tests**
* Improved test mocks and typings (updated mock
factories/implementations and tightened spy/type assertions) to increase
test reliability and compatibility with updated tooling.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
---------
Co-authored-by: Alaister Young <10985857+alaister@users.noreply.github.com>
|
||
|
|
205cbe7d26 | chore(studio}: enforce import order, remove bare import specifiers (#44585) | ||
|
|
d21098ada4 |
chore(studio): upgrade @supabase/mcp-server-supabase to v0.6.2 (#42210)
* chore(mcp): upgrade @supabase/mcp-server-supabase to v0.6.2 * fix: mocks for Node.js / Web Standard HTTP APIs |
||
|
|
9820707d71 |
feat: local mcp server (#38797)
* feat: local mcp server * feat(local-mcp): implement migrations * fix: remove unsupported mcp args * feat(local-mcp): tests * fix(local-mcp): packages to adhere to minimumReleaseAge * fix(mcp): import path for createSupabaseApiPlatform * fix(local-mcp): move tests out of pages/api dir * refactor: self-hosted execute sql logic * fix: deps |