
本文详解 Nuxt 3 项目中 nuxt.config.ts 无法读取 .env 变量的根本原因,并提供适用于 SSR 模式与 Docker 部署的完整解决方案,涵盖构建时注入、运行时暴露、Docker 配置及 runtimeConfig 正确用法。
本文详解 nuxt 3 项目中 `nuxt.config.ts` 无法读取 `.env` 变量的根本原因,并提供适用于 ssr 模式与 docker 部署的完整解决方案,涵盖构建时注入、运行时暴露、docker 配置及 runtimeconfig 正确用法。
在 Nuxt 3 中,nuxt.config.ts 是一个构建时(build-time)执行的 Node.js 脚本,而非运行时(runtime)代码。这意味着它只能访问构建阶段可用的环境上下文——例如本地开发时的 .env 文件、CI/CD 的构建参数,或 Docker 构建阶段通过 ARG 注入的变量;而容器启动后通过 environment: 设置的运行时环境变量,对 nuxt.config.ts 完全不可见。这正是你遇到 process.env.NUXT_PUBLIC_STRAPI_BASE_URI 始终为空的根本原因:.env 文件虽挂载进容器,但 nuxt.config.ts 在构建镜像时早已执行完毕,此时挂载的 .env 对其无效。
✅ 正确做法:分清「构建时」与「运行时」,按需注入
1. 构建阶段注入(推荐用于 CI/CD 或多环境镜像构建)
使用 Docker ARG + --build-arg 在 docker build 时传入变量,确保 nuxt.config.ts 可读取:
# Dockerfile FROM node:20-alpine AS builder WORKDIR /src COPY package*.json ./ RUN npm ci --silent COPY . . ARG NUXT_PUBLIC_STRAPI_BASE_URI ARG NUXT_STRAPI_ADMIN_TOKEN RUN npm run build
构建命令:
docker build \ --build-arg NUXT_PUBLIC_STRAPI_BASE_URI="https://strapi.example.com" \ --build-arg NUXT_STRAPI_ADMIN_TOKEN="your-secret-token" \ -t nuxt-app .
并在 nuxt.config.ts 中直接使用:
export default defineNuxtConfig({
runtimeConfig: {
strapiAdminToken: process.env.NUXT_STRAPI_ADMIN_TOKEN || '',
public: {
strapiBaseUri: process.env.NUXT_PUBLIC_STRAPI_BASE_URI || '',
stripe: {
publishableKey: ''
}
}
}
})
⚠️ 注意:
NUXT_前缀变量会自动被 Nuxt 解析为runtimeConfig,但前提是它们必须在构建时已存在(即ARG注入或本地.env加载),而非容器启动后才设置。
2. 运行时注入(适用于 Docker Compose 动态配置)
若需在容器启动时动态覆盖(如测试/预发环境),必须配合 Nuxt 的 Runtime Config API 使用:
✅ 正确写法(docker-compose.yml):
nuxt-app:
container_name: nuxt-app
image: ${CI_REGISTRY_IMAGE}/nuxt-app:latest
restart: unless-stopped
environment:
# 必须以 NUXT_ 或 NUXT_PUBLIC_ 开头,且需在 runtimeConfig 中显式声明
- NUXT_PUBLIC_STRAPI_BASE_URI=https://staging-strapi.example.com
- NUXT_STRAPI_ADMIN_TOKEN=abc123
ports:
- "3000:3000"
networks:
- Strapi
同时确保 nuxt.config.ts 中显式引用环境变量(不能留空字符串):
export default defineNuxtConfig({
runtimeConfig: {
// 私有变量(仅服务端可见)
strapiAdminToken: process.env.NUXT_STRAPI_ADMIN_TOKEN,
// 公共变量(客户端+服务端可见)
public: {
strapiBaseUri: process.env.NUXT_PUBLIC_STRAPI_BASE_URI,
stripe: {
publishableKey: process.env.NUXT_PUBLIC_STRIPE_PUBLISHABLE_KEY || ''
}
}
}
})
✅ 关键点:Nuxt 3 的
runtimeConfig支持运行时热替换(仅限 Nitro 服务端),但前提是:
- 变量名严格匹配
NUXT_*/NUXT_PUBLIC_*前缀;nuxt.config.ts中必须通过process.env.XXX显式赋值(不能写'');- 启动命令需使用
node .output/server/index.mjs(非npm run dev)。
3. 本地开发与多环境支持(.env + --dotenv)
为统一开发/构建流程,推荐在 package.json 中定义多环境脚本:
"scripts": {
"dev": "nuxi dev --dotenv .env.development",
"build:staging": "nuxi build --dotenv .env.staging",
"build:prod": "nuxi build --dotenv .env.production"
}
对应 .env.staging 示例:
NUXT_PUBLIC_STRAPI_BASE_URI=https://staging-api.example.com NUXT_STRAPI_ADMIN_TOKEN=staging_token_123
? 提示:
.env文件必须位于项目根目录,且格式严格为KEY=VALUE(无空格、无引号)。Nuxt 自动加载.env仅在nuxi dev/build/generate阶段生效,不作用于 Docker 容器内运行时。
? 调试技巧:验证变量是否生效
在 nuxt.config.ts 顶部添加调试日志:
console.log('? Build-time env:', {
STRAPI_BASE: process.env.NUXT_PUBLIC_STRAPI_BASE_URI,
ADMIN_TOKEN: process.env.NUXT_STRAPI_ADMIN_TOKEN
})
构建后检查控制台输出;若为空,则说明构建时未注入成功。
✅ 最佳实践总结
| 场景 | 推荐方式 | 是否影响 nuxt.config.ts
|
客户端可访问 |
|---|---|---|---|
| CI/CD 多环境镜像构建 |
ARG + --build-arg
|
✅ 是 | ✅(需 NUXT_PUBLIC_ 前缀) |
| Docker Compose 动态部署 |
environment: + runtimeConfig 显式引用 |
❌ 否(仅影响 Nitro 运行时) | ✅ |
| 本地开发 |
--dotenv + .env.*
|
✅ 是 | ✅ |
| 敏感密钥(如 token) |
NUXT_*(非 PUBLIC)+ runtimeConfig
|
✅ 是(构建时)/ ✅ 运行时(Nitro) | ❌ 仅服务端 |
遵循以上原则,即可彻底解决 nuxt.config.ts 读不到环境变量的问题,实现安全、灵活、可复现的多环境部署。











