Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
a6c6cb9
fix(functions): port functions download to native TypeScript (CLI-1963)
Coly010 Aug 5, 2026
265a39a
fix(functions): treat empty --network-id as the generated network (re…
Coly010 Aug 5, 2026
8103233
fix(functions): preserve v-prefixed edge-runtime-version pins (review…
Coly010 Aug 5, 2026
5583c93
fix(functions): request the raw eszip body instead of a negotiated JS…
Coly010 Aug 5, 2026
bc765ee
fix(functions): validate project config before falling back from Dock…
Coly010 Aug 5, 2026
f7b2a4a
fix(functions): skip the named Deno cache volume bind on Bitbucket (r…
Coly010 Aug 5, 2026
51524c6
fix(functions): honor pflag boolean value for --debug in eszip cleanu…
Coly010 Aug 5, 2026
b88cf6a
fix(functions): treat container: as a non-user-defined docker network…
Coly010 Aug 5, 2026
f0d3361
fix(functions): resolve legacy Docker download config from the exact …
Coly010 Aug 5, 2026
143addc
Merge remote-tracking branch 'origin/develop' into columferry/cli-196…
Coly010 Aug 5, 2026
d4530b1
docs(functions): document deno-version-default and network-id env-var…
Coly010 Aug 5, 2026
695afaa
fix(functions): honor the final occurrence of a repeated --network-id…
Coly010 Aug 5, 2026
d556716
fix(functions): surface malformed function-list entries instead of dr…
Coly010 Aug 5, 2026
7834238
docs(functions): document project_id-validation gap for Docker downlo…
Coly010 Aug 5, 2026
8b7dad1
docs(functions): fix SIDE_EFFECTS.md config-read scope for download (…
Coly010 Aug 5, 2026
b856a53
fix(functions): style the Docker-unbundle progress slug in legacy she…
Coly010 Aug 5, 2026
1187874
fix(functions): fail the whole function list on a typed non-string sl…
Coly010 Aug 5, 2026
29f2f28
docs(functions): document project-dotenv registry gap as cross-cuttin…
Coly010 Aug 5, 2026
42b5c37
docs(functions): fix legacy download SIDE_EFFECTS.md file-read matrix…
Coly010 Aug 5, 2026
39b98d0
fix(functions): style the --legacy-bundle suggestion aqua in legacy s…
Coly010 Aug 5, 2026
213c701
fix(functions): close deferred Docker-path parity gaps across deploy/…
Coly010 Aug 10, 2026
2e03304
Merge remote-tracking branch 'origin/develop' into columferry/cli-196…
Coly010 Aug 10, 2026
f102b66
fix(functions): apply parity-audit and engineering-review findings (r…
Coly010 Aug 10, 2026
396e25c
fix(functions): close remaining styling-parity gaps in download sugge…
Coly010 Aug 11, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 8 additions & 15 deletions apps/cli/docs/go-cli-porting-status.md

Large diffs are not rendered by default.

50 changes: 29 additions & 21 deletions apps/cli/src/legacy/commands/functions/deploy/SIDE_EFFECTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,16 +2,18 @@

## Files Read

| Path | Format | When |
| ---------------------------------------------- | ---------- | ----------------------------------------------------------- |
| `~/.supabase/access-token` | plain text | when `SUPABASE_ACCESS_TOKEN` unset and keyring unavailable |
| `<workdir>/supabase/config.toml` | TOML | to resolve function config, project id, and local Functions |
| `<workdir>/supabase/functions/<slug>/index.ts` | TypeScript | function source to deploy |
| `<workdir>/supabase/functions/**/deno.json*` | JSON/JSONC | when resolving import maps |
| imported modules | TypeScript | when walking local import graphs for deploy uploads/bundles |
| configured static files | any | when `static_files` patterns match local files |
| `package.json` next to function entrypoint | JSON | Docker bundling package discovery |
| `<workdir>/supabase/functions/import_map.json` | JSON | deprecated fallback import map discovery |
| Path | Format | When |
| -------------------------------------------------------------------------------------------------------------------------- | ---------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `~/.supabase/access-token` | plain text | when `SUPABASE_ACCESS_TOKEN` unset and keyring unavailable |
| `<workdir>/supabase/{.env,.env.local,.env.<SUPABASE_ENV>,.env.<SUPABASE_ENV>.local}` and the same four at the project root | dotenv | Go-parity project dotenv (`legacyResolveProjectEnvironmentValues`), merged into the `SUPABASE_*` overrides below and threaded into registry resolution |
| `<workdir>/supabase/config.toml` | TOML | to resolve function config, project id, and local Functions — via `goConfigCompat`'s `tomlOnly: true`/`search: false` (same resolver `start`/`stop`/`status` use), so `config.json` is never read here and no ancestor directory is searched past `<workdir>`; also runs the full `Config.Validate` pipeline (`legacyResolveLocalConfigValues`), so an invalid config fails up front even for fields this command never otherwise reads |
| `<workdir>/supabase/<auth.signing_keys_path>`, `[api.tls]` cert/key paths, email template `content_path` — when configured | varies | as part of the `Config.Validate` pipeline above, unconditionally, matching Go's `Config.Load` |
| `<workdir>/supabase/functions/<slug>/index.ts` | TypeScript | function source to deploy |
| `<workdir>/supabase/functions/**/deno.json*` | JSON/JSONC | when resolving import maps |
| imported modules | TypeScript | when walking local import graphs for deploy uploads/bundles |
| configured static files | any | when `static_files` patterns match local files |
| `package.json` next to function entrypoint | JSON | Docker bundling package discovery |
| `<workdir>/supabase/functions/import_map.json` | JSON | deprecated fallback import map discovery |

## Files Written

Expand All @@ -22,10 +24,12 @@

## Subprocesses

| Command | When |
| ------------- | ------------------------------------------------------------------- |
| `docker info` | to detect whether explicitly selected local Docker bundling can run |
| `docker run` | when Docker bundling is selected/available |
| Command | When |
| ------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------ |
| `docker info` | to detect whether explicitly selected local Docker bundling can run |
| `docker image inspect <candidate>` (ECR, then GHCR, then Docker Hub) | Docker bundling: check whether the edge-runtime image is already cached locally, tried in registry order, before the network/volume ensure |
| `docker pull <candidate>` | Docker bundling, cache miss on a candidate: pull with 2 retries (4s/8s backoff) before falling through to the next registry candidate |
| `docker run --rm ... --label com.supabase.cli.project=<id> --label com.docker.compose.project=<id> ...` | when Docker bundling is selected/available; labeled so orphaned containers can be associated with the project (Go: `DockerStart`) |

Docker bundling may pull or run the configured edge-runtime image and uses the
`supabase_edge_runtime_<project_id>` Deno cache volume.
Expand All @@ -43,13 +47,17 @@ Docker bundling may pull or run the configured edge-runtime image and uses the

## Environment Variables

| Variable | Purpose | Required? |
| ---------------------------------- | --------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------- |
| `SUPABASE_ACCESS_TOKEN` | auth token (bypasses credential file/keyring lookup) | no (falls back to keyring → `~/.supabase/access-token`) |
| `SUPABASE_PROJECT_ID` | optional project ref fallback | no |
| `SUPABASE_INTERNAL_IMAGE_REGISTRY` | selects the Functions bundler image registry | no |
| `NPM_CONFIG_REGISTRY` | forwarded into Docker bundling when set (the only npm variable forwarded, matching Go; `NPM_AUTH_TOKEN` is not) | no |
| `DEBUG` | enables verbose Docker bundle output when `true` | no |
| Variable | Purpose | Required? |
| ------------------------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------- |
| `SUPABASE_ACCESS_TOKEN` | auth token (bypasses credential file/keyring lookup) | no (falls back to keyring → `~/.supabase/access-token`) |
| `SUPABASE_PROJECT_ID` | optional project ref fallback; also read from project dotenv now (previously ambient-shell-only) | no |
| `SUPABASE_ENV` | selects environment-specific dotenv files (`.env.<env>.local`, `.env.<env>`) | no (defaults to `development`) |
| `SUPABASE_INTERNAL_IMAGE_REGISTRY` | selects the Functions bundler image registry; read from the ambient shell **or** project dotenv; unset resolves ECR->GHCR->Docker-Hub candidates in order instead of a single URL | no |
| `SUPABASE_NETWORK_ID` | overrides the generated `supabase_network_<project>` Docker network name when `--network-id` isn't passed; read from the ambient shell or project dotenv | no |
| `BITBUCKET_CLONE_DIR` | when set, skips creating the named Deno-cache volume and omits its bind mount from the bundler `docker run` (Bitbucket's restricted Docker environment rejects both); a project-dotenv-only value is installed into `process.env` by config loading, matching Go's `loadNestedEnv` | no |
| `SUPABASE_EDGE_RUNTIME_DENO_VERSION` | overrides `edge_runtime.deno_version` (which bundler image tag to use) when set, from the ambient shell or project dotenv — takes effect even with no `config.toml` on disk | no |
| `NPM_CONFIG_REGISTRY` | forwarded into Docker bundling when set (the only npm variable forwarded, matching Go; `NPM_AUTH_TOKEN` is not) | no |
| `DEBUG` | enables verbose Docker bundle output when `true` | no |

## Exit Codes

Expand Down
20 changes: 10 additions & 10 deletions apps/cli/src/legacy/commands/functions/deploy/deploy.handler.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { DEFAULT_VERSIONS } from "@supabase/stack/effect";
import { readFile } from "node:fs/promises";
import { join } from "node:path";
import { Effect, Option, Stdio } from "effect";
import { deployFunctions } from "../../../../shared/functions/deploy.ts";
import { legacyAqua, legacyBold } from "../../../shared/legacy-colors.ts";
import { resolveEdgeRuntimeVersionPin } from "../../../../shared/functions/functions.shared.ts";
import { legacyAqua, legacyBold, legacyYellow } from "../../../shared/legacy-colors.ts";
import { legacyFunctionsGoConfigCompat } from "../../../shared/legacy-functions-go-config.ts";
import { LegacyPlatformApi } from "../../../auth/legacy-platform-api.service.ts";
import { LegacyCliConfig } from "../../../config/legacy-cli-config.service.ts";
import { LegacyProjectRefResolver } from "../../../config/legacy-project-ref.service.ts";
Expand All @@ -29,12 +29,8 @@ export const legacyFunctionsDeploy = Effect.fn("legacy.functions.deploy")(functi
const runtimeInfo = yield* RuntimeInfo;
const stdio = yield* Stdio.Stdio;
const rawArgs = yield* stdio.args;
const edgeRuntimeVersion = yield* Effect.tryPromise(() =>
readFile(join(cliConfig.workdir, "supabase", ".temp", "edge-runtime-version"), "utf8"),
).pipe(
Effect.map((version) => version.trim()),
Effect.catch(() => Effect.succeed("")),
Effect.map((version) => version || DEFAULT_VERSIONS["edge-runtime"]),
const edgeRuntimeVersion = yield* resolveEdgeRuntimeVersionPin(
join(cliConfig.workdir, "supabase"),
);
let resolvedProjectRef = Option.none<string>();

Expand All @@ -45,7 +41,7 @@ export const legacyFunctionsDeploy = Effect.fn("legacy.functions.deploy")(functi
projectRoot: cliConfig.workdir,
supabaseDir: join(cliConfig.workdir, "supabase"),
dashboardUrl: legacyDashboardUrl(cliConfig.profile),
goViperCompat: true,
goConfigCompat: legacyFunctionsGoConfigCompat,
yes,
rawArgs,
edgeRuntimeVersion,
Expand All @@ -65,6 +61,10 @@ export const legacyFunctionsDeploy = Effect.fn("legacy.functions.deploy")(functi
// and the no-functions error dir (`deploy.go:35`, rendered on stderr) —
// both stderr-bound, matching `legacyBold`'s default TTY gate.
styleEmphasis: (text) => legacyBold(text),
// Go: `utils.Yellow` on the `WARNING:` token before "Docker is not
// running" (`deploy.go:60`, stderr) — matches `legacyYellow`'s default
// TTY gate.
styleWarning: (text) => legacyYellow(text),
}).pipe(
Effect.ensuring(
Effect.suspend(() =>
Expand Down
Loading
Loading