Skip to content

.env files written by the CLI do not read back the same values (values with #, surrounding spaces, or newlines) #11314

Open

Description

@sebxt

What happens

The CLI writes .env files in two places and later reads them back with the same parser (parse() in src/functions/env.ts). Some values do not survive the round trip.

  1. Function params. When firebase deploy prompts for a param value, it is saved to .env.<projectId> by writeUserEnvs(). A value containing # (for example https://example.com/#/home) or with leading or trailing spaces is written unquoted. The parser treats # as the start of a comment and trims unquoted values, so the next deploy silently uses https://example.com/ or foo instead of what was entered.

  2. Extensions. ext:install, ext:configure, ext:update and ext:export write extensions/<instance>.env (and extensions/<instance>.secret.local) as plain KEY=value lines with no quoting or escaping at all. A param value with # is truncated the same way. A value with a newline (for example a multi-line prompt exported from an existing instance) is split across lines; the second line is not a valid entry, readEnvFile() throws, and readInstanceParam() swallows that error, so the whole file is ignored on the next deploy.

What should happen

Any string the CLI writes to a .env file should be read back unchanged.

Minimal repro

// functions
env.writeUserEnvs({ HASH: "https://example.com/#/home" }, opts);
env.loadUserEnvs(opts).HASH; // "https://example.com/", expected "https://example.com/#/home"

// extensions: writeToManifest with params { a: "line one\nline two", b: "#ff0000" }
// writes "a=line one\nline two\nb=#ff0000", which parses to
// { envs: { a: "line one", b: "" }, errors: ["line two"] }

Root cause

formatUserEnvForWrite() only quotes a value when it contains a character that needs an escape sequence (newline, tab, quote, backslash). It does not quote values containing # or starting or ending with whitespace, even though parse() cuts unquoted values at # and trims them. src/extensions/manifest.ts does not use this formatter at all and joins ${key}=${value} directly.

Activity

  1. IzaakGough commented on Oct 22, 2026

    @IzaakGough
    Contributor

    Hi @sebxt thanks for raising this. We will review as soon as possible.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions

      ⌂ Proxy