Skip to main content
By default, sandboxed processes inherit all environment variables from the parent process. This means API keys, tokens, and other secrets present in the shell environment are visible inside the sandbox — even if the profile blocks network access or filesystem paths. Environment variable filtering lets you explicitly control which variables are passed through, so only the variables your agent needs are available.

How It Works

When environment.allow_vars is set in a profile, nono:
  1. Clears the inherited environment
  2. Passes through only variables matching the allow-list
  3. Adds back nono-injected credentials (from env_credentials) on top
If the environment section is omitted entirely, all variables are passed through (backward compatible). Setting allow_vars to an empty array [] restricts the environment to only nono-injected credentials — no inherited variables are passed.

Configuration

Add the environment section to your profile:
{
  "environment": {
    "allow_vars": ["PATH", "HOME", "TERM", "LANG"]
  }
}

Prefix Patterns

Use a trailing * to match all variables with a given prefix:
{
  "environment": {
    "allow_vars": ["PATH", "HOME", "AWS_*", "MYAPP_*"]
  }
}
This passes through AWS_REGION, AWS_SECRET_ACCESS_KEY, and any variable starting with MYAPP_, while blocking everything else. A bare "*" matches all variables (equivalent to not setting the environment section at all). The * wildcard is only valid as a trailing suffix — patterns like "A*B" or "*X" are rejected at profile load time.

Inheritance

allow_vars is additive across profile inheritance. A child profile appends its entries to the base profile’s list, and duplicates are removed:
// base.json
{
  "environment": {
    "allow_vars": ["PATH", "HOME"]
  }
}

// child.json
{
  "extends": "base",
  "environment": {
    "allow_vars": ["AWS_*"]
  }
}
// Result: ["PATH", "HOME", "AWS_*"]

Interaction with Credential Injection

Variables injected by nono — via env_credentials or --env-credentialalways bypass the allow-list. They are explicitly configured by the user and must reach the child process regardless of filtering rules.
{
  "environment": {
    "allow_vars": ["PATH"]
  },
  "env_credentials": {
    "openai": "OPENAI_API_KEY"
  }
}
In this case, OPENAI_API_KEY is passed through even though it’s not in allow_vars, because it was explicitly injected via env_credentials.
If you inject a secret via env_credentials and also list it in allow_vars, it will be present once (deduplicated). There is no conflict.

Interaction with the Deny-List

nono maintains a built-in deny-list of dangerous environment variables (e.g., LD_PRELOAD, DYLD_INSERT_LIBRARIES, PYTHONPATH, NODE_OPTIONS). These variables are always blocked, even if they appear in allow_vars. This prevents a compromised profile from disabling sandbox protections.
{
  "environment": {
    "allow_vars": ["LD_PRELOAD"]
  }
}
LD_PRELOAD will not be passed through, despite being in the allow-list.

Security Properties

  • Default-allow: Without the environment section, all variables are passed through (no regression)
  • Empty allow-list restricts all: "allow_vars": [] passes zero inherited variables — only nono-injected credentials reach the child
  • Explicit allow-list: When configured with entries, only listed variables reach the child process
  • Injected credentials bypass the allow-list: env_credentials variables always pass through
  • Deny-list is non-overridable: Dangerous variables like LD_PRELOAD are always blocked
  • Prefix patterns reduce misconfiguration: Only * suffix is supported (no regex), reducing risk of accidental over-permission
  • Bare * matches everything: Use as an escape hatch, but prefer explicit lists

Example: Minimal Agent Environment

A typical profile for an AI agent that only needs basic shell environment and cloud credentials:
{
  "meta": {
    "name": "secure-agent"
  },
  "filesystem": {
    "allow": ["/usr", "/project"]
  },
  "network": {
    "block": false
  },
  "environment": {
    "allow_vars": [
      "PATH",
      "HOME",
      "TERM",
      "LANG",
      "LC_ALL",
      "USER",
      "AWS_*"
    ]
  },
  "env_credentials": {
    "openai": "OPENAI_API_KEY"
  }
}
This ensures the agent sees AWS_* variables and the injected OPENAI_API_KEY, but no other secrets accidentally present in the parent environment.
Next: Credential Injection | Profile Authoring