Skip to content

[Env] Stop mutating process-global environment during project loading #716

Description

@cssbruno

Priority

High — composability, test isolation, LSP/dev correctness, and future embedded API safety.

Context

runtime/envfile.LoadIntoEnv parses .env files and writes entries directly into the process environment with os.Setenv. It also keeps package-global state to remember values that were previously applied by the loader.

Project-aware CLI commands call this while loading gowdk.config.go.

Problem

Loading a project configuration mutates process-global state.

This has several risks:

  1. Two project loads in the same process can influence each other.
  2. Tests can pass or fail depending on load order.
  3. A future daemon, LSP session, or embedded compiler API cannot safely load multiple workspaces concurrently.
  4. Dev rebuilds reuse a process with sticky env-file state.
  5. Subprocesses inherit an environment shaped by prior project loads unless every caller carefully filters it.

The current package-global appliedValues map makes env loading a process lifecycle concern rather than a workspace input.

Proposed direction

Parse env files into an explicit immutable environment overlay instead of mutating os.Environ.

Example model:

type Environment struct {
    Process map[string]string
    File    map[string]string
}

func (env Environment) Lookup(name string) (string, bool)
func (env Environment) ForSubprocess(base []string) []string

Configuration validation, executable config helpers, build-data helpers, generated app tests, and other subprocesses should receive an explicit environment from the workspace plan.

Acceptance criteria

  • Loading .env or .env.<GOWDK_ENV> does not call os.Setenv during project loading.
  • Project env values are available to config validation through an explicit lookup.
  • Subprocess environment construction is explicit and testable.
  • Repeated loads of different project roots in one process do not leak values.
  • Dev/LSP workflows can reload env-file contents without process-global sticky state.
  • Tests cover two projects loaded in one process and concurrent loads.

Related

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions