You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Angular 19 + Nx 单仓项目中dotenv环境变量替换配置缺失问题排查

Angular 19 + Nx 单仓项目中dotenv环境变量替换配置缺失问题排查

你碰到的这个问题其实是Angular/Nx项目里用dotenv类工具的常见坑——浏览器环境根本没有process这个Node.js全局对象,直接在environment.ts里写process.env['SOME_API_KEY'],不管你用dotenvx还是什么,运行时浏览器都认不出来。而且Vite(现在Nx Angular默认用Vite构建)会把Node相关模块比如process标记为外部依赖,不让你在客户端代码里直接引用,这就是为什么你导入process后会看到那个“模块已外部化”的错误。

下面我一步步给你拆解解决方案:

第一步:修正environment.ts的写法,别直接用process.env

先把你的src/environments/environment.ts改成符合浏览器环境的写法,这里推荐用Vite官方支持的import.meta.env(编译时会自动替换成实际变量值),示例:

export const env = {
  someApi: "https://some.tld/api/v1/",
  // 用Vite支持的import.meta.env,后面加默认值方便本地开发
  someApiKey: import.meta.env.VITE_SOME_API_KEY || "local-dev-key",
  anotherApiKey: import.meta.env.VITE_ANOTHER_API_KEY || "local-dev-key"
};

第二步:调整环境变量的命名规则(或配置Vite兼容原有命名)

Vite默认只会自动识别前缀为VITE_的环境变量,所以你需要二选一:

方案A:给.env文件的变量加VITE_前缀(推荐,符合Vite规范)

修改你的apps/some-app/.env、.env.uat、.env.prod:

VITE_SOME_API_KEY="123-API-456-KEY-789"
VITE_ANOTHER_API_KEY="123-API-456-KEY-789"

方案B:配置Vite兼容原有变量名(不推荐,多一步配置)

如果不想改变量名,就在apps/some-app/vite.config.ts里添加define配置,让Vite在编译时把process.env的变量替换成实际值:

import { defineConfig } from 'vite';
import angular from '@nx/angular/plugins/vite';

export default defineConfig({
  plugins: [angular()],
  define: {
    // 把dotenvx注入的变量映射成全局常量,编译时替换
    'process.env.SOME_API_KEY': JSON.stringify(process.env.SOME_API_KEY || "local-dev-key"),
    'process.env.ANOTHER_API_KEY': JSON.stringify(process.env.ANOTHER_API_KEY || "local-dev-key")
  }
});

这种情况下你可以继续用process.env['SOME_API_KEY']的写法,但本质上是Vite在编译时把它替换成了字符串,浏览器运行时根本看不到process。

第三步:修正package.json的脚本(两个关键细节)

我看你的脚本里有两个小问题,必须改:

  1. 命令参数的空格:nx build some-app--configuration production里的some-app和--configuration之间少了空格,Nx会把它当成一个错误的项目名
  2. watch:some-app没加dotenvx,本地开发时变量不会被注入

修正后的脚本:

"scripts": {
  "start:some-app": "dotenvx run -f apps/some-app/.env -- nx serve some-app",
  "build:some-app": "dotenvx run -f apps/some-app/.env.prod -- nx build some-app --configuration production",
  "build:some-app:uat": "dotenvx run -f apps/some-app/.env.uat -- nx build some-app --configuration uat",
  "watch:some-app": "dotenvx run -f apps/some-app/.env -- nx build some-app --watch --configuration development",
  "test:some-app": "nx test some-app",
  "coverage:some-app": "nx test some-app --no-watch --code-coverage"
}

第四步:给TypeScript加类型声明(避免红色波浪线)

如果用import.meta.env的方案,TypeScript可能会报类型错误,你可以在src/env.d.ts里添加类型声明:

interface ImportMetaEnv {
  readonly VITE_SOME_API_KEY: string;
  readonly VITE_ANOTHER_API_KEY: string;
}

interface ImportMeta {
  readonly env: ImportMetaEnv;
}

如果用process.env的方案,就在src/types/process.d.ts里加:

declare namespace NodeJS {
  interface ProcessEnv {
    readonly SOME_API_KEY: string;
    readonly ANOTHER_API_KEY: string;
  }
}

然后在tsconfig.app.json的compilerOptions.types里包含这个类型文件。

最后验证

运行npm run start:some-app,打开浏览器控制台打印env.someApiKey,应该能看到.env里的实际值,再也不会出现process is not defined的错误了。

内容来源于stack exchange

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.07 13:38:06