Netlify: env vars not loading in functions [2026 fix]
Env vars undefined in Netlify Functions? Deploy netlify.toml with [functions] context or use process.env in build step.
Netlify: env vars not loading in functions [2026 fix]
TL;DR
Cause: Netlify Functions can't access env vars because they're not explicitly configured innetlify.toml or the function runtime doesn't have build context.
Fix: Add [functions] config block to netlify.toml and ensure vars are set in Netlify UI under Site settings → Build & deploy → Environment.---
Exact Error Messages You'll See
``` TypeError: Cannot read property 'API_KEY' of undefined at Runtime.handler (/var/task/api.js:5:12)
ReferenceError: process is not defined at Object.<anonymous> (/var/task/stripe.js:12:3)
Error: Missing required env var DATABASE_URL at connectDB (/var/task/db.js:8:15)
[Function] Error: process.env.NETLIFY_CONTEXT returned undefined Handler response: {"statusCode":500,"body":"Internal error"}
warning: Environment variables from .env not loaded in serverless context (Functions use Netlify UI config, not local .env files) ```
---
Broken Code → Fixed Code
❌ BROKEN: Relying on .env alone
```javascript // netlify/functions/api.js const stripe = require('stripe')(process.env.STRIPE_SECRET);
exports.handler = async (event) => { // process.env.STRIPE_SECRET is undefined in production const payment = await stripe.charges.create({ amount: 2000, currency: 'usd' }); return { statusCode: 200, body: JSON.stringify(payment) }; }; ```
✅ FIXED: Add netlify.toml config + UI vars
Step 1: Create/update netlify.toml:
```toml [functions] node_bundler = "esbuild" external_node_modules = ["stripe"]
[build] command = "npm run build" functions = "netlify/functions"
Reference env vars (they're pulled from Netlify UI)
Don't hardcode secrets here—set them in Site settings instead
```Step 2: Update function to access env vars correctly:
```javascript // netlify/functions/api.js const stripe = require('stripe')(process.env.STRIPE_SECRET);
exports.handler = async (event) => { // process.env.STRIPE_SECRET now loads from Netlify UI if (!process.env.STRIPE_SECRET) { return { statusCode: 500, body: JSON.stringify({ error: 'STRIPE_SECRET not configured' }) }; } const payment = await stripe.charges.create({ amount: 2000, currency: 'usd' }); return { statusCode: 200, body: JSON.stringify(payment) }; }; ```
Step 3: Set env vars in Netlify UI:
1. Go to Site settings → Build & deploy → Environment
2. Click Add a variable
3. Key: STRIPE_SECRET | Value: (paste your secret key)
4. Redeploy: git push or Deploy site button
---
Why This Happens
Netlify Functions run in AWS Lambda, which doesn't read your local .env file. The function bundle is isolated from your build process. Variables must be:
1. Explicitly configured in Netlify's environment (UI or netlify.toml)
2. Available at function invocation time (not just at build time)
3. Not included in version control (keep secrets out of git)
I'm uncertain whether Netlify will deprecate direct .env injection in Functions after 2026—their docs suggest moving toward netlify.toml config, but local development still uses .env for convenience.
---
Still broken? Check these too
1. [Environment variables not persisting after redeploy](/?guide=netlify-env-cache) — Clear Netlify build cache under Site settings → Build & deploy → Delete site data if vars were added *after* the last deploy.
2. [Functions timeout when accessing external APIs](/?guide=netlify-function-timeout) — Add timeout = 30 (seconds) to [functions] block in netlify.toml. Default is 10 seconds.
3. [TypeScript functions can't find env types](/?guide=netlify-ts-env) — Create env.d.ts with declare namespace NodeJS { interface ProcessEnv { STRIPE_SECRET: string; } } for autocomplete.
---
Verification Checklist
.env file)netlify.toml has [functions] block with functions = "netlify/functions" pathprocess.env.VAR_NAME (not process.env['VAR_NAME'] with dynamic keys).env file is in .gitignore (don't commit secrets)npm run dev (Netlify CLI loads .env for local Functions)---
Official Resources
---
Found a different variation? Drop it in the comments — we're likely missing edge cases around monorepos, pnpm workspaces, or regional function deployments.