├── .changeset
├── README.md
└── config.json
├── .dockerignore
├── .github
└── workflows
│ ├── docs.yml
│ ├── main.yml
│ └── release.yml
├── .gitignore
├── .husky
└── pre-commit
├── .npmrc
├── CNAME
├── Dockerfile
├── README.md
├── docs
├── .dockerignore
├── .gitignore
├── CHANGELOG.md
├── README.md
├── astro.config.mjs
├── package.json
├── public
│ └── favicon.svg
├── src
│ ├── assets
│ │ └── houston.webp
│ ├── content
│ │ ├── config.ts
│ │ └── docs
│ │ │ ├── getting-started
│ │ │ ├── about.md
│ │ │ ├── architecture.md
│ │ │ ├── command-line.md
│ │ │ ├── comparison.md
│ │ │ ├── env-files.md
│ │ │ ├── expand.md
│ │ │ ├── loading-priorities.md
│ │ │ ├── monorepo-setup.md
│ │ │ ├── options.md
│ │ │ └── quick-start.md
│ │ │ ├── index.mdx
│ │ │ ├── integrations
│ │ │ ├── babel.md
│ │ │ ├── cli.md
│ │ │ ├── core.md
│ │ │ ├── esbuild.md
│ │ │ ├── loader.md
│ │ │ ├── node.md
│ │ │ ├── rollup.md
│ │ │ ├── vite.md
│ │ │ └── webpack.md
│ │ │ └── recipes
│ │ │ └── angular.md
│ ├── env.d.ts
│ └── styles
│ │ └── custom.css
└── tsconfig.json
├── examples
├── nx-workspace-old
│ ├── .dockerignore
│ ├── .env.app
│ ├── .env.app.dev
│ ├── .env.app.prod
│ ├── .gitignore
│ ├── .secrets
│ ├── .secrets.prod
│ ├── .verdaccio
│ │ └── config.yml
│ ├── apps
│ │ ├── cli-app
│ │ │ ├── .secrets
│ │ │ ├── .secrets.local
│ │ │ ├── .secrets.prod
│ │ │ ├── .secrets.prod.local
│ │ │ ├── __snapshots__
│ │ │ │ └── cli.test.ts.snap
│ │ │ ├── cli.test.ts
│ │ │ ├── package.json
│ │ │ ├── project.json
│ │ │ └── turbo.json
│ │ ├── ng-app-cli
│ │ │ ├── .app.prod
│ │ │ ├── .editorconfig
│ │ │ ├── .env
│ │ │ ├── .env.local
│ │ │ ├── .env.prod
│ │ │ ├── .env.test
│ │ │ ├── .gitignore
│ │ │ ├── README.md
│ │ │ ├── angular.json
│ │ │ ├── jest.config.mjs
│ │ │ ├── karma.conf.js
│ │ │ ├── package.json
│ │ │ ├── playwright.config.ts
│ │ │ ├── project.json
│ │ │ ├── setup-jest.ts
│ │ │ ├── src
│ │ │ │ ├── app
│ │ │ │ │ ├── app.component.css
│ │ │ │ │ ├── app.component.html
│ │ │ │ │ ├── app.component.spec.ts
│ │ │ │ │ ├── app.component.ts
│ │ │ │ │ ├── app.config.server.ts
│ │ │ │ │ ├── app.config.ts
│ │ │ │ │ ├── app.routes.ts
│ │ │ │ │ └── hello
│ │ │ │ │ │ ├── hello.component.css
│ │ │ │ │ │ ├── hello.component.html
│ │ │ │ │ │ ├── hello.component.spec.ts
│ │ │ │ │ │ └── hello.component.ts
│ │ │ │ ├── assets
│ │ │ │ │ └── .gitkeep
│ │ │ │ ├── env.d.ts
│ │ │ │ ├── environments
│ │ │ │ │ ├── environment.prod.ts
│ │ │ │ │ └── environment.ts
│ │ │ │ ├── favicon.ico
│ │ │ │ ├── index.html
│ │ │ │ ├── locale
│ │ │ │ │ ├── messages.fr.xlf
│ │ │ │ │ └── messages.xlf
│ │ │ │ ├── main.server.ts
│ │ │ │ ├── main.ts
│ │ │ │ ├── server.ts
│ │ │ │ └── styles.css
│ │ │ ├── tests
│ │ │ │ └── app.spec.ts
│ │ │ ├── tsconfig.app.json
│ │ │ ├── tsconfig.json
│ │ │ └── tsconfig.spec.json
│ │ ├── ng-app-webpack
│ │ │ ├── .editorconfig
│ │ │ ├── .env.app
│ │ │ ├── .env.app.local
│ │ │ ├── .gitignore
│ │ │ ├── README.md
│ │ │ ├── angular.json
│ │ │ ├── package.ignore.json
│ │ │ ├── playwright.config.ts
│ │ │ ├── project.ignore.json
│ │ │ ├── src
│ │ │ │ ├── app
│ │ │ │ │ ├── app.component.html
│ │ │ │ │ ├── app.component.ts
│ │ │ │ │ └── app.module.ts
│ │ │ │ ├── assets
│ │ │ │ │ └── .gitkeep
│ │ │ │ ├── env.d.ts
│ │ │ │ ├── environments
│ │ │ │ │ ├── environment.prod.ts
│ │ │ │ │ └── environment.ts
│ │ │ │ ├── favicon.ico
│ │ │ │ ├── index.html
│ │ │ │ ├── main.ts
│ │ │ │ ├── polyfills.ts
│ │ │ │ ├── styles.css
│ │ │ │ └── test.ts
│ │ │ ├── tsconfig.app.json
│ │ │ ├── tsconfig.json
│ │ │ ├── tsconfig.spec.json
│ │ │ └── webpack.config.ts
│ │ ├── rspack-app
│ │ │ ├── __snapshots__
│ │ │ │ ├── rspack-dev.test.ts.snap
│ │ │ │ └── rspack-prod.test.ts.snap
│ │ │ ├── package.json
│ │ │ ├── project.json
│ │ │ ├── rspack-dev.test.ts
│ │ │ ├── rspack-prod.test.ts
│ │ │ ├── rspack.config.mjs
│ │ │ └── src
│ │ │ │ └── index.js
│ │ └── webpack-app
│ │ │ ├── __snapshots__
│ │ │ ├── webpack-dev.test.ts.snap
│ │ │ └── webpack-prod.test.ts.snap
│ │ │ ├── package.json
│ │ │ ├── project.json
│ │ │ ├── src
│ │ │ └── index.js
│ │ │ ├── webpack-dev.test.ts
│ │ │ ├── webpack-prod.test.ts
│ │ │ └── webpack.config.mjs
│ ├── libs
│ │ └── rollup-lib
│ │ │ ├── package.json
│ │ │ ├── project.json
│ │ │ ├── rollup.config.mjs
│ │ │ └── src
│ │ │ ├── index.mjs
│ │ │ └── index.test.js
│ ├── nx.json
│ ├── package.json
│ └── project.json
└── nx-workspace
│ ├── .editorconfig
│ ├── .github
│ └── workflows
│ │ └── ci.yml
│ ├── .gitignore
│ ├── .prettierignore
│ ├── .prettierrc
│ ├── README.md
│ ├── apps
│ ├── ng-app-cli-e2e
│ │ ├── eslint.config.js
│ │ ├── playwright.config.ts
│ │ ├── project.json
│ │ ├── src
│ │ │ └── example.spec.ts
│ │ └── tsconfig.json
│ └── ng-app-cli
│ │ ├── eslint.config.js
│ │ ├── jest.config.ts
│ │ ├── package.json
│ │ ├── project.json
│ │ ├── public
│ │ └── favicon.ico
│ │ ├── server.ts
│ │ ├── src
│ │ ├── app
│ │ │ ├── app.component.css
│ │ │ ├── app.component.html
│ │ │ ├── app.component.spec.ts
│ │ │ ├── app.component.ts
│ │ │ ├── app.config.server.ts
│ │ │ ├── app.config.ts
│ │ │ └── app.routes.ts
│ │ ├── env.d.ts
│ │ ├── index.html
│ │ ├── main.server.ts
│ │ ├── main.ts
│ │ ├── styles.css
│ │ └── test-setup.ts
│ │ ├── tsconfig.app.json
│ │ ├── tsconfig.editor.json
│ │ ├── tsconfig.json
│ │ └── tsconfig.spec.json
│ ├── eslint.config.js
│ ├── jest.config.ts
│ ├── jest.preset.js
│ ├── nx.json
│ ├── package.json
│ └── tsconfig.base.json
├── package.json
├── packages
├── .env
├── angular
│ ├── CHANGELOG.md
│ ├── README.md
│ ├── builders.json
│ ├── collection.json
│ ├── logo.svg
│ ├── manekinekko.png
│ ├── motdotla.png
│ ├── package.json
│ ├── runtime.mjs
│ ├── src
│ │ ├── builders
│ │ │ ├── application
│ │ │ │ ├── application.json
│ │ │ │ └── index.ts
│ │ │ ├── browser-esbuild
│ │ │ │ ├── browser-esbuild.json
│ │ │ │ └── index.ts
│ │ │ ├── browser
│ │ │ │ ├── browser.json
│ │ │ │ └── index.ts
│ │ │ ├── dev-server
│ │ │ │ ├── dev-server.json
│ │ │ │ └── index.ts
│ │ │ ├── extract-i18n
│ │ │ │ ├── extract-i18n.json
│ │ │ │ └── index.ts
│ │ │ ├── karma
│ │ │ │ ├── index.ts
│ │ │ │ └── karma.json
│ │ │ ├── ngx-env
│ │ │ │ ├── ngx-env-schema.ts
│ │ │ │ └── ngx-env.json
│ │ │ ├── server
│ │ │ │ ├── index.ts
│ │ │ │ └── server.json
│ │ │ └── utils
│ │ │ │ ├── escape-string-regexp.ts
│ │ │ │ ├── get-environment.ts
│ │ │ │ ├── index-html-build.ts
│ │ │ │ ├── index-html-serve.ts
│ │ │ │ ├── project.ts
│ │ │ │ ├── variables-reducer.ts
│ │ │ │ ├── webpack-plugin.ts
│ │ │ │ └── workspace.ts
│ │ └── schematics
│ │ │ └── ng-add
│ │ │ ├── index.ts
│ │ │ ├── schema.json
│ │ │ └── template
│ │ │ └── env.d.ts
│ ├── tools
│ │ ├── cli-targets.ts
│ │ ├── schema-copy-run.ts
│ │ ├── schema-copy.ts
│ │ ├── schema-dist.ts
│ │ └── schema-generate.ts
│ └── tsconfig.json
├── cli
│ ├── .env.dev
│ ├── .env.prod
│ ├── CHANGELOG.md
│ ├── README.md
│ ├── package.json
│ ├── src
│ │ ├── index.mts
│ │ └── run.ts
│ ├── test
│ │ └── cli.test.ts
│ └── tsconfig.json
├── core
│ ├── .env.dev
│ ├── .env.prod
│ ├── CHANGELOG.md
│ ├── README.md
│ ├── package.json
│ ├── src
│ │ ├── build.ts
│ │ ├── env.ts
│ │ ├── expand.ts
│ │ ├── index.ts
│ │ ├── options.ts
│ │ ├── root.ts
│ │ └── utils.ts
│ ├── test
│ │ ├── dev.test.ts
│ │ └── prod.test.ts
│ └── tsconfig.json
├── esbuild
│ ├── .env
│ ├── CHANGELOG.md
│ ├── README.md
│ ├── package.json
│ ├── src
│ │ └── index.ts
│ ├── test
│ │ ├── __snapshots__
│ │ │ └── index.test.ts.snap
│ │ ├── app.js
│ │ ├── index.test.ts
│ │ └── util.js
│ └── tsconfig.json
├── jest-angular
│ ├── CHANGELOG.md
│ ├── README.md
│ ├── index.mjs
│ └── package.json
├── jest
│ ├── package.json
│ └── src
│ │ └── jest-env.mjs
├── load
│ ├── .env
│ ├── .env.dev
│ ├── .env.prod
│ ├── CHANGELOG.md
│ ├── package.json
│ ├── src
│ │ └── index.ts
│ ├── test
│ │ ├── load.test.ts
│ │ └── server.js
│ └── tsconfig.json
├── rollup
│ ├── CHANGELOG.md
│ ├── README.md
│ ├── package.json
│ ├── src
│ │ └── index.ts
│ └── tsconfig.json
├── rspack
│ ├── package.json
│ ├── src
│ │ └── index.ts
│ └── tsconfig.json
├── vite
│ ├── README.md
│ ├── package.json
│ ├── src
│ │ ├── constants.ts
│ │ ├── index.ts
│ │ ├── mapper.ts
│ │ └── options.ts
│ └── tsconfig.json
└── webpack
│ ├── CHANGELOG.md
│ ├── README.md
│ ├── package.json
│ ├── src
│ └── index.ts
│ └── tsconfig.json
├── pnpm-lock.yaml
├── pnpm-workspace.yaml
└── turbo.json
/.changeset/README.md:
--------------------------------------------------------------------------------
1 | # Changesets
2 |
3 | Hello and welcome! This folder has been automatically generated by `@changesets/cli`, a build tool that works
4 | with multi-package repos, or single-package repos to help you version and publish your code. You can
5 | find the full documentation for it [in our repository](https://github.com/changesets/changesets)
6 |
7 | We have a quick list of common questions to get you started engaging with this project in
8 | [our documentation](https://github.com/changesets/changesets/blob/main/docs/common-questions.md)
9 |
--------------------------------------------------------------------------------
/.changeset/config.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "https://unpkg.com/@changesets/config@2.3.0/schema.json",
3 | "changelog": "@changesets/cli/changelog",
4 | "commit": false,
5 | "fixed": [],
6 | "linked": [],
7 | "access": "public",
8 | "baseBranch": "main",
9 | "updateInternalDependencies": "patch",
10 | "ignore": ["!@dotenv-run/**", "!@ngx-env/**"]
11 | }
12 |
--------------------------------------------------------------------------------
/.dockerignore:
--------------------------------------------------------------------------------
1 | .turbo
2 | .vscode
3 | .DS_Store
4 | node_modules
5 | dist
6 | tmp
7 |
--------------------------------------------------------------------------------
/.github/workflows/docs.yml:
--------------------------------------------------------------------------------
1 | name: Deploy to GitHub Pages
2 |
3 | on:
4 | # Trigger the workflow every time you push to the `main` branch
5 | # Using a different branch name? Replace `main` with your branch’s name
6 | push:
7 | branches: [main]
8 | # Allows you to run this workflow manually from the Actions tab on GitHub.
9 | workflow_dispatch:
10 |
11 | # Allow this job to clone the repo and create a page deployment
12 | permissions:
13 | contents: read
14 | pages: write
15 | id-token: write
16 |
17 | jobs:
18 | build:
19 | runs-on: ubuntu-latest
20 | steps:
21 | - name: Checkout your repository using git
22 | uses: actions/checkout@v4
23 | - name: Install, build, and upload your site
24 | uses: withastro/action@v2
25 | with:
26 | node-version: 20
27 | path: ./docs # The root location of your Astro project inside the repository. (optional)
28 | package-manager: pnpm@10 # The Node package manager that should be used to install dependencies and build your site. Automatically detected based on your lockfile. (optional)
29 |
30 | deploy:
31 | needs: build
32 | runs-on: ubuntu-latest
33 | environment:
34 | name: github-pages
35 | url: ${{ steps.deployment.outputs.page_url }}
36 | steps:
37 | - name: Deploy to GitHub Pages
38 | id: deployment
39 | uses: actions/deploy-pages@v4
40 |
--------------------------------------------------------------------------------
/.github/workflows/main.yml:
--------------------------------------------------------------------------------
1 | name: Node.js CI
2 |
3 | on:
4 | pull_request:
5 | branches: [main]
6 |
7 | jobs:
8 | build:
9 | name: Build
10 | runs-on: ubuntu-latest
11 | steps:
12 | - uses: actions/checkout@v4
13 | - uses: actions/setup-node@v3
14 | with:
15 | node-version: 20
16 | - uses: pnpm/action-setup@v4
17 | - name: Install Packages
18 | run: |
19 | pnpm i
20 | - name: Build Packages
21 | run: |
22 | pnpm build
23 | pnpm i # create bin scripts
24 | - name: Test Packages
25 | run: |
26 | pnpm test
27 | - name: Build and Test Examples
28 | run: |
29 | cd examples/nx-workspace-old
30 | pnpm playwright install --with-deps
31 | cd apps/ng-app-cli
32 | # npx ng add ../../../packages/angular --skip-confirmation
33 | npx tsc --noEmit --project tsconfig.app.json
34 | cd -
35 | pnpm build:all
36 | pnpm test:all
37 | pnpm e2e:all
38 |
--------------------------------------------------------------------------------
/.github/workflows/release.yml:
--------------------------------------------------------------------------------
1 | name: Node.js CI
2 |
3 | on:
4 | push:
5 | branches: [main]
6 |
7 | jobs:
8 | release:
9 | name: Release
10 | runs-on: ubuntu-latest
11 | steps:
12 | - uses: actions/checkout@v4
13 | - uses: actions/setup-node@v3
14 | with:
15 | node-version: 20
16 | - uses: pnpm/action-setup@v4
17 | - name: Prepare Packages
18 | run: |
19 | pnpm i
20 | pnpm build
21 | pnpm build:docs
22 | - name: Publish @dotenv-run packages
23 | id: changesets
24 | uses: changesets/action@v1
25 | with:
26 | publish: pnpm publish -r --no-git-checks --access public
27 | env:
28 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
29 | NPM_TOKEN: ${{ secrets.NPM_TOKEN }}
30 | NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
31 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | .turbo
2 | .vscode
3 | .DS_Store
4 | node_modules
5 | dist
6 | tmp
7 |
--------------------------------------------------------------------------------
/.husky/pre-commit:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env sh
2 | . "$(dirname -- "$0")/_/husky.sh"
3 |
4 | npm test
5 |
--------------------------------------------------------------------------------
/.npmrc:
--------------------------------------------------------------------------------
1 | auto-install-peers=false
--------------------------------------------------------------------------------
/CNAME:
--------------------------------------------------------------------------------
1 | dotenv.run
--------------------------------------------------------------------------------
/Dockerfile:
--------------------------------------------------------------------------------
1 | FROM node:18
2 |
3 | RUN npm install -g pnpm
4 |
5 | WORKDIR /app
6 |
7 | COPY . /app
8 | RUN pnpm install --frozen-lockfile
9 | RUN cd examples/nx-workspace-old && pnpm playwright install --with-deps && cd -
10 | RUN CI=1 pnpm test
11 | RUN pnpm build && \
12 | cd examples/nx-workspace-old && \
13 | cd apps/ng-app-cli && \
14 | # npx ng add ../../../packages/angular --skip-confirmation
15 | npx tsc --noEmit --project tsconfig.app.json && \
16 | cd - && \
17 | pnpm build:all && \
18 | CI=1 pnpm test:all && \
19 | pnpm e2e:all
20 |
21 | CMD echo "Build successful"
22 |
--------------------------------------------------------------------------------
/docs/.dockerignore:
--------------------------------------------------------------------------------
1 | # build output
2 | dist/
3 | # generated types
4 | .astro/
5 |
6 | # dependencies
7 | node_modules/
8 |
9 | # logs
10 | npm-debug.log*
11 | yarn-debug.log*
12 | yarn-error.log*
13 | pnpm-debug.log*
14 |
15 |
16 | # environment variables
17 | .env
18 | .env.production
19 |
20 | # macOS-specific files
21 | .DS_Store
22 |
--------------------------------------------------------------------------------
/docs/.gitignore:
--------------------------------------------------------------------------------
1 | # build output
2 | dist/
3 | # generated types
4 | .astro/
5 |
6 | # dependencies
7 | node_modules/
8 |
9 | # logs
10 | npm-debug.log*
11 | yarn-debug.log*
12 | yarn-error.log*
13 | pnpm-debug.log*
14 |
15 |
16 | # environment variables
17 | .env
18 | .env.production
19 |
20 | # macOS-specific files
21 | .DS_Store
22 |
--------------------------------------------------------------------------------
/docs/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/docs
2 |
3 | ## 0.1.5
4 |
5 | ### Patch Changes
6 |
7 | - chore: use pnpm workspace protocol for dependencies
8 |
9 | ## 0.1.4
10 |
11 | ### Patch Changes
12 |
13 | - docs: updates packages' README files
14 |
15 | ## 0.1.3
16 |
17 | ### Patch Changes
18 |
19 | - fix(cli): fix unsecure mode alias
20 |
21 | ## 0.1.2
22 |
23 | ### Patch Changes
24 |
25 | - feat(angular): add unsecure mode option
26 |
27 | ## 0.1.1
28 |
29 | ### Patch Changes
30 |
31 | - feat: add secure mode to debug info
32 |
33 | ## 0.1.0
34 |
35 | ### Minor Changes
36 |
37 | - refactor and docs initialization
38 |
--------------------------------------------------------------------------------
/docs/README.md:
--------------------------------------------------------------------------------
1 | # Starlight Starter Kit: Basics
2 |
3 | ```
4 | npm create astro@latest -- --template starlight
5 | ```
6 |
7 | [](https://stackblitz.com/github/withastro/starlight/tree/main/examples/basics)
8 | [](https://codesandbox.io/p/sandbox/github/withastro/starlight/tree/main/examples/basics)
9 |
10 | > 🧑🚀 **Seasoned astronaut?** Delete this file. Have fun!
11 |
12 | ## 🚀 Project Structure
13 |
14 | Inside of your Astro + Starlight project, you'll see the following folders and files:
15 |
16 | ```
17 | .
18 | ├── public/
19 | ├── src/
20 | │ ├── assets/
21 | │ ├── content/
22 | │ │ ├── docs/
23 | │ │ └── config.ts
24 | │ └── env.d.ts
25 | ├── astro.config.mjs
26 | ├── package.json
27 | └── tsconfig.json
28 | ```
29 |
30 | Starlight looks for `.md` or `.mdx` files in the `src/content/docs/` directory. Each file is exposed as a route based on its file name.
31 |
32 | Images can be added to `src/assets/` and embedded in Markdown with a relative link.
33 |
34 | Static assets, like favicons, can be placed in the `public/` directory.
35 |
36 | ## 🧞 Commands
37 |
38 | All commands are run from the root of the project, from a terminal:
39 |
40 | | Command | Action |
41 | | :------------------------ | :----------------------------------------------- |
42 | | `npm install` | Installs dependencies |
43 | | `npm run dev` | Starts local dev server at `localhost:3000` |
44 | | `npm run build` | Build your production site to `./dist/` |
45 | | `npm run preview` | Preview your build locally, before deploying |
46 | | `npm run astro ...` | Run CLI commands like `astro add`, `astro check` |
47 | | `npm run astro -- --help` | Get help using the Astro CLI |
48 |
49 | ## 👀 Want to learn more?
50 |
51 | Check out [Starlight’s docs](https://starlight.astro.build/), read [the Astro documentation](https://docs.astro.build), or jump into the [Astro Discord server](https://astro.build/chat).
52 |
--------------------------------------------------------------------------------
/docs/astro.config.mjs:
--------------------------------------------------------------------------------
1 | import { defineConfig } from 'astro/config';
2 | import starlight from '@astrojs/starlight';
3 |
4 | // https://astro.build/config
5 | export default defineConfig({
6 | site: 'https://dotenv.run',
7 | base: '/',
8 | integrations: [
9 | starlight({
10 | title: 'dotenv.run',
11 | social: {
12 | github: 'https://github.com/chihab/dotenv-run',
13 | },
14 | sidebar: [
15 | {
16 | label: 'Getting Started',
17 | items: [
18 | { label: 'Introduction', link: '/' },
19 | { label: 'Quick Start', link: '/getting-started/quick-start/' },
20 | { label: 'Variables', items: [{ label: '.env files', link: '/getting-started/env-files/' }, { label: 'expand', link: '/getting-started/expand/' }, { label: 'command line', link: '/getting-started/command-line/' }] },
21 | { label: 'Loading Priorities', link: '/getting-started/loading-priorities/' },
22 | { label: 'Monorepo Setup ✨', link: '/getting-started/monorepo-setup/' },
23 | // { label: 'Comparison', link: '/getting-started/comparison/' },
24 | // { label: 'About', link: '/getting-started/about/' },
25 | ],
26 | },
27 | {
28 | label: 'Integrations',
29 | items: [
30 | { label: 'CLI', link: '/integrations/cli/' },
31 | { label: 'Node.js', link: '/integrations/loader/' },
32 | { label: 'Rollup', link: '/integrations/rollup/' },
33 | { label: 'Webpack', link: '/integrations/webpack/' },
34 | { label: 'Vite', link: '/integrations/vite/' },
35 | // { label: 'Babel', link: '/integrations/webpack/' },
36 | // { label: 'Jest', link: '/integrations/jest/' },
37 | // { label: 'SWC', link: '/integrations/swc/' },
38 | // { label: 'ESBuild', link: '/integrations/esbuild/' },
39 | { label: 'Core', link: '/integrations/core/' },
40 | ],
41 | },
42 | // {
43 | // label: 'Recipes',
44 | // items: [
45 | // { label: 'Nx', link: '/recipes/nx/' },
46 | // { label: 'Turbo', link: '/recipes/turbo/' },
47 | // { label: 'Docker', link: '/recipes/docker/' },
48 | // { label: 'Next.js', link: '/recipes/next.js/' },
49 | // { label: 'Angular', link: '/integrations/angular/' },
50 | // ],
51 | // },
52 | ],
53 | customCss: [
54 | // Relative path to your custom CSS file
55 | './src/styles/custom.css',
56 | ],
57 | }),
58 | ],
59 | image: { service: { entrypoint: 'astro/assets/services/sharp' } },
60 | });
61 |
--------------------------------------------------------------------------------
/docs/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/docs",
3 | "private": true,
4 | "type": "module",
5 | "version": "0.1.5",
6 | "scripts": {
7 | "dev": "astro dev",
8 | "start": "astro dev",
9 | "build": "astro build",
10 | "preview": "astro preview",
11 | "astro": "astro"
12 | },
13 | "dependencies": {
14 | "@astrojs/starlight": "^0.15.4",
15 | "astro": "^4.15.11",
16 | "sharp": "^0.33.5"
17 | }
18 | }
--------------------------------------------------------------------------------
/docs/public/favicon.svg:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/docs/src/assets/houston.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/docs/src/assets/houston.webp
--------------------------------------------------------------------------------
/docs/src/content/config.ts:
--------------------------------------------------------------------------------
1 | import { defineCollection } from 'astro:content';
2 | import { docsSchema, i18nSchema } from '@astrojs/starlight/schema';
3 |
4 | export const collections = {
5 | docs: defineCollection({ schema: docsSchema() }),
6 | i18n: defineCollection({ type: 'data', schema: i18nSchema() }),
7 | };
8 |
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/about.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: About
3 | ---
4 |
5 | TODO
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/architecture.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Architecture
3 | ---
4 |
5 | @dotenv-run/cli
6 | |- @dotenv-run/core
7 | * Locate .env files and creates a `dotenv` object
8 | * Expands variables in .env files
9 | * Filter variables by prefix
10 |
11 | @dotenv-run/webpack
12 | * Webpack plugin that injects environment variables into the build
13 | |- @dotenv-run/core
14 |
15 | @angular-builders/custom-webpack
16 | |- @dotenv-run/webpack
17 |
18 | @ngx-env/builder
19 | |- @dotenv-run/webpack
20 |
21 | @ngx-env/esbuilder
22 | |- @dotenv-run/esbuilder
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/command-line.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Command Line
3 | ---
4 |
5 | Defining environment variables can vary between OSes. It’s also important to know that this manner is temporary for the life of the shell session.
6 |
7 |
8 | ## Windows (cmd.exe)
9 |
10 | ```cmd
11 | set "API_URL=abcdef" && dotenv-run -- npm start
12 | ```
13 |
14 | (Note: Quotes around the variable assignment are required to avoid a trailing whitespace.)
15 |
16 | ## Windows (Powershell)
17 |
18 | ```Powershell
19 | ($env:API_URL = "abcdef") -and (dotenv-run -- npm start)
20 | ```
21 |
22 | ## Linux, macOS (Bash)
23 |
24 | ```sh
25 | API_URL=abcdef dotenv-run -- npm start
26 | ```
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/comparison.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Comparison
3 | ---
4 |
5 | TODO
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/env-files.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: .env files
3 | ---
4 |
5 | A .env file is a simple text file that stores environment variables. Environment variables are key-value pairs that are used to configure applications and services. They can be used to store things like database passwords, API keys, and other sensitive information.
6 |
7 | .env files are typically located in the root directory of a project. They are ignored by version control systems, so you can store sensitive information in them without worrying about it being exposed.
8 |
9 | To use a .env file, you need to load it into your application's environment. There are a number of ways to do this, depending on the programming language and framework you are using.
10 |
11 | Here is an example of a .env file:
12 |
13 | ```
14 | DATABASE_URL=postgres://user:password@localhost:5432/my_database
15 | API_KEY=1234567890
16 | ```
17 |
18 | This file defines two environment variables:
19 |
20 | * DATABASE_URL: The URL of the database server
21 | * API_KEY: The API key for a third-party service
22 |
23 | .env files are a convenient way to store environment variables. They are easy to use and secure, making them a valuable tool for developers.
24 |
25 | Here are some additional things to keep in mind when using .env files:
26 |
27 | * Use a consistent naming convention for your environment variables. This will make it easier to find and manage them.
28 | * Use comments in your .env file to document what each variable is used for. This will be helpful for future developers who need to work on your project.
29 | * Don't commit your .env file to version control. This will help to keep your sensitive information secure.
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/expand.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Expanding Variables
3 | ---
4 |
5 |
6 | You can expand variables already available on your machine for use in your `.env`
7 |
8 | For example:
9 |
10 | ```shell
11 | VERSION=$npm_package_version
12 | HOSTNAME=$HOSTNAME
13 | ```
14 |
15 | Or expand variables local to the current `.env` file:
16 |
17 | ```shell
18 | DOMAIN=www.example.com
19 | FOO=$DOMAIN/foo
20 | BAR=$DOMAIN/bar
21 | ```
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/loading-priorities.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Loading Priorities
3 | ---
4 |
5 | `@dotenv-run/cli` uses [dotenv](https://github.com/motdotla/dotenv) to support loading environment variables from `.env` files.
6 |
7 | `@dotenv-run/cli` loads `.env` files with these specific names for the following `-e ENV` value, files on the top have less priority than files on the bottom.
8 |
9 | An env file for a specific mode (e.g. .env.production) will take higher priority than a generic one (e.g. .env).
10 |
11 | | valid `.env` filenames | `ENV=*` | `ENV=test` |
12 | | -------------------------- | -------------- | --------------- |
13 | | `.env` | ✔️ | ✔️ |
14 | | `.env.local` | ✔️ | ✖️ |
15 | | `.env.${ENV}` | ✔️ | ✔️ |
16 | | `.env.${ENV}.local` | ✔️ | ✔️ |
17 |
18 | In addition, environment variables that already exist when the CLI is executed have the highest priority and will not be overwritten by .env files. For example, when running `SOME_KEY=123 dotenv-run`.
19 |
20 |
21 |
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/monorepo-setup.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Monorepo Setup
3 | ---
4 |
5 | In a monorepo configuration, `.env.*` files can be defined in the root workspace and overriden by each application:
6 |
7 | Let's say we have the following monorepo structure:
8 |
9 | ```shell
10 | platform
11 | ├── apps
12 | │ ├── vite-app
13 | │ │ ├── .env.local # API_USERS=http://localhost:3001/users
14 | │ │ └── vite.config.js
15 | │ └── webpack-app
16 | │ │ ├── package.json
17 | │ │ └── webapp.config.mjs
18 | │ └── node-app
19 | │ └── package.json
20 | ├── libs
21 | │ └── rollup-lib
22 | │ ├── package.json
23 | │ └── rollup.config.mjs
24 | ├── .env.dev # API_BASE=https://dotenv-run.dev
25 | ├── .env.prod # API_BASE=https://dotenv-run.app
26 | ├── .env # API_USERS=$API_BASE/api/v1/users API_AUTH=https://$API_BASE/auth
27 | ├── nx.json
28 | └── package.json
29 | ```
30 |
31 | `dotenv-run` will search and load `.env.*` files located in the root workspace down to the current working directory.
32 |
33 | ### cli
34 |
35 | ```sh
36 | NODE_ENV=prod nx run build
37 | ✔ /platform/.env.prod
38 | ✔ /platform/.env
39 | https://dotenv-run.app/api/v1/users
40 | ```
41 |
42 | ```shell
43 | cd /platform/apps/frontend1
44 | NODE_ENV=dev vite
45 | ✔ /platform/apps/frontend1/.env.local
46 | ✔ /platform/.env.dev
47 | ✔ /platform/.env
48 | API_USERS http://localhost:3001/users
49 | ```
50 |
51 | See [vite plugin](/docs/integrations/vite) for more details.
52 |
--------------------------------------------------------------------------------
/docs/src/content/docs/getting-started/options.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Options
3 | ---
--------------------------------------------------------------------------------
/docs/src/content/docs/index.mdx:
--------------------------------------------------------------------------------
1 | ---
2 | title: Introduction
3 | ---
4 |
5 | Defining configuration as environment variables is one of the tenets of a [twelve-factor app](https://12factor.net/config), it separates the config from your codebase and keeps it under your control.
6 |
7 | `dotenv-run` is a collection of packages that use **dotenv** to support loading environment variables from `.env` files with multiple integrations.
8 |
9 | Here are some of the benefits of using @dotenv-run:
10 |
11 | - **Simple**: seamelessly integrates with your existing workflow.
12 | - **Flexible**: supports multiple `.env` files and loading priorities.
13 | - **Expand**: supports expanding variables already available on your machine for use in your `.env` files.
14 | - **Secure**: supports filtering environment variables by prefix.
15 | - **Monorepo ✨**: supports monorepo projects with multiple applications. .env files can be defined in the root workspace and overriden by each application.
16 | - **TypeScript**: supports TypeScript projects with type definitions for `process.env` and `import.meta.env`.
17 | - **ESM**: supports `process.env` and `import.meta.env` in ESM modules.
18 | - **Universal**: supports multiple intergrations including CLI, Node.js preload, Webpack, Rollup, Vite, and esbuild.
19 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/babel.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Babel
3 | ---
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/core.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Core
3 | ---
4 |
5 | ## install
6 |
7 | ```console
8 | npm add @dotenv-run/core
9 | ```
10 |
11 | ## usage
12 |
13 | ```js
14 | // index.js
15 | import { expand, paths } from "@dotenv-run/core";
16 | expand(paths(process.env.NODE_ENV, '../../'));
17 | console.log(process.env.API_USERS);
18 | ```
19 |
20 | given the following files:
21 |
22 | ```shell
23 | .env
24 | API_USERS=$API_BASE/v1/users
25 | API_AUTH=$API_BASE/v1/auth
26 | .env.dev
27 | API_BASE=https://localhost:3000
28 | .env.prod
29 | API_BASE=https://dotenv-run.app
30 | ```
31 |
32 | then:
33 |
34 | ```shell
35 | NODE_ENV=dev node index.js
36 | https://localhost:3000/v1/users
37 | ```
38 |
39 | ```shell
40 | NODE_ENV=prod node index.js
41 | https://dotenv-run.app/v1/users
42 | ```
43 |
44 | The list of options is the same as the ones supported by `@dotenv-run/core`. Please refer to the [API](#api) section for more details.
45 |
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/esbuild.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: ESBuild
3 | ---
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/loader.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Loader
3 | ---
4 |
5 | # install
6 |
7 | ```console
8 | npm add @dotenv-run/load
9 | ```
10 |
11 | # usage
12 |
13 | ```js
14 | // index.js
15 | console.log(process.env.API_USERS);
16 | ```
17 |
18 | Given the following `.env` files:
19 |
20 | ```shell
21 | .env
22 | API_USERS=$API_BASE/v1/users
23 | API_AUTH=$API_BASE/v1/auth
24 | .env.dev
25 | API_BASE=https://localhost:3000
26 | .env.prod
27 | API_BASE=https://dotenv-run.app
28 | ```
29 |
30 | ```shell
31 | NODE_ENV=dev node -r @dotenv-run/load ./index.js
32 | https://localhost:3000/v1/users
33 | ```
34 |
35 | ```shell
36 | NODE_ENV=prod node -r @dotenv-run/load ./index.js
37 | https://dotenv-run.app/v1/users
38 | ```
39 |
40 | ```shell
41 | NODE_ENV=prod NODE_OPTIONS='-r @dotenv-run/load' node ./index.js
42 | https://dotenv-run.app/v1/users
43 | ```
44 |
45 |
46 |
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/node.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Node.js
3 | ---
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/rollup.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Rollup
3 | ---
4 |
5 | ## install
6 |
7 |
8 | ```console
9 | npm add @dotenv-run/rollup --save-dev
10 | ```
11 |
12 | ## usage
13 |
14 | Create a `rollup.config.js` [configuration file](https://www.rollupjs.org/guide/en/#configuration-files) and import the plugin:
15 |
16 | ```js
17 | import env from '@dotenv-run/rollup';
18 |
19 | export default {
20 | input: 'src/index.js',
21 | output: {
22 | file: 'dist/index.js',
23 | },
24 | plugins: [
25 | env({ prefix: 'API', verbose: true, root: '../../..' })
26 | ]
27 | };
28 | ```
29 |
30 | Then call `rollup` either via the [CLI](https://www.rollupjs.org/guide/en/#command-line-reference) or the [API](https://www.rollupjs.org/guide/en/#javascript-api).
31 |
32 |
33 | The list of options is the same as the ones supported by `@dotenv-run/core`. Please refer to the [API](#api) section for more details.
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/vite.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Vite
3 | ---
4 |
5 | ## Install
6 |
7 | ```console
8 | npm add @dotenv-run/vite --save-dev
9 | ```
10 |
11 | ## Usage
12 |
13 | Create a `vite.config.js` [configuration file](https://vite.dev/config) and import the plugin:
14 |
15 | ```js
16 | import env from "@dotenv-run/vite";
17 |
18 | export default {
19 | envPrefix: 'MY_PREFIX_',
20 | envDir: './my-env-directory',
21 | plugins: [env()],
22 | };
23 | ```
24 |
25 | Then call `vite` or `vite build` either via the [CLI](https://vite.dev/guide/cli.html).
26 |
27 | The available options are similar to those supported by [`@dotenv-run/core`](https://www.npmjs.com/package/@dotenv-run/core), but this plugin seamlessly integrates with Vite by automatically deriving the root, prefix, and environment values from its standard configuration, ensuring a more cohesive experience. For more details, refer to the API section.
28 |
--------------------------------------------------------------------------------
/docs/src/content/docs/integrations/webpack.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Webpack
3 | ---
4 |
5 | ## install
6 |
7 | ```console
8 | npm add @dotenv-run/webpack --save-dev
9 | ```
10 |
11 | ## usage
12 |
13 | Create a `webpack.config.js` [configuration file](https://www.webpackjs.org/guide/en/#configuration-files) and import the plugin:
14 |
15 | ```js
16 | import { DotenvRunPlugin } from '@dotenv-run/webpack';
17 | import path from 'path';
18 |
19 | const __dirname = path.resolve();
20 |
21 | export default {
22 | entry: './src/index.js',
23 | output: {
24 | filename: 'main.js',
25 | path: path.resolve(__dirname, 'dist'),
26 | },
27 | plugins: [
28 | new DotenvRunPlugin(
29 | { prefix: 'API', verbose: true, root: '../../..' },
30 | __dirname
31 | )
32 | ]
33 | }
34 | ```
35 |
36 | The list of options is the same as the ones supported by `@dotenv-run/core`. Please refer to the [API](#api) section for more details.
--------------------------------------------------------------------------------
/docs/src/content/docs/recipes/angular.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Angular
3 | ---
--------------------------------------------------------------------------------
/docs/src/env.d.ts:
--------------------------------------------------------------------------------
1 | ///
2 | ///
3 |
--------------------------------------------------------------------------------
/docs/src/styles/custom.css:
--------------------------------------------------------------------------------
1 | /* Dark mode colors. */
2 | :root {
3 | --sl-color-accent-low: #331833;
4 | --sl-color-accent: #2db492;
5 | --sl-color-accent-high: #5f937f;
6 | --sl-color-white: #ffffff;
7 | --sl-color-gray-1: #e1f0ff;
8 | --sl-color-gray-2: #a7c6e5;
9 | --sl-color-gray-5: #3c4348;
10 | --sl-color-gray-5: #3c4348;
11 | --sl-color-gray-5: #3c4348;
12 | --sl-color-gray-5: #3c4348;
13 | --sl-color-gray-5: #3c4348;
14 | }
15 |
16 | /* Light mode colors. */
17 | :root[data-theme='light'] {
18 | --sl-color-accent-low: #e8cde7;
19 | --sl-color-accent: #2db492;
20 | --sl-color-accent-high: #5f937f;
21 | --sl-color-white: #011930;
22 | --sl-color-gray-1: #002849;
23 | --sl-color-gray-2: #003a66;
24 | --sl-color-gray-3: #195b93;
25 | --sl-color-gray-4: #5290cc;
26 | --sl-color-gray-5: #a7c6e5;
27 | --sl-color-gray-6: #e1f0ff;
28 | --sl-color-gray-7: #f0f7ff;
29 | --sl-color-black: #ffffff;
30 | }
--------------------------------------------------------------------------------
/docs/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "astro/tsconfigs/strict"
3 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.dockerignore:
--------------------------------------------------------------------------------
1 | .nx
2 | test-results
3 | tests
4 | playwright-report
5 | tests-examples
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.env.app:
--------------------------------------------------------------------------------
1 | API_USERS=$API_BASE/api/v1/users
2 | API_AUTH=$API_BASE/api/v1/auth
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.env.app.dev:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.dev
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.env.app.prod:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.app
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.gitignore:
--------------------------------------------------------------------------------
1 | .nx
2 | test-results
3 | playwright-report
4 | tests-examples
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.secrets:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-secret-root-run.app
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.secrets.prod:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-secret-root-prod-run.app
--------------------------------------------------------------------------------
/examples/nx-workspace-old/.verdaccio/config.yml:
--------------------------------------------------------------------------------
1 | # path to a directory with all packages
2 | storage: /tmp/local-registry/storage
3 |
4 | # a list of other known repositories we can talk to
5 | uplinks:
6 | npmjs:
7 | url: https://registry.npmjs.org/
8 | maxage: 60m
9 |
10 | packages:
11 | "**":
12 | # give all users (including non-authenticated users) full access
13 | # because it is a local registry
14 | access: $all
15 | publish: $all
16 | unpublish: $all
17 |
18 | # if package is not available locally, proxy requests to npm registry
19 | proxy: npmjs
20 |
21 | # log settings
22 | logs:
23 | type: stdout
24 | format: pretty
25 | level: warn
26 |
27 | publish:
28 | allow_offline: true # set offline to true to allow publish offline
29 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/.secrets:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-secret-subapp-run.app
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/.secrets.local:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-secret-subapp-local-run.app
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/.secrets.prod:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-secret-subapp-prod-run.app
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/.secrets.prod.local:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-secret-subapp-prod-local-run.app
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/__snapshots__/cli.test.ts.snap:
--------------------------------------------------------------------------------
1 | // Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
2 |
3 | exports[`dotenv-run should give the expected output > dev 1`] = `
4 | "Hello World https://dotenv-run.dev/api/v1/users
5 | "
6 | `;
7 |
8 | exports[`dotenv-run should give the expected output > empty 1`] = `
9 | "Hello World /api/v1/users
10 | "
11 | `;
12 |
13 | exports[`dotenv-run should give the expected output > multi 1`] = `
14 | "Hello World https://dotenv-secret-subapp-prod-local-run.app/api/v1/users
15 | "
16 | `;
17 |
18 | exports[`dotenv-run should give the expected output > prod 1`] = `
19 | "Hello World https://dotenv-run.app/api/v1/users
20 | "
21 | `;
22 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/cli.test.ts:
--------------------------------------------------------------------------------
1 | import { execSync } from "child_process";
2 | import { describe, it, expect } from "vitest";
3 |
4 | describe("dotenv-run should give the expected output", () => {
5 | it("empty", () => {
6 | const actual = execSync(
7 | "dotenv-run -f .env.app -- bash -c 'echo \"Hello World $API_USERS\"'",
8 | {
9 | encoding: "utf8",
10 | }
11 | );
12 | expect(actual).toMatchSnapshot();
13 | });
14 |
15 | it("dev", () => {
16 | const actual = execSync(
17 | "NODE_ENV=dev dotenv-run -f .env.app -- bash -c 'echo \"Hello World $API_USERS\"'",
18 | {
19 | encoding: "utf8",
20 | }
21 | );
22 | expect(actual).toMatchSnapshot();
23 | });
24 |
25 | it("prod", () => {
26 | const actual = execSync(
27 | "NODE_ENV=prod dotenv-run -f .env.app -e prod -- bash -c 'echo \"Hello World $API_USERS\"'",
28 | {
29 | encoding: "utf8",
30 | }
31 | );
32 | expect(actual).toMatchSnapshot();
33 | });
34 |
35 | it("multi", () => {
36 | const actual = execSync(
37 | "NODE_ENV=prod dotenv-run -e prod -f .secrets,.env.app -- bash -c 'echo \"Hello World $API_USERS\"'",
38 | {
39 | encoding: "utf8",
40 | }
41 | );
42 | expect(actual).toMatchSnapshot();
43 | });
44 | });
45 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "cli-app",
3 | "version": "1.0.0",
4 | "private": true,
5 | "scripts": {
6 | "test": "vitest",
7 | "test:dev": "NODE_ENV=dev dotenv-run -r ../../ -f .env,.secrets -- bash -c 'echo \"Hello World $API_USERS\"'",
8 | "build": "echo $API_USERS"
9 | }
10 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/project.json:
--------------------------------------------------------------------------------
1 | {}
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/cli-app/turbo.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "//"
3 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/.app.prod:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-cli/.app.prod
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/.editorconfig:
--------------------------------------------------------------------------------
1 | # Editor configuration, see https://editorconfig.org
2 | root = true
3 |
4 | [*]
5 | charset = utf-8
6 | indent_style = space
7 | indent_size = 2
8 | insert_final_newline = true
9 | trim_trailing_whitespace = true
10 |
11 | [*.ts]
12 | quote_type = single
13 |
14 | [*.md]
15 | max_line_length = off
16 | trim_trailing_whitespace = false
17 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/.env:
--------------------------------------------------------------------------------
1 | NGX_VERSION=IGNORED_SINCE_SET_IN_ENV_LOCAL
2 | NGX_BRANCH=main
3 |
4 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/.env.local:
--------------------------------------------------------------------------------
1 | NGX_VERSION=$npm_package_version
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/.env.prod:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-cli/.env.prod
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/.env.test:
--------------------------------------------------------------------------------
1 | NGX_VERSION=12.0.0
2 | NGX_BRANCH=test
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/.gitignore:
--------------------------------------------------------------------------------
1 | # See http://help.github.com/ignore-files/ for more about ignoring files.
2 |
3 | # Compiled output
4 | /dist
5 | /tmp
6 | /out-tsc
7 | /bazel-out
8 |
9 | # Node
10 | /node_modules
11 | npm-debug.log
12 | yarn-error.log
13 |
14 | # IDEs and editors
15 | .idea/
16 | .project
17 | .classpath
18 | .c9/
19 | *.launch
20 | .settings/
21 | *.sublime-workspace
22 |
23 | # Visual Studio Code
24 | .vscode/*
25 | !.vscode/settings.json
26 | !.vscode/tasks.json
27 | !.vscode/launch.json
28 | !.vscode/extensions.json
29 | .history/*
30 |
31 | # Miscellaneous
32 | /.angular/cache
33 | .sass-cache/
34 | /connect.lock
35 | /coverage
36 | /libpeerconnection.log
37 | testem.log
38 | /typings
39 |
40 | # System files
41 | .DS_Store
42 | Thumbs.db
43 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/README.md:
--------------------------------------------------------------------------------
1 | # NgxEnvDemo
2 |
3 | This project was generated with [Angular CLI](https://github.com/angular/angular-cli) version 17.0.0.
4 |
5 | ## Development server
6 |
7 | Run `ng serve` for a dev server. Navigate to `http://localhost:4200/`. The application will automatically reload if you change any of the source files.
8 |
9 | ## Code scaffolding
10 |
11 | Run `ng generate component component-name` to generate a new component. You can also use `ng generate directive|pipe|service|class|guard|interface|enum|module`.
12 |
13 | ## Build
14 |
15 | Run `ng build` to build the project. The build artifacts will be stored in the `dist/` directory.
16 |
17 | ## Running unit tests
18 |
19 | Run `ng test` to execute the unit tests via [Karma](https://karma-runner.github.io).
20 |
21 | ## Running end-to-end tests
22 |
23 | Run `ng e2e` to execute the end-to-end tests via a platform of your choice. To use this command, you need to first add a package that implements end-to-end testing capabilities.
24 |
25 | ## Further help
26 |
27 | To get more help on the Angular CLI use `ng help` or go check out the [Angular CLI Overview and Command Reference](https://angular.io/cli) page.
28 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/jest.config.mjs:
--------------------------------------------------------------------------------
1 | const jestConfig = {
2 | preset: "jest-preset-angular/presets/defaults-esm",
3 | setupFilesAfterEnv: ["/setup-jest.ts"],
4 | testMatch: ["/src/app/**/*.(spec|jest).ts"],
5 | cache: false,
6 | moduleNameMapper: {
7 | "^rxjs(/operators$)?$":
8 | "/node_modules/rxjs/dist/bundles/rxjs.umd.js",
9 | tslib: "/node_modules/tslib/tslib.es6.mjs",
10 | },
11 | transform: {
12 | "^.+\\.(ts)$": [
13 | "@dotenv-run/jest-angular",
14 | {
15 | useESM: true,
16 | stringifyContentPathRegex: "\\.(html|svg)$",
17 | },
18 | ],
19 | },
20 | };
21 |
22 | export default jestConfig;
23 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/karma.conf.js:
--------------------------------------------------------------------------------
1 | // Karma configuration file, see link for more information
2 | // https://karma-runner.github.io/1.0/config/configuration-file.html
3 |
4 | module.exports = function (config) {
5 | config.set({
6 | basePath: "",
7 | frameworks: ["jasmine", "@angular-devkit/build-angular"],
8 | plugins: [
9 | require("karma-jasmine"),
10 | require("karma-chrome-launcher"),
11 | require("karma-jasmine-html-reporter"),
12 | require("karma-coverage"),
13 | require("@angular-devkit/build-angular/plugins/karma"),
14 | ],
15 | client: {
16 | jasmine: {
17 | // you can add configuration options for Jasmine here
18 | // the possible options are listed at https://jasmine.github.io/api/edge/Configuration.html
19 | // for example, you can disable the random execution with `random: false`
20 | // or set a specific seed with `seed: 4321`
21 | },
22 | clearContext: false, // leave Jasmine Spec Runner output visible in browser
23 | },
24 | jasmineHtmlReporter: {
25 | suppressAll: true, // removes the duplicated traces
26 | },
27 | coverageReporter: {
28 | dir: require("path").join(__dirname, "./coverage/ng-app-cli"),
29 | subdir: ".",
30 | reporters: [{ type: "html" }, { type: "text-summary" }],
31 | },
32 | reporters: ["progress", "kjhtml"],
33 | port: 9876,
34 | colors: true,
35 | logLevel: config.LOG_INFO,
36 | autoWatch: true,
37 | browsers: ["ChromeHeadless"],
38 | singleRun: false,
39 | restartOnFileChange: true,
40 | });
41 | };
42 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/playwright.config.ts:
--------------------------------------------------------------------------------
1 | import { defineConfig, devices } from "@playwright/test";
2 |
3 | export default defineConfig({
4 | // Look for test files in the "tests" directory, relative to this configuration file.
5 | testDir: "tests",
6 |
7 | // Run all tests in parallel.
8 | fullyParallel: true,
9 |
10 | use: {
11 | // Base URL to use in actions like `await page.goto('/')`.
12 | baseURL: "http://127.0.0.1:8081",
13 |
14 | // Collect trace when retrying the failed test.
15 | trace: "on-first-retry",
16 | },
17 | // Configure projects for major browsers.
18 | projects: [
19 | {
20 | name: "chromium",
21 | use: { ...devices["Desktop Chrome"] },
22 | },
23 | ],
24 | // Run your local dev server before starting the tests.
25 | webServer: {
26 | command: "npm run static -- -p 8081",
27 | url: "http://127.0.0.1:8081"
28 | },
29 | });
30 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/project.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "ng-app-cli"
3 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/setup-jest.ts:
--------------------------------------------------------------------------------
1 | import 'jest-preset-angular/setup-jest.mjs';
2 | import { env } from '@dotenv-run/core';
3 | env({ root: '../../..', files: ['.env', '.env.app'] });
4 |
5 | import '@angular/localize/init';
6 | import { TextEncoder } from 'util';
7 | Object.defineProperty(window, 'TextEncoder', {
8 | writable: true,
9 | value: TextEncoder,
10 | });
11 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.component.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.component.css
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.component.html:
--------------------------------------------------------------------------------
1 | {{ title }}
2 |
3 | element string
4 |
5 |
6 | NAME |
7 | VALUE |
8 |
9 |
10 |
11 |
12 | ENV |
13 |
14 | {{ env }}
15 | |
16 |
17 |
18 | VERSION |
19 |
20 | {{ version }}
21 | |
22 |
23 |
24 | BRANCH |
25 |
26 | {{ branch }}
27 | |
28 |
29 |
30 |
31 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.component.spec.ts:
--------------------------------------------------------------------------------
1 | import { ComponentFixture, TestBed } from '@angular/core/testing';
2 | import { AppComponent } from './app.component';
3 |
4 | describe('AppComponent', () => {
5 | let component: AppComponent;
6 | let fixture: ComponentFixture;
7 |
8 | beforeEach(async () => {
9 | await TestBed.configureTestingModule({
10 | imports: [AppComponent],
11 | }).compileComponents();
12 | fixture = TestBed.createComponent(AppComponent);
13 | component = fixture.componentInstance;
14 | fixture.detectChanges();
15 | });
16 |
17 | it('should create the app 2', () => {
18 | expect(component).toBeTruthy();
19 | });
20 |
21 | it(`should have the 'Hello world' title`, () => {
22 | expect(component.title).toEqual('Hello world');
23 | expect(component.env).toEqual('test');
24 | });
25 | });
26 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.component.ts:
--------------------------------------------------------------------------------
1 | import { CommonModule } from '@angular/common';
2 | import { Component } from '@angular/core';
3 | import { RouterOutlet } from '@angular/router';
4 | import { environment } from '../environments/environment';
5 |
6 | @Component({
7 | selector: 'app-root',
8 | standalone: true,
9 | templateUrl: './app.component.html',
10 | styleUrls: ['./app.component.css'],
11 | })
12 | export class AppComponent {
13 | title = $localize`Hello world`;
14 | env = import.meta.env['NODE_ENV'];
15 | version = environment.env.NGX_VERSION;
16 | branch = import.meta.env['NGX_BRANCH'];
17 | }
18 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.config.server.ts:
--------------------------------------------------------------------------------
1 | import { mergeApplicationConfig, ApplicationConfig } from '@angular/core';
2 | import { provideServerRendering } from '@angular/platform-server';
3 | import { appConfig } from './app.config';
4 |
5 | const serverConfig: ApplicationConfig = {
6 | providers: [provideServerRendering()],
7 | };
8 |
9 | export const config = mergeApplicationConfig(appConfig, serverConfig);
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.config.ts:
--------------------------------------------------------------------------------
1 | import { ApplicationConfig } from '@angular/core';
2 | import { provideRouter } from '@angular/router';
3 |
4 | import { provideClientHydration } from '@angular/platform-browser';
5 | import { routes } from './app.routes';
6 |
7 | export const appConfig: ApplicationConfig = {
8 | providers: [provideRouter(routes), provideClientHydration()],
9 | };
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/app.routes.ts:
--------------------------------------------------------------------------------
1 | import { Routes } from '@angular/router';
2 |
3 | export const routes: Routes = [];
4 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/hello/hello.component.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-cli/src/app/hello/hello.component.css
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/hello/hello.component.html:
--------------------------------------------------------------------------------
1 | hello works!
2 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/hello/hello.component.spec.ts:
--------------------------------------------------------------------------------
1 | import { ComponentFixture, TestBed } from '@angular/core/testing';
2 |
3 | import { HelloComponent } from './hello.component';
4 |
5 | describe('HelloComponent', () => {
6 | let component: HelloComponent;
7 | let fixture: ComponentFixture;
8 |
9 | beforeEach(async () => {
10 | await TestBed.configureTestingModule({
11 | imports: [HelloComponent]
12 | })
13 | .compileComponents();
14 |
15 | fixture = TestBed.createComponent(HelloComponent);
16 | component = fixture.componentInstance;
17 | fixture.detectChanges();
18 | });
19 |
20 | it('should create', () => {
21 | expect(component).toBeTruthy();
22 | });
23 | });
24 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/app/hello/hello.component.ts:
--------------------------------------------------------------------------------
1 | import { Component } from '@angular/core';
2 |
3 | @Component({
4 | selector: 'app-hello',
5 | standalone: true,
6 | imports: [],
7 | templateUrl: './hello.component.html',
8 | styleUrl: './hello.component.css'
9 | })
10 | export class HelloComponent {
11 |
12 | }
13 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/assets/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-cli/src/assets/.gitkeep
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/env.d.ts:
--------------------------------------------------------------------------------
1 | // Define the type of the environment variables.
2 | declare interface Env {
3 | readonly NODE_ENV: string;
4 | // Replace the following with your own environment variables.
5 | // Example: NGX_VERSION: string;
6 | NGX_BRANCH: string;
7 | NGX_VERSION: string;
8 | [key: string]: any;
9 | }
10 |
11 | declare interface ImportMeta {
12 | env: Env;
13 | }
14 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/environments/environment.prod.ts:
--------------------------------------------------------------------------------
1 | export const environment = {
2 | production: true,
3 | env: {
4 | NGX_VERSION: import.meta.env['NGX_VERSION'],
5 | },
6 | };
7 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/environments/environment.ts:
--------------------------------------------------------------------------------
1 | // This file can be replaced during build by using the `fileReplacements` array.
2 | // `ng build` replaces `environment.ts` with `environment.prod.ts`.
3 | // The list of file replacements can be found in `angular.json`.
4 |
5 | export const environment = {
6 | production: false,
7 | env: {
8 | NGX_VERSION: import.meta.env['NGX_VERSION'],
9 | },
10 | };
11 |
12 | /*
13 | * For easier debugging in development mode, you can import the following file
14 | * to ignore zone related error stack frames such as `zone.run`, `zoneDelegate.invokeTask`.
15 | *
16 | * This import should be commented out in production mode because it will have a negative impact
17 | * on performance if an error is thrown.
18 | */
19 | // import 'zone.js/plugins/zone-error'; // Included with Angular CLI.
20 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-cli/src/favicon.ico
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 | %NGX_VERSION%
9 |
10 |
11 | %NODE_ENV%
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/locale/messages.fr.xlf:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | Attribute string
7 |
8 | src/app/app.component.html
9 | 3
10 |
11 |
12 |
13 | element string
14 |
15 | src/app/app.component.html
16 | 3,4
17 |
18 |
19 |
20 | Hello world
21 |
22 | src/app/app.component.ts
23 | 14
24 |
25 |
26 |
27 |
28 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/locale/messages.xlf:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | Attribute string
7 |
8 | src/app/app.component.html
9 | 3
10 |
11 |
12 |
13 | element string
14 |
15 | src/app/app.component.html
16 | 3,4
17 |
18 |
19 |
20 | Hello world
21 |
22 | src/app/app.component.ts
23 | 14
24 |
25 |
26 |
27 |
28 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/main.server.ts:
--------------------------------------------------------------------------------
1 | import '@ngx-env/builder/runtime';
2 |
3 | import { bootstrapApplication } from '@angular/platform-browser';
4 | import { AppComponent } from './app/app.component';
5 | import { config } from './app/app.config.server';
6 |
7 | const bootstrap = () => bootstrapApplication(AppComponent, config);
8 |
9 | export default bootstrap;
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/main.ts:
--------------------------------------------------------------------------------
1 | ///
2 |
3 | import { bootstrapApplication } from '@angular/platform-browser';
4 | import { appConfig } from './app/app.config';
5 | import { AppComponent } from './app/app.component';
6 |
7 | bootstrapApplication(AppComponent, appConfig).catch((err) =>
8 | console.error(err)
9 | );
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/server.ts:
--------------------------------------------------------------------------------
1 | import {
2 | AngularNodeAppEngine,
3 | createNodeRequestHandler,
4 | isMainModule,
5 | writeResponseToNodeResponse,
6 | } from '@angular/ssr/node';
7 | import express from 'express';
8 | import { dirname, resolve } from 'node:path';
9 | import { fileURLToPath } from 'node:url';
10 |
11 | const serverDistFolder = dirname(fileURLToPath(import.meta.url));
12 | const browserDistFolder = resolve(serverDistFolder, '../browser');
13 |
14 | const app = express();
15 | const angularApp = new AngularNodeAppEngine();
16 |
17 | /**
18 | * Example Express Rest API endpoints can be defined here.
19 | * Uncomment and define endpoints as necessary.
20 | *
21 | * Example:
22 | * ```ts
23 | * app.get('/api/**', (req, res) => {
24 | * // Handle API request
25 | * });
26 | * ```
27 | */
28 |
29 | /**
30 | * Serve static files from /browser
31 | */
32 | app.use(
33 | express.static(browserDistFolder, {
34 | maxAge: '1y',
35 | index: false,
36 | redirect: false,
37 | })
38 | );
39 |
40 | /**
41 | * Handle all other requests by rendering the Angular application.
42 | */
43 | app.use('/**', (req, res, next) => {
44 | angularApp
45 | .handle(req)
46 | .then((response) =>
47 | response ? writeResponseToNodeResponse(response, res) : next()
48 | )
49 | .catch(next);
50 | });
51 |
52 | /**
53 | * Start the server if this module is the main entry point.
54 | * The server listens on the port defined by the `PORT` environment variable, or defaults to 4000.
55 | */
56 | if (isMainModule(import.meta.url)) {
57 | const port = process.env['PORT'] || 4000;
58 | app.listen(port, () => {
59 | console.log(`Node Express server listening on http://localhost:${port}`);
60 | });
61 | }
62 |
63 | /**
64 | * The request handler used by the Angular CLI (dev-server and during build).
65 | */
66 | export const reqHandler = createNodeRequestHandler(app);
67 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/src/styles.css:
--------------------------------------------------------------------------------
1 | /* You can add global styles to this file, and also import other style files */
2 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/tests/app.spec.ts:
--------------------------------------------------------------------------------
1 | import { test, expect } from '@playwright/test';
2 |
3 | test('has title', async ({ page }) => {
4 | await page.goto('/');
5 | await expect(page).toHaveTitle('10');
6 | await expect(page.locator('h1')).toHaveText('production');
7 | });
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/tsconfig.app.json:
--------------------------------------------------------------------------------
1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */
2 | {
3 | "extends": "./tsconfig.json",
4 | "compilerOptions": {
5 | "outDir": "./out-tsc/app",
6 | "types": ["node", "@angular/localize"]
7 | },
8 | "files": ["src/main.ts", "src/main.server.ts", "src/server.ts"],
9 | "include": ["src/**/*.d.ts"]
10 | }
11 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/tsconfig.json:
--------------------------------------------------------------------------------
1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */
2 | {
3 | "compileOnSave": false,
4 | "compilerOptions": {
5 | "outDir": "./dist/out-tsc",
6 | "forceConsistentCasingInFileNames": true,
7 | "strict": true,
8 | "noImplicitOverride": true,
9 | "noPropertyAccessFromIndexSignature": true,
10 | "noImplicitReturns": true,
11 | "noFallthroughCasesInSwitch": true,
12 | "esModuleInterop": true,
13 | "sourceMap": true,
14 | "declaration": false,
15 | "downlevelIteration": true,
16 | "experimentalDecorators": true,
17 | "moduleResolution": "node",
18 | "importHelpers": true,
19 | "target": "ES2022",
20 | "module": "es2022",
21 | "useDefineForClassFields": false,
22 | "lib": ["ES2022", "dom"]
23 | },
24 | "angularCompilerOptions": {
25 | "enableI18nLegacyMessageIdFormat": false,
26 | "strictInjectionParameters": true,
27 | "strictInputAccessModifiers": true,
28 | "strictTemplates": true
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-cli/tsconfig.spec.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "./tsconfig.json",
3 | "compilerOptions": {
4 | "outDir": "./out-tsc/spec",
5 | "types": ["jasmine", "@angular/localize"],
6 | "esModuleInterop": true,
7 | "module": "es2022"
8 | },
9 | "include": ["src/**/*.spec.ts", "src/**/*.jest.ts", "src/**/*.d.ts"]
10 | }
11 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/.editorconfig:
--------------------------------------------------------------------------------
1 | # Editor configuration, see https://editorconfig.org
2 | root = true
3 |
4 | [*]
5 | charset = utf-8
6 | indent_style = space
7 | indent_size = 2
8 | insert_final_newline = true
9 | trim_trailing_whitespace = true
10 |
11 | [*.ts]
12 | quote_type = single
13 |
14 | [*.md]
15 | max_line_length = off
16 | trim_trailing_whitespace = false
17 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/.env.app:
--------------------------------------------------------------------------------
1 | USER_HOME=/home/chihab
2 | NGX_VERSION=ERROR_HERE_SINCE_SET_IN_ENV_LOCAL
3 | NGX_USER_HOME=$USER_HOME
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/.env.app.local:
--------------------------------------------------------------------------------
1 | NGX_VERSION=$npm_package_version
2 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/.gitignore:
--------------------------------------------------------------------------------
1 | # See http://help.github.com/ignore-files/ for more about ignoring files.
2 |
3 | # compiled output
4 | dist
5 | /tmp
6 | /out-tsc
7 | # Only exists if Bazel was run
8 | /bazel-out
9 |
10 | # dependencies
11 | node_modules
12 |
13 | # profiling files
14 | chrome-profiler-events*.json
15 |
16 | # IDEs and editors
17 | /.idea
18 | .project
19 | .classpath
20 | .c9/
21 | *.launch
22 | .settings/
23 | *.sublime-workspace
24 |
25 | # IDE - VSCode
26 | .vscode/*
27 | !.vscode/settings.json
28 | !.vscode/tasks.json
29 | !.vscode/launch.json
30 | !.vscode/extensions.json
31 | .history/*
32 |
33 | # misc
34 | /.angular/cache
35 | /.sass-cache
36 | /connect.lock
37 | /coverage
38 | /libpeerconnection.log
39 | npm-debug.log
40 | testem.log
41 | /typings
42 |
43 | # System Files
44 | .DS_Store
45 | Thumbs.db
46 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/README.md:
--------------------------------------------------------------------------------
1 | # NgxEnv
2 |
3 | This project was generated with [Angular CLI](https://github.com/angular/angular-cli) version 12.1.4.
4 |
5 | ## Development server
6 |
7 | Run `ng serve` for a dev server. Navigate to `http://localhost:4200/`. The app will automatically reload if you change any of the source files.
8 |
9 | ## Code scaffolding
10 |
11 | Run `ng generate component component-name` to generate a new component. You can also use `ng generate directive|pipe|service|class|guard|interface|enum|module`.
12 |
13 | ## Build
14 |
15 | Run `ng build` to build the project. The build artifacts will be stored in the `dist/` directory.
16 |
17 | ## Running unit tests
18 |
19 | Run `ng test` to execute the unit tests via [Karma](https://karma-runner.github.io).
20 |
21 | ## Running end-to-end tests
22 |
23 | Run `ng e2e` to execute the end-to-end tests via a platform of your choice. To use this command, you need to first add a package that implements end-to-end testing capabilities.
24 |
25 | ## Further help
26 |
27 | To get more help on the Angular CLI use `ng help` or go check out the [Angular CLI Overview and Command Reference](https://angular.io/cli) page.
28 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/package.ignore.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "ng-app",
3 | "version": "16.1.1",
4 | "private": true,
5 | "scripts": {
6 | "ng": "ng",
7 | "start": "cross-env NODE_ENV=dev ng serve",
8 | "prepare:build": "npx ng config projects.ng-app-webpack.architect.build.options.ngxEnv.prefix 'NGX_'",
9 | "build": "ng build",
10 | "e2e": "playwright test",
11 | "static": "npx serve dist/ng-app-webpack/browser"
12 | },
13 | "dependencies": {
14 | "@angular/common": "^18.2.7",
15 | "@angular/compiler": "^18.2.7",
16 | "@angular/core": "^18.2.7",
17 | "@angular/platform-browser": "^18.2.7",
18 | "@angular/platform-browser-dynamic": "^18.2.7",
19 | "rxjs": "~7.6.0",
20 | "tslib": "^2.7.0",
21 | "zone.js": "~0.14.10"
22 | },
23 | "devDependencies": {
24 | "@angular-builders/custom-webpack": "^18.0.0",
25 | "@angular-devkit/build-angular": "^18.2.7",
26 | "@angular/cli": "^18.2.7",
27 | "@angular/compiler-cli": "^18.2.7",
28 | "@dotenv-run/webpack": "workspace:^1.4.1",
29 | "@types/node": "^18.19.54",
30 | "cross-env": "^7.0.3",
31 | "typescript": "~5.4.5"
32 | }
33 | }
34 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/playwright.config.ts:
--------------------------------------------------------------------------------
1 | import { defineConfig, devices } from "@playwright/test";
2 |
3 | export default defineConfig({
4 | // Look for test files in the "tests" directory, relative to this configuration file.
5 | testDir: "tests",
6 |
7 | // Run all tests in parallel.
8 | fullyParallel: true,
9 |
10 | use: {
11 | // Base URL to use in actions like `await page.goto('/')`.
12 | baseURL: "http://127.0.0.1:8080",
13 |
14 | // Collect trace when retrying the failed test.
15 | trace: "on-first-retry",
16 | },
17 | // Configure projects for major browsers.
18 | projects: [
19 | {
20 | name: "chromium",
21 | use: { ...devices["Desktop Chrome"] },
22 | },
23 | ],
24 | // Run your local dev server before starting the tests.
25 | webServer: {
26 | command: "npm run static -- -p 8080",
27 | url: "http://127.0.0.1:8080"
28 | },
29 | });
30 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/project.ignore.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "ng-app-webpack"
3 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/app/app.component.html:
--------------------------------------------------------------------------------
1 | {{ env }} {{ version }}
2 | {{ api }}
3 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/app/app.component.ts:
--------------------------------------------------------------------------------
1 | import { Component } from '@angular/core';
2 | import { environment } from 'src/environments/environment';
3 |
4 | @Component({
5 | selector: 'app-root',
6 | templateUrl: './app.component.html',
7 | })
8 | export class AppComponent {
9 | env = process.env['NODE_ENV'];
10 | version = environment.env.NGX_VERSION;
11 | api = environment.env.API_USERS;
12 | }
13 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/app/app.module.ts:
--------------------------------------------------------------------------------
1 | import { NgModule } from '@angular/core';
2 | import { BrowserModule } from '@angular/platform-browser';
3 | import { AppComponent } from './app.component';
4 |
5 | @NgModule({
6 | declarations: [AppComponent],
7 | imports: [BrowserModule],
8 | bootstrap: [AppComponent],
9 | })
10 | export class AppModule {}
11 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/assets/.gitkeep:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-webpack/src/assets/.gitkeep
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/env.d.ts:
--------------------------------------------------------------------------------
1 | interface ImportMeta {
2 | env: ImportMetaEnv;
3 | }
4 |
5 | interface ImportMetaEnv {
6 | readonly NG_APP_ENV: string;
7 | readonly API_USERS: string;
8 | readonly NGX_VERSION: string;
9 | }
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/environments/environment.prod.ts:
--------------------------------------------------------------------------------
1 | export const environment = {
2 | production: true,
3 | env: {
4 | NGX_VERSION: import.meta.env['NGX_VERSION'],
5 | API_USERS: import.meta.env['API_USERS'],
6 | },
7 | };
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/environments/environment.ts:
--------------------------------------------------------------------------------
1 | // This file can be replaced during build by using the `fileReplacements` array.
2 | // `ng build` replaces `environment.ts` with `environment.prod.ts`.
3 | // The list of file replacements can be found in `angular.json`.
4 |
5 | export const environment = {
6 | production: false,
7 | env: {
8 | NGX_VERSION: import.meta.env['NGX_VERSION'],
9 | API_USERS: import.meta.env['API_USERS'],
10 | },
11 | };
12 |
13 | /*
14 | * For easier debugging in development mode, you can import the following file
15 | * to ignore zone related error stack frames such as `zone.run`, `zoneDelegate.invokeTask`.
16 | *
17 | * This import should be commented out in production mode because it will have a negative impact
18 | * on performance if an error is thrown.
19 | */
20 | // import 'zone.js/plugins/zone-error'; // Included with Angular CLI.
21 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace-old/apps/ng-app-webpack/src/favicon.ico
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 | %NGX_VERSION%
9 |
10 |
11 | %NODE_ENV%
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/main.ts:
--------------------------------------------------------------------------------
1 | import { enableProdMode } from '@angular/core';
2 | import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
3 |
4 | import { AppModule } from './app/app.module';
5 | import { environment } from './environments/environment';
6 |
7 | if (environment.production) {
8 | enableProdMode();
9 | }
10 |
11 | platformBrowserDynamic()
12 | .bootstrapModule(AppModule)
13 | .catch((err) => console.error(err));
14 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/styles.css:
--------------------------------------------------------------------------------
1 | /* You can add global styles to this file, and also import other style files */
2 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/src/test.ts:
--------------------------------------------------------------------------------
1 | // This file is required by karma.conf.js and loads recursively all the .spec and framework files
2 |
3 | import 'zone.js/testing';
4 | import { getTestBed } from '@angular/core/testing';
5 | import {
6 | BrowserDynamicTestingModule,
7 | platformBrowserDynamicTesting
8 | } from '@angular/platform-browser-dynamic/testing';
9 |
10 | // First, initialize the Angular testing environment.
11 | getTestBed().initTestEnvironment(
12 | BrowserDynamicTestingModule,
13 | platformBrowserDynamicTesting(), {
14 | teardown: { destroyAfterEach: false }
15 | }
16 | );
17 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/tsconfig.app.json:
--------------------------------------------------------------------------------
1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */
2 | {
3 | "extends": "./tsconfig.json",
4 | "compilerOptions": {
5 | "outDir": "./out-tsc/app"
6 | },
7 | "files": ["src/main.ts", "src/polyfills.ts"],
8 | "include": ["src/env.d.ts"]
9 | }
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/tsconfig.json:
--------------------------------------------------------------------------------
1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */
2 | {
3 | "compileOnSave": false,
4 | "compilerOptions": {
5 | "baseUrl": "./",
6 | "outDir": "./dist/out-tsc",
7 | "forceConsistentCasingInFileNames": true,
8 | "strict": true,
9 | "noImplicitReturns": true,
10 | "noFallthroughCasesInSwitch": true,
11 | "noPropertyAccessFromIndexSignature": true,
12 | "sourceMap": true,
13 | "declaration": false,
14 | "downlevelIteration": true,
15 | "experimentalDecorators": true,
16 | "moduleResolution": "node",
17 | "importHelpers": true,
18 | "target": "ES2022",
19 | "module": "es2020",
20 | "lib": [
21 | "es2018",
22 | "dom"
23 | ],
24 | "useDefineForClassFields": false
25 | },
26 | "angularCompilerOptions": {
27 | "enableI18nLegacyMessageIdFormat": false,
28 | "strictInjectionParameters": true,
29 | "strictInputAccessModifiers": true,
30 | "strictTemplates": true
31 | }
32 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/tsconfig.spec.json:
--------------------------------------------------------------------------------
1 | /* To learn more about this file see: https://angular.io/config/tsconfig. */
2 | {
3 | "extends": "./tsconfig.json",
4 | "compilerOptions": {
5 | "outDir": "./out-tsc/spec",
6 | "types": ["jasmine"]
7 | },
8 | "files": ["src/test.ts"],
9 | "include": ["src/**/*.spec.ts", "src/**/*.d.ts"]
10 | }
11 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/ng-app-webpack/webpack.config.ts:
--------------------------------------------------------------------------------
1 | import { DotenvRunPlugin } from '@dotenv-run/webpack';
2 | import type { Configuration } from 'webpack';
3 |
4 | export default (config: Configuration) => {
5 | config.plugins?.push(
6 | new DotenvRunPlugin({
7 | root: '../..',
8 | cwd: process.cwd(),
9 | prefix: /^API|NGX/,
10 | verbose: true,
11 | files: ['.env.app'],
12 | nodeEnv: false,
13 | })
14 | );
15 | return config;
16 | };
17 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/__snapshots__/rspack-dev.test.ts.snap:
--------------------------------------------------------------------------------
1 | // Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
2 |
3 | exports[`dotenv-run should give the expected output > dev 1`] = `
4 | "https://dotenv-run.dev/api/v1/users
5 | development
6 | "
7 | `;
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/__snapshots__/rspack-prod.test.ts.snap:
--------------------------------------------------------------------------------
1 | // Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
2 |
3 | exports[`dotenv-run should give the expected output > prod 1`] = `
4 | "https://dotenv-run.app/api/v1/users
5 | production
6 | "
7 | `;
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "rspack-app",
3 | "version": "1.0.0",
4 | "private": true,
5 | "scripts": {
6 | "build": "concurrently npm:build:*",
7 | "build:prod": "NODE_ENV=prod rspack build --mode production --output-path dist/prod",
8 | "build:dev": "NODE_ENV=dev rspack build --mode development --output-path dist/dev",
9 | "test": "concurrently npm:test:*",
10 | "test:dev": "vitest ./rspack-dev.test.ts",
11 | "test:prod": "vitest ./rspack-prod.test.ts"
12 | }
13 | }
14 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/project.json:
--------------------------------------------------------------------------------
1 | {}
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/rspack-dev.test.ts:
--------------------------------------------------------------------------------
1 | import { execSync } from "child_process";
2 | import { describe, it, expect } from "vitest";
3 |
4 | describe("dotenv-run should give the expected output", () => {
5 | it("dev", () => {
6 | const actual = execSync("node dist/dev/main.js", {
7 | encoding: "utf8",
8 | });
9 | expect(actual).toMatchSnapshot();
10 | });
11 | });
12 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/rspack-prod.test.ts:
--------------------------------------------------------------------------------
1 | import { execSync } from "child_process";
2 | import { describe, it, expect } from "vitest";
3 |
4 | describe("dotenv-run should give the expected output", () => {
5 | it("prod", () => {
6 | const actual = execSync("node dist/prod/main.js", {
7 | encoding: "utf8",
8 | });
9 | expect(actual).toMatchSnapshot();
10 | });
11 | });
12 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/rspack.config.mjs:
--------------------------------------------------------------------------------
1 | import { DotenvRunPlugin } from "@dotenv-run/rspack";
2 | import path from "path";
3 |
4 | const __dirname = path.resolve();
5 |
6 | export default {
7 | plugins: [
8 | new DotenvRunPlugin(
9 | {
10 | environment: process.env.NODE_ENV,
11 | prefix: "^API",
12 | cwd: process.cwd(),
13 | verbose: true,
14 | root: "../..",
15 | files: [".env.app"],
16 | nodeEnv: false,
17 | dotenv: { override: true },
18 | },
19 | __dirname
20 | ),
21 | ],
22 | entry: "./src/index.js",
23 | output: {
24 | filename: "main.js",
25 | path: path.resolve(__dirname, "dist"),
26 | },
27 | };
28 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/rspack-app/src/index.js:
--------------------------------------------------------------------------------
1 | console.log(process.env.API_USERS)
2 | console.log(process.env.NODE_ENV)
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/__snapshots__/webpack-dev.test.ts.snap:
--------------------------------------------------------------------------------
1 | // Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
2 |
3 | exports[`dotenv-run should give the expected output > dev 1`] = `
4 | "https://dotenv-run.dev/api/v1/users
5 | development
6 | "
7 | `;
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/__snapshots__/webpack-prod.test.ts.snap:
--------------------------------------------------------------------------------
1 | // Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
2 |
3 | exports[`dotenv-run should give the expected output > prod 1`] = `
4 | "https://dotenv-run.app/api/v1/users
5 | production
6 | "
7 | `;
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "webpack-app",
3 | "version": "1.0.0",
4 | "private": true,
5 | "scripts": {
6 | "build": "concurrently npm:build:*",
7 | "build:prod": "NODE_ENV=prod webpack build --mode production --output-path dist/prod",
8 | "build:dev": "NODE_ENV=dev webpack build --mode development --output-path dist/dev",
9 | "test": "concurrently npm:test:*",
10 | "test:dev": "vitest ./webpack-dev.test.ts",
11 | "test:prod": "vitest ./webpack-prod.test.ts"
12 | }
13 | }
14 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/project.json:
--------------------------------------------------------------------------------
1 | {}
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/src/index.js:
--------------------------------------------------------------------------------
1 | console.log(process.env.API_USERS)
2 | console.log(process.env.NODE_ENV)
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/webpack-dev.test.ts:
--------------------------------------------------------------------------------
1 | import { execSync } from "child_process";
2 | import { describe, it, expect } from "vitest";
3 |
4 | describe("dotenv-run should give the expected output", () => {
5 | it("dev", () => {
6 | const actual = execSync("node dist/dev/main.js", {
7 | encoding: "utf8",
8 | });
9 | expect(actual).toMatchSnapshot();
10 | });
11 | });
12 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/webpack-prod.test.ts:
--------------------------------------------------------------------------------
1 | import { execSync } from "child_process";
2 | import { describe, it, expect } from "vitest";
3 |
4 | describe("dotenv-run should give the expected output", () => {
5 | it("prod", () => {
6 | const actual = execSync("node dist/prod/main.js", {
7 | encoding: "utf8",
8 | });
9 | expect(actual).toMatchSnapshot();
10 | });
11 | });
12 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/apps/webpack-app/webpack.config.mjs:
--------------------------------------------------------------------------------
1 | import { DotenvRunPlugin } from "@dotenv-run/webpack";
2 | import path from "path";
3 |
4 | const __dirname = path.resolve();
5 |
6 | export default {
7 | plugins: [
8 | new DotenvRunPlugin(
9 | {
10 | environment: process.env.NODE_ENV,
11 | prefix: "^API",
12 | cwd: process.cwd(),
13 | verbose: true,
14 | root: "../..",
15 | files: [".env.app"],
16 | nodeEnv: false,
17 | dotenv: { override: true },
18 | },
19 | __dirname
20 | ),
21 | ],
22 | entry: "./src/index.js",
23 | output: {
24 | filename: "main.js",
25 | path: path.resolve(__dirname, "dist"),
26 | },
27 | };
28 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/libs/rollup-lib/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "rollup-lib",
3 | "version": "1.0.0",
4 | "private": true,
5 | "scripts": {
6 | "build": "NODE_ENV=dev rollup -c rollup.config.mjs",
7 | "test": "vitest"
8 | }
9 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/libs/rollup-lib/project.json:
--------------------------------------------------------------------------------
1 | {}
--------------------------------------------------------------------------------
/examples/nx-workspace-old/libs/rollup-lib/rollup.config.mjs:
--------------------------------------------------------------------------------
1 | import env from "@dotenv-run/rollup";
2 |
3 | export default {
4 | input: "src/index.mjs",
5 | output: {
6 | file: "dist/index.js",
7 | },
8 | plugins: [
9 | env({
10 | prefix: "^API",
11 | verbose: true,
12 | root: "../../..",
13 | files: [".env.app"],
14 | environment: process.env.NODE_ENV,
15 | cwd: process.cwd(),
16 | }),
17 | ],
18 | };
19 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/libs/rollup-lib/src/index.mjs:
--------------------------------------------------------------------------------
1 | export function getApiUrl() {
2 | return process.env.API_USERS;
3 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/libs/rollup-lib/src/index.test.js:
--------------------------------------------------------------------------------
1 | import { it, expect } from "vitest";
2 | import { getApiUrl } from "../dist/index.js";
3 |
4 | it("dotenv-run should give the expected output", () => {
5 | expect(getApiUrl()).toBe("https://dotenv-run.dev/api/v1/users");
6 | });
7 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/nx.json:
--------------------------------------------------------------------------------
1 | {
2 | "tasksRunnerOptions": {
3 | "default": {
4 | "runner": "nx/tasks-runners/default",
5 | "options": {
6 | "cacheableOperations": [
7 | "build"
8 | ]
9 | }
10 | }
11 | },
12 | "targetDefaults": {
13 | "test": {
14 | "inputs": [
15 | "^test"
16 | ]
17 | }
18 | },
19 | "affected": {
20 | "defaultBase": "main"
21 | }
22 | }
--------------------------------------------------------------------------------
/examples/nx-workspace-old/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "platform",
3 | "private": true,
4 | "version": "2.0.0",
5 | "scripts": {
6 | "build:all": "nx run-many --target=build --all --parallel",
7 | "test:all": "nx run-many --target=test,test:jest --all --parallel --verbose",
8 | "e2e:all": "nx run-many --target=e2e --all --parallel"
9 | },
10 | "devDependencies": {
11 | "@dotenv-run/cli": "workspace:^1.3.6",
12 | "@dotenv-run/load": "workspace:^1.3.6",
13 | "@dotenv-run/rollup": "workspace:^1.3.6",
14 | "@dotenv-run/webpack": "workspace:^1.5.0",
15 | "@dotenv-run/rspack": "workspace:^1.0.0",
16 | "@nx/js": "^18.3.5",
17 | "@playwright/test": "^1.47.2",
18 | "@types/node": "^20.16.10",
19 | "nx": "^16.10.0",
20 | "playwright": "^1.47.2",
21 | "rollup": "^3.29.5",
22 | "serve": "^14.2.3",
23 | "verdaccio": "^5.32.2",
24 | "webpack": "5.96.1",
25 | "webpack-cli": "^5.1.4",
26 | "@rspack/cli": "^1.0.10",
27 | "@rspack/core": "^1.0.10"
28 | },
29 | "nx": {
30 | "includedScripts": []
31 | }
32 | }
33 |
--------------------------------------------------------------------------------
/examples/nx-workspace-old/project.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "platform",
3 | "$schema": "node_modules/nx/schemas/project-schema.json",
4 | "targets": {
5 | "local-registry": {
6 | "executor": "@nx/js:verdaccio",
7 | "options": {
8 | "port": 4873,
9 | "config": ".verdaccio/config.yml",
10 | "storage": "tmp/local-registry/storage"
11 | }
12 | }
13 | }
14 | }
15 |
--------------------------------------------------------------------------------
/examples/nx-workspace/.editorconfig:
--------------------------------------------------------------------------------
1 | # Editor configuration, see http://editorconfig.org
2 | root = true
3 |
4 | [*]
5 | charset = utf-8
6 | indent_style = space
7 | indent_size = 2
8 | insert_final_newline = true
9 | trim_trailing_whitespace = true
10 |
11 | [*.md]
12 | max_line_length = off
13 | trim_trailing_whitespace = false
14 |
--------------------------------------------------------------------------------
/examples/nx-workspace/.github/workflows/ci.yml:
--------------------------------------------------------------------------------
1 | name: CI
2 |
3 | on:
4 | push:
5 | branches:
6 | - main
7 | pull_request:
8 |
9 | permissions:
10 | actions: read
11 | contents: read
12 |
13 | jobs:
14 | main:
15 | runs-on: ubuntu-latest
16 | steps:
17 | - uses: actions/checkout@v4
18 | with:
19 | fetch-depth: 0
20 |
21 | # This enables task distribution via Nx Cloud
22 | # Run this command as early as possible, before dependencies are installed
23 | # Learn more at https://nx.dev/ci/reference/nx-cloud-cli#npx-nxcloud-startcirun
24 | # Uncomment this line to enable task distribution
25 | # - run: npx nx-cloud start-ci-run --distribute-on="3 linux-medium-js" --stop-agents-after="e2e-ci"
26 |
27 | # Cache node_modules
28 | - uses: actions/setup-node@v4
29 | with:
30 | node-version: 20
31 | cache: 'npm'
32 |
33 | - run: npm ci --legacy-peer-deps
34 | - run: npx playwright install --with-deps
35 | - uses: nrwl/nx-set-shas@v4
36 |
37 | # Prepend any command with "nx-cloud record --" to record its logs to Nx Cloud
38 | # - run: npx nx-cloud record -- echo Hello World
39 | # Nx Affected runs only tasks affected by the changes in this PR/commit. Learn more: https://nx.dev/ci/features/affected
40 | # When you enable task distribution, run the e2e-ci task instead of e2e
41 | - run: npx nx affected -t lint test build e2e
42 |
--------------------------------------------------------------------------------
/examples/nx-workspace/.gitignore:
--------------------------------------------------------------------------------
1 | # See http://help.github.com/ignore-files/ for more about ignoring files.
2 |
3 | # compiled output
4 | dist
5 | tmp
6 | /out-tsc
7 |
8 | # dependencies
9 | node_modules
10 |
11 | # IDEs and editors
12 | /.idea
13 | .project
14 | .classpath
15 | .c9/
16 | *.launch
17 | .settings/
18 | *.sublime-workspace
19 |
20 | # IDE - VSCode
21 | .vscode/*
22 | !.vscode/settings.json
23 | !.vscode/tasks.json
24 | !.vscode/launch.json
25 | !.vscode/extensions.json
26 |
27 | # misc
28 | /.sass-cache
29 | /connect.lock
30 | /coverage
31 | /libpeerconnection.log
32 | npm-debug.log
33 | yarn-error.log
34 | testem.log
35 | /typings
36 |
37 | # System Files
38 | .DS_Store
39 | Thumbs.db
40 |
41 | .nx/cache
42 | .nx/workspace-data
43 |
44 | .angular
45 |
--------------------------------------------------------------------------------
/examples/nx-workspace/.prettierignore:
--------------------------------------------------------------------------------
1 | # Add files here to ignore them from prettier formatting
2 | /dist
3 | /coverage
4 | /.nx/cache
5 | /.nx/workspace-data
6 | .angular
7 |
--------------------------------------------------------------------------------
/examples/nx-workspace/.prettierrc:
--------------------------------------------------------------------------------
1 | {
2 | "singleQuote": true
3 | }
4 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli-e2e/eslint.config.js:
--------------------------------------------------------------------------------
1 | const playwright = require('eslint-plugin-playwright');
2 | const baseConfig = require('../../eslint.config.js');
3 |
4 | module.exports = [
5 | playwright.configs['flat/recommended'],
6 |
7 | ...baseConfig,
8 | {
9 | files: ['**/*.ts', '**/*.js'],
10 | // Override or add rules here
11 | rules: {},
12 | },
13 | ];
14 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli-e2e/playwright.config.ts:
--------------------------------------------------------------------------------
1 | import { defineConfig, devices } from '@playwright/test';
2 | import { nxE2EPreset } from '@nx/playwright/preset';
3 |
4 | import { workspaceRoot } from '@nx/devkit';
5 |
6 | // For CI, you may want to set BASE_URL to the deployed application.
7 | const baseURL = process.env['BASE_URL'] || 'http://localhost:4200';
8 |
9 | /**
10 | * Read environment variables from file.
11 | * https://github.com/motdotla/dotenv
12 | */
13 | // require('dotenv').config();
14 |
15 | /**
16 | * See https://playwright.dev/docs/test-configuration.
17 | */
18 | export default defineConfig({
19 | ...nxE2EPreset(__filename, { testDir: './src' }),
20 | /* Shared settings for all the projects below. See https://playwright.dev/docs/api/class-testoptions. */
21 | use: {
22 | baseURL,
23 | /* Collect trace when retrying the failed test. See https://playwright.dev/docs/trace-viewer */
24 | trace: 'on-first-retry',
25 | },
26 | /* Run your local dev server before starting the tests */
27 | webServer: {
28 | command: 'npx nx run ng-app-cli:serve',
29 | url: 'http://localhost:4200',
30 | reuseExistingServer: !process.env.CI,
31 | cwd: workspaceRoot,
32 | },
33 | projects: [
34 | {
35 | name: 'chromium',
36 | use: { ...devices['Desktop Chrome'] },
37 | },
38 |
39 | {
40 | name: 'firefox',
41 | use: { ...devices['Desktop Firefox'] },
42 | },
43 |
44 | {
45 | name: 'webkit',
46 | use: { ...devices['Desktop Safari'] },
47 | },
48 |
49 | // Uncomment for mobile browsers support
50 | /* {
51 | name: 'Mobile Chrome',
52 | use: { ...devices['Pixel 5'] },
53 | },
54 | {
55 | name: 'Mobile Safari',
56 | use: { ...devices['iPhone 12'] },
57 | }, */
58 |
59 | // Uncomment for branded browsers
60 | /* {
61 | name: 'Microsoft Edge',
62 | use: { ...devices['Desktop Edge'], channel: 'msedge' },
63 | },
64 | {
65 | name: 'Google Chrome',
66 | use: { ...devices['Desktop Chrome'], channel: 'chrome' },
67 | } */
68 | ],
69 | });
70 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli-e2e/project.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "ng-app-cli-e2e",
3 | "$schema": "../../node_modules/nx/schemas/project-schema.json",
4 | "projectType": "application",
5 | "sourceRoot": "apps/ng-app-cli-e2e/src",
6 | "implicitDependencies": ["ng-app-cli"],
7 | "// targets": "to see all targets run: nx show project ng-app-cli-e2e --web",
8 | "targets": {}
9 | }
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli-e2e/src/example.spec.ts:
--------------------------------------------------------------------------------
1 | import { test, expect } from '@playwright/test';
2 |
3 | test('has title', async ({ page }) => {
4 | await page.goto('/');
5 |
6 | // Expect h1 to contain a substring.
7 | expect(await page.locator('h1').innerText()).toContain('Welcome');
8 | });
9 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli-e2e/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "../../tsconfig.base.json",
3 | "compilerOptions": {
4 | "allowJs": true,
5 | "outDir": "../../dist/out-tsc",
6 | "sourceMap": false,
7 | "module": "commonjs",
8 | "forceConsistentCasingInFileNames": true,
9 | "strict": true,
10 | "noImplicitOverride": true,
11 | "noPropertyAccessFromIndexSignature": true,
12 | "noImplicitReturns": true,
13 | "noFallthroughCasesInSwitch": true
14 | },
15 | "include": [
16 | "**/*.ts",
17 | "**/*.js",
18 | "playwright.config.ts",
19 | "src/**/*.spec.ts",
20 | "src/**/*.spec.js",
21 | "src/**/*.test.ts",
22 | "src/**/*.test.js",
23 | "src/**/*.d.ts"
24 | ]
25 | }
26 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/eslint.config.js:
--------------------------------------------------------------------------------
1 | const nx = require('@nx/eslint-plugin');
2 | const baseConfig = require('../../eslint.config.js');
3 |
4 | module.exports = [
5 | ...baseConfig,
6 | ...nx.configs['flat/angular'],
7 | ...nx.configs['flat/angular-template'],
8 | {
9 | files: ['**/*.ts'],
10 | rules: {
11 | '@angular-eslint/directive-selector': [
12 | 'error',
13 | {
14 | type: 'attribute',
15 | prefix: 'app',
16 | style: 'camelCase',
17 | },
18 | ],
19 | '@angular-eslint/component-selector': [
20 | 'error',
21 | {
22 | type: 'element',
23 | prefix: 'app',
24 | style: 'kebab-case',
25 | },
26 | ],
27 | },
28 | },
29 | {
30 | files: ['**/*.html'],
31 | // Override or add rules here
32 | rules: {},
33 | },
34 | ];
35 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/jest.config.ts:
--------------------------------------------------------------------------------
1 | export default {
2 | preset: 'jest-preset-angular/presets/defaults-esm',
3 | setupFilesAfterEnv: ['/src/test-setup.ts'],
4 | cache: false,
5 | testMatch: ['/src/app/**/*.(spec|jest).ts'],
6 | moduleNameMapper: {
7 | '^rxjs(/operators$)?$':
8 | '/../../node_modules/rxjs/dist/bundles/rxjs.umd.js',
9 | tslib: '/../../node_modules/tslib/tslib.es6.mjs',
10 | },
11 | transform: {
12 | '^.+\\.(ts)$': [
13 | '@dotenv-run/jest-angular',
14 | {
15 | useESM: true,
16 | stringifyContentPathRegex: '\\.(html|svg)$',
17 | },
18 | ],
19 | },
20 | };
21 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "ng-app-cli",
3 | "private": true,
4 | "scripts": {
5 | "test:esm": "node --experimental-vm-modules ../../node_modules/jest/bin/jest.js"
6 | }
7 | }
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/public/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace/apps/ng-app-cli/public/favicon.ico
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/server.ts:
--------------------------------------------------------------------------------
1 | import { APP_BASE_HREF } from '@angular/common';
2 | import { CommonEngine } from '@angular/ssr';
3 | import express from 'express';
4 | import { fileURLToPath } from 'node:url';
5 | import { dirname, join, resolve } from 'node:path';
6 | import bootstrap from './src/main.server';
7 |
8 | // The Express app is exported so that it can be used by serverless Functions.
9 | export function app(): express.Express {
10 | const server = express();
11 | const serverDistFolder = dirname(fileURLToPath(import.meta.url));
12 | const browserDistFolder = resolve(serverDistFolder, '../browser');
13 | const indexHtml = join(serverDistFolder, 'index.server.html');
14 |
15 | const commonEngine = new CommonEngine();
16 |
17 | server.set('view engine', 'html');
18 | server.set('views', browserDistFolder);
19 |
20 | // Example Express Rest API endpoints
21 | // server.get('/api/**', (req, res) => { });
22 | // Serve static files from /browser
23 | server.get(
24 | '**',
25 | express.static(browserDistFolder, {
26 | maxAge: '1y',
27 | index: 'index.html',
28 | })
29 | );
30 |
31 | // All regular routes use the Angular engine
32 | server.get('**', (req, res, next) => {
33 | const { protocol, originalUrl, baseUrl, headers } = req;
34 |
35 | commonEngine
36 | .render({
37 | bootstrap,
38 | documentFilePath: indexHtml,
39 | url: `${protocol}://${headers.host}${originalUrl}`,
40 | publicPath: browserDistFolder,
41 | providers: [{ provide: APP_BASE_HREF, useValue: baseUrl }],
42 | })
43 | .then((html) => res.send(html))
44 | .catch((err) => next(err));
45 | });
46 |
47 | return server;
48 | }
49 |
50 | function run(): void {
51 | const port = process.env['PORT'] || 4000;
52 |
53 | // Start up the Node server
54 | const server = app();
55 | server.listen(port, () => {
56 | console.log(`Node Express server listening on http://localhost:${port}`);
57 | });
58 | }
59 |
60 | run();
61 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/app/app.component.css:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/examples/nx-workspace/apps/ng-app-cli/src/app/app.component.css
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/app/app.component.html:
--------------------------------------------------------------------------------
1 | {{ title }}
2 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/app/app.component.spec.ts:
--------------------------------------------------------------------------------
1 | import { TestBed } from '@angular/core/testing';
2 | import { AppComponent } from './app.component';
3 | import { RouterModule } from '@angular/router';
4 |
5 | const title = 'test';
6 |
7 | describe('AppComponent', () => {
8 | beforeEach(async () => {
9 | await TestBed.configureTestingModule({
10 | imports: [AppComponent, RouterModule.forRoot([])],
11 | }).compileComponents();
12 | });
13 |
14 | it('should render title', () => {
15 | const fixture = TestBed.createComponent(AppComponent);
16 | fixture.detectChanges();
17 | const compiled = fixture.nativeElement as HTMLElement;
18 | expect(compiled.querySelector('h1')?.textContent).toContain(title);
19 | });
20 |
21 | it(`should have as title 'ng-app-cli'`, () => {
22 | const fixture = TestBed.createComponent(AppComponent);
23 | const app = fixture.componentInstance;
24 | expect(app.title).toEqual(title);
25 | });
26 | });
27 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/app/app.component.ts:
--------------------------------------------------------------------------------
1 | import { Component } from '@angular/core';
2 |
3 | @Component({
4 | standalone: true,
5 | selector: 'app-root',
6 | templateUrl: './app.component.html',
7 | })
8 | export class AppComponent {
9 | title = 'Title: ' + import.meta.env.NODE_ENV;
10 | }
11 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/app/app.config.server.ts:
--------------------------------------------------------------------------------
1 | import { mergeApplicationConfig, ApplicationConfig } from '@angular/core';
2 | import { provideServerRendering } from '@angular/platform-server';
3 | import { appConfig } from './app.config';
4 |
5 | const serverConfig: ApplicationConfig = {
6 | providers: [provideServerRendering()],
7 | };
8 |
9 | export const config = mergeApplicationConfig(appConfig, serverConfig);
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/app/app.config.ts:
--------------------------------------------------------------------------------
1 | import { ApplicationConfig, provideZoneChangeDetection } from '@angular/core';
2 | import { provideRouter } from '@angular/router';
3 | import { appRoutes } from './app.routes';
4 | import { provideClientHydration } from '@angular/platform-browser';
5 |
6 | export const appConfig: ApplicationConfig = {
7 | providers: [
8 | provideClientHydration(),
9 | provideZoneChangeDetection({ eventCoalescing: true }),
10 | provideRouter(appRoutes),
11 | ],
12 | };
13 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/app/app.routes.ts:
--------------------------------------------------------------------------------
1 | import { Route } from '@angular/router';
2 |
3 | export const appRoutes: Route[] = [];
4 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/env.d.ts:
--------------------------------------------------------------------------------
1 | // Define the type of the environment variables.
2 | declare interface Env {
3 | readonly NODE_ENV: string;
4 | // Replace the following with your own environment variables.
5 | // Example: NGX_VERSION: string;
6 | [key: string]: any;
7 | }
8 |
9 | // Choose how to access the environment variables.
10 | // Remove the unused options.
11 |
12 | // 1. Use import.meta.env.YOUR_ENV_VAR in your code. (conventional)
13 | declare interface ImportMeta {
14 | readonly env: Env;
15 | }
16 |
17 | // 2. Use _NGX_ENV_.YOUR_ENV_VAR in your code. (customizable)
18 | // You can modify the name of the variable in angular.json.
19 | // ngxEnv: {
20 | // define: '_NGX_ENV_',
21 | // }
22 | declare const _NGX_ENV_: Env;
23 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | ng-app-cli
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/main.server.ts:
--------------------------------------------------------------------------------
1 | import '@ngx-env/builder/runtime';
2 |
3 | import { bootstrapApplication } from '@angular/platform-browser';
4 | import { AppComponent } from './app/app.component';
5 | import { config } from './app/app.config.server';
6 |
7 | const bootstrap = () => bootstrapApplication(AppComponent, config);
8 |
9 | export default bootstrap;
10 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/main.ts:
--------------------------------------------------------------------------------
1 | import { bootstrapApplication } from '@angular/platform-browser';
2 | import { appConfig } from './app/app.config';
3 | import { AppComponent } from './app/app.component';
4 |
5 | bootstrapApplication(AppComponent, appConfig).catch((err) =>
6 | console.error(err)
7 | );
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/styles.css:
--------------------------------------------------------------------------------
1 | /* You can add global styles to this file, and also import other style files */
2 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/src/test-setup.ts:
--------------------------------------------------------------------------------
1 | import 'jest-preset-angular/setup-jest.mjs';
2 |
3 | // import { setupZoneTestEnv } from 'jest-preset-angular/setup-env/zone/index.mjs';
4 | // setupZoneTestEnv();
5 |
6 | import { env } from '@dotenv-run/core';
7 | env({ root: '../../..', files: ['.env', '.env.app'] });
8 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/tsconfig.app.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "./tsconfig.json",
3 | "compilerOptions": {
4 | "outDir": "../../dist/out-tsc",
5 | "types": ["node"]
6 | },
7 | "files": ["src/main.ts", "src/main.server.ts", "server.ts"],
8 | "include": ["src/**/*.d.ts"],
9 | "exclude": ["jest.config.ts", "src/**/*.test.ts", "src/**/*.spec.ts"]
10 | }
11 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/tsconfig.editor.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "./tsconfig.json",
3 | "include": ["src/**/*.ts"],
4 | "compilerOptions": {},
5 | "exclude": ["jest.config.ts", "src/**/*.test.ts", "src/**/*.spec.ts"]
6 | }
7 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compilerOptions": {
3 | "target": "es2022",
4 | "esModuleInterop": true,
5 | "forceConsistentCasingInFileNames": true,
6 | "strict": true,
7 | "noImplicitOverride": true,
8 | "noPropertyAccessFromIndexSignature": true,
9 | "noImplicitReturns": true,
10 | "noFallthroughCasesInSwitch": true
11 | },
12 | "files": [],
13 | "include": [],
14 | "references": [
15 | {
16 | "path": "./tsconfig.editor.json"
17 | },
18 | {
19 | "path": "./tsconfig.app.json"
20 | },
21 | {
22 | "path": "./tsconfig.spec.json"
23 | }
24 | ],
25 | "extends": "../../tsconfig.base.json",
26 | "angularCompilerOptions": {
27 | "enableI18nLegacyMessageIdFormat": false,
28 | "strictInjectionParameters": true,
29 | "strictInputAccessModifiers": true,
30 | "strictTemplates": true
31 | }
32 | }
33 |
--------------------------------------------------------------------------------
/examples/nx-workspace/apps/ng-app-cli/tsconfig.spec.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "./tsconfig.json",
3 | "compilerOptions": {
4 | "outDir": "../../dist/out-tsc",
5 | "types": ["jest"],
6 | "esModuleInterop": true,
7 | "module": "es2022"
8 | },
9 | "files": ["src/test-setup.ts"],
10 | "include": [
11 | "jest.config.ts",
12 | "src/**/*.test.ts",
13 | "src/**/*.spec.ts",
14 | "src/**/*.d.ts"
15 | ]
16 | }
17 |
--------------------------------------------------------------------------------
/examples/nx-workspace/eslint.config.js:
--------------------------------------------------------------------------------
1 | const nx = require('@nx/eslint-plugin');
2 |
3 | module.exports = [
4 | ...nx.configs['flat/base'],
5 | ...nx.configs['flat/typescript'],
6 | ...nx.configs['flat/javascript'],
7 | {
8 | ignores: ['**/dist'],
9 | },
10 | {
11 | files: ['**/*.ts', '**/*.tsx', '**/*.js', '**/*.jsx'],
12 | rules: {
13 | '@nx/enforce-module-boundaries': [
14 | 'error',
15 | {
16 | enforceBuildableLibDependency: true,
17 | allow: ['^.*/eslint(\\.base)?\\.config\\.[cm]?js$'],
18 | depConstraints: [
19 | {
20 | sourceTag: '*',
21 | onlyDependOnLibsWithTags: ['*'],
22 | },
23 | ],
24 | },
25 | ],
26 | },
27 | },
28 | {
29 | files: ['**/*.ts', '**/*.tsx', '**/*.js', '**/*.jsx'],
30 | // Override or add rules here
31 | rules: {},
32 | },
33 | ];
34 |
--------------------------------------------------------------------------------
/examples/nx-workspace/jest.config.ts:
--------------------------------------------------------------------------------
1 | import { getJestProjectsAsync } from '@nx/jest';
2 |
3 | export default async () => ({
4 | projects: await getJestProjectsAsync(),
5 | });
6 |
--------------------------------------------------------------------------------
/examples/nx-workspace/jest.preset.js:
--------------------------------------------------------------------------------
1 | const nxPreset = require('@nx/jest/preset').default;
2 |
3 | module.exports = { ...nxPreset };
4 |
--------------------------------------------------------------------------------
/examples/nx-workspace/nx.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "./node_modules/nx/schemas/nx-schema.json",
3 | "namedInputs": {
4 | "default": ["{projectRoot}/**/*", "sharedGlobals"],
5 | "production": [
6 | "default",
7 | "!{projectRoot}/.eslintrc.json",
8 | "!{projectRoot}/eslint.config.js",
9 | "!{projectRoot}/**/?(*.)+(spec|test).[jt]s?(x)?(.snap)",
10 | "!{projectRoot}/tsconfig.spec.json",
11 | "!{projectRoot}/jest.config.[jt]s",
12 | "!{projectRoot}/src/test-setup.[jt]s",
13 | "!{projectRoot}/test-setup.[jt]s"
14 | ],
15 | "sharedGlobals": ["{workspaceRoot}/.github/workflows/ci.yml"]
16 | },
17 | "targetDefaults": {
18 | "@angular-devkit/build-angular:application": {
19 | "cache": true,
20 | "dependsOn": ["^build"],
21 | "inputs": ["production", "^production"]
22 | },
23 | "@nx/eslint:lint": {
24 | "cache": true,
25 | "inputs": [
26 | "default",
27 | "{workspaceRoot}/.eslintrc.json",
28 | "{workspaceRoot}/.eslintignore",
29 | "{workspaceRoot}/eslint.config.js"
30 | ]
31 | },
32 | "@nx/jest:jest": {
33 | "cache": true,
34 | "inputs": ["default", "^production", "{workspaceRoot}/jest.preset.js"],
35 | "options": {
36 | "passWithNoTests": true
37 | },
38 | "configurations": {
39 | "ci": {
40 | "ci": true,
41 | "codeCoverage": true
42 | }
43 | }
44 | },
45 | "e2e-ci--**/*": {
46 | "dependsOn": ["^build"]
47 | }
48 | },
49 | "plugins": [
50 | {
51 | "plugin": "@nx/playwright/plugin",
52 | "options": {
53 | "targetName": "e2e"
54 | }
55 | },
56 | {
57 | "plugin": "@nx/eslint/plugin",
58 | "options": {
59 | "targetName": "lint"
60 | }
61 | }
62 | ],
63 | "generators": {
64 | "@nx/angular:application": {
65 | "e2eTestRunner": "playwright",
66 | "linter": "eslint",
67 | "style": "css",
68 | "unitTestRunner": "jest"
69 | }
70 | }
71 | }
72 |
--------------------------------------------------------------------------------
/examples/nx-workspace/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@nx-workspace/source",
3 | "version": "0.0.0",
4 | "license": "MIT",
5 | "scripts": {
6 | "test": "NODE_ENV=test nx run-many -t test:esm",
7 | "build": "NODE_ENV=dev nx run-many -t build"
8 | },
9 | "private": true,
10 | "dependencies": {
11 | "@angular/animations": "~18.2.0",
12 | "@angular/common": "~18.2.0",
13 | "@angular/compiler": "~18.2.0",
14 | "@angular/core": "~18.2.0",
15 | "@angular/forms": "~18.2.0",
16 | "@angular/platform-browser": "~18.2.0",
17 | "@angular/platform-browser-dynamic": "~18.2.0",
18 | "@angular/platform-server": "~18.2.0",
19 | "@angular/router": "~18.2.0",
20 | "@angular/ssr": "~18.2.0",
21 | "express": "~4.18.2",
22 | "rxjs": "~7.8.0",
23 | "zone.js": "~0.14.3"
24 | },
25 | "devDependencies": {
26 | "@angular-devkit/build-angular": "~18.2.0",
27 | "@angular-devkit/core": "~18.2.0",
28 | "@angular-devkit/schematics": "~18.2.0",
29 | "@angular/cli": "~18.2.0",
30 | "@angular/compiler-cli": "~18.2.0",
31 | "@angular/language-service": "~18.2.0",
32 | "@dotenv-run/jest-angular": "^0.1.1",
33 | "@eslint/js": "^9.8.0",
34 | "@ngx-env/builder": "^18.0.2",
35 | "@nx/angular": "20.1.1",
36 | "@nx/devkit": "20.1.1",
37 | "@nx/eslint": "20.1.1",
38 | "@nx/eslint-plugin": "20.1.1",
39 | "@nx/jest": "^20.1.1",
40 | "@nx/js": "20.1.1",
41 | "@nx/playwright": "20.1.1",
42 | "@nx/web": "20.1.1",
43 | "@nx/workspace": "20.1.1",
44 | "@playwright/test": "^1.36.0",
45 | "@schematics/angular": "~18.2.0",
46 | "@swc-node/register": "~1.9.1",
47 | "@swc/core": "~1.5.7",
48 | "@swc/helpers": "~0.5.11",
49 | "@types/express": "4.17.14",
50 | "@types/jest": "^29.5.12",
51 | "@types/node": "18.16.9",
52 | "@typescript-eslint/utils": "^8.0.0",
53 | "angular-eslint": "^18.3.0",
54 | "eslint": "^9.8.0",
55 | "eslint-config-prettier": "^9.0.0",
56 | "eslint-plugin-playwright": "^1.6.2",
57 | "jest": "^29.7.0",
58 | "jest-environment-jsdom": "^29.7.0",
59 | "jest-preset-angular": "~14.1.0",
60 | "nx": "20.1.1",
61 | "prettier": "^2.6.2",
62 | "ts-jest": "^29.1.0",
63 | "ts-node": "10.9.1",
64 | "tslib": "^2.3.0",
65 | "typescript": "~5.5.2",
66 | "typescript-eslint": "^8.0.0"
67 | }
68 | }
69 |
--------------------------------------------------------------------------------
/examples/nx-workspace/tsconfig.base.json:
--------------------------------------------------------------------------------
1 | {
2 | "compileOnSave": false,
3 | "compilerOptions": {
4 | "rootDir": ".",
5 | "sourceMap": true,
6 | "declaration": false,
7 | "moduleResolution": "node",
8 | "emitDecoratorMetadata": true,
9 | "experimentalDecorators": true,
10 | "importHelpers": true,
11 | "target": "es2015",
12 | "module": "esnext",
13 | "lib": ["es2020", "dom"],
14 | "skipLibCheck": true,
15 | "skipDefaultLibCheck": true,
16 | "baseUrl": ".",
17 | "paths": {}
18 | },
19 | "exclude": ["node_modules", "tmp"]
20 | }
21 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "dotenv-run",
3 | "version": "0.0.0",
4 | "private": true,
5 | "scripts": {
6 | "dev": "turbo run dev --parallel --no-cache --filter=./packages/*",
7 | "test": "CI=1 turbo test --filter=./packages/*",
8 | "build": "turbo build --filter=./packages/*",
9 | "build:docs": "turbo build --filter=./docs",
10 | "prepare": "husky install",
11 | "docker:build": "docker build -t temp-build . && docker rmi --force temp-build"
12 | },
13 | "license": "MIT",
14 | "devDependencies": {
15 | "@changesets/cli": "^2.27.9",
16 | "concurrently": "^8.2.2",
17 | "husky": "^8.0.3",
18 | "turbo": "^1.13.4",
19 | "typescript": "~5.6.2",
20 | "vitest": "^0.33.0"
21 | },
22 | "packageManager": "pnpm@10.6.2"
23 | }
24 |
--------------------------------------------------------------------------------
/packages/.env:
--------------------------------------------------------------------------------
1 | API_USERS=$API_BASE/api/v1/users
2 | API_AUTH=$API_BASE/api/v1/auth
--------------------------------------------------------------------------------
/packages/angular/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @ngx-env/builder
2 |
3 | ## 19.0.4
4 |
5 | ### Patch Changes
6 |
7 | - doc: remove karma non support
8 |
9 | ## 19.0.3
10 |
11 | ### Patch Changes
12 |
13 | - add support to karma browser builder after cli fix
14 |
15 | ## 19.0.2
16 |
17 | ### Patch Changes
18 |
19 | - dfb69c0: fix: csr angular 19 support
20 |
21 | ## 19.0.0
22 |
23 | ### Major Changes
24 |
25 | - 8f83f0c: feat: add compatibility with Angular 19
26 |
27 | ### Patch Changes
28 |
29 | - Updated dependencies [8f83f0c]
30 | - @dotenv-run/webpack@1.5.0
31 |
--------------------------------------------------------------------------------
/packages/angular/builders.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "./node_modules/@angular-devkit/architect/src/builders-schema.json",
3 | "builders": {
4 | "browser": {
5 | "implementation": "./dist/builders/browser",
6 | "schema": "./dist/builders/schemas/browser.json",
7 | "description": "Build browser app extended with ngx-env config"
8 | },
9 | "dev-server": {
10 | "implementation": "./dist/builders/dev-server",
11 | "schema": "./dist/builders/schemas/dev-server.json",
12 | "description": "Dev server extended with ngx-env config"
13 | },
14 | "karma": {
15 | "implementation": "./dist/builders/karma",
16 | "schema": "./dist/builders/schemas/karma.json",
17 | "description": "Karma server extended with ngx-env config"
18 | },
19 | "extract-i18n": {
20 | "implementation": "./dist/builders/extract-i18n",
21 | "schema": "./dist/builders/schemas/extract-i18n.json",
22 | "description": "Extract i18n extended with ngx-env config"
23 | },
24 | "server": {
25 | "implementation": "./dist/builders/server",
26 | "schema": "./dist/builders/schemas/server.json",
27 | "description": "Build server app extended with ngx-env config"
28 | },
29 | "application": {
30 | "implementation": "./dist/builders/application",
31 | "schema": "./dist/builders/schemas/application.json",
32 | "description": "Build application extended with ngx-env config"
33 | },
34 | "browser-esbuild": {
35 | "implementation": "./dist/builders/browser-esbuild",
36 | "schema": "./dist/builders/schemas/browser-esbuild.json",
37 | "description": "Build browser app extended with ngx-env config using esbuild"
38 | }
39 | }
40 | }
41 |
--------------------------------------------------------------------------------
/packages/angular/collection.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "./node_modules/@angular-devkit/schematics/collection-schema.json",
3 | "schematics": {
4 | "ng-add": {
5 | "description": "Add ngx-env to your Angular Application",
6 | "factory": "./dist/schematics/ng-add/index",
7 | "schema": "./dist/schematics/ng-add/schema.json",
8 | "aliases": ["install"]
9 | }
10 | }
11 | }
12 |
--------------------------------------------------------------------------------
/packages/angular/logo.svg:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/packages/angular/manekinekko.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/packages/angular/manekinekko.png
--------------------------------------------------------------------------------
/packages/angular/motdotla.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/chihab/dotenv-run/5f2442a008acfbfd1108d43fbc4e78c985e64531/packages/angular/motdotla.png
--------------------------------------------------------------------------------
/packages/angular/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@ngx-env/builder",
3 | "version": "19.0.4",
4 | "description": "Easily inject environment variables into your Angular applications",
5 | "author": "chihab ",
6 | "homepage": "https://github.com/chihab/ngx-env/tree/main/packages/angular",
7 | "license": "MIT",
8 | "keywords": [
9 | "angular",
10 | "dotenv",
11 | "environment",
12 | "builder",
13 | "schematics"
14 | ],
15 | "files": [
16 | "dist",
17 | "builders.json",
18 | "collection.json",
19 | "README.md",
20 | "runtime.mjs"
21 | ],
22 | "builders": "builders.json",
23 | "schematics": "./collection.json",
24 | "ng-add": {
25 | "save": "devDependencies"
26 | },
27 | "scripts": {
28 | "dev": "tsc -w",
29 | "build": "tsc && ts-node tools/schema-copy-run.ts",
30 | "copy-dist": "ts-node tools/schema-dist.ts"
31 | },
32 | "dependencies": {
33 | "@dotenv-run/webpack": "workspace:^1.5.0",
34 | "glob": "^10.4.5"
35 | },
36 | "devDependencies": {
37 | "@angular/build": "^19.0.4",
38 | "@angular-devkit/architect": "^0.1900.4",
39 | "@angular-devkit/build-angular": "^19.0.4",
40 | "@angular-devkit/core": "^19.0.4",
41 | "@angular-devkit/schematics": "^19.0.4",
42 | "@angular/router": "^19.0.4",
43 | "@angular/animations": "^19.0.4",
44 | "@angular/common": "^19.0.4",
45 | "@angular/platform-browser": "^19.0.4",
46 | "@dotenv-run/core": "workspace:^1.3.6",
47 | "cpy": "^8.1.2",
48 | "karma": "^6.4.4",
49 | "rxjs": "^7.8.1",
50 | "ts-node": "^10.9.2",
51 | "typescript": "~5.6.2",
52 | "webpack": "5.96.1",
53 | "zone.js": "~0.15.0"
54 | },
55 | "peerDpendencies": {
56 | "rxjs": "^7.0.0",
57 | "webpack": "5.96.1"
58 | }
59 | }
60 |
--------------------------------------------------------------------------------
/packages/angular/runtime.mjs:
--------------------------------------------------------------------------------
1 | globalThis._NGX_ENV_ = process.env;
2 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/application/index.ts:
--------------------------------------------------------------------------------
1 | import {
2 | BuilderContext,
3 | BuilderOutput,
4 | createBuilder,
5 | fromAsyncIterable,
6 | } from "@angular-devkit/architect";
7 | import {
8 | ApplicationBuilderOptions,
9 | buildApplication,
10 | } from "@angular-devkit/build-angular";
11 | import { env, type DotenvRunOptions } from "@dotenv-run/core";
12 | import { join } from "path";
13 | import { Observable, from, switchMap, tap } from "rxjs";
14 | import { NgxEnvSchema } from "../ngx-env/ngx-env-schema";
15 | import { indexHtml } from "../utils/index-html-build";
16 | import { getEnvironment } from "../utils/get-environment";
17 | import { getProjectCwd } from "../utils/project";
18 |
19 | export const buildWithPlugin = (
20 | options: ApplicationBuilderOptions & NgxEnvSchema,
21 | context: BuilderContext
22 | ): Observable => {
23 | const dotEnvOptions: DotenvRunOptions = options.ngxEnv;
24 | return from(getProjectCwd(context)).pipe(
25 | switchMap((cwd) => {
26 | const { full, raw } = env({
27 | ...dotEnvOptions,
28 | cwd,
29 | global: "_NGX_ENV_",
30 | environment: getEnvironment(context.target.configuration),
31 | });
32 | options.define = full;
33 | return fromAsyncIterable(
34 | buildApplication(options, context)
35 | ).pipe(
36 | tap(() => {
37 | const outputDir = join(
38 | context.workspaceRoot,
39 | options.outputPath.toString()
40 | );
41 | indexHtml(
42 | join(outputDir, "browser"),
43 | options.ssr ? join(outputDir, "server") : null,
44 | Array.isArray(options.localize) ? options.localize : [],
45 | raw,
46 | dotEnvOptions.runtime
47 | );
48 | })
49 | );
50 | })
51 | );
52 | };
53 |
54 | export default createBuilder(buildWithPlugin);
55 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/browser-esbuild/index.ts:
--------------------------------------------------------------------------------
1 | import {
2 | BuilderContext,
3 | createBuilder,
4 | fromAsyncIterable,
5 | } from "@angular-devkit/architect";
6 | import { buildEsbuildBrowser } from "@angular-devkit/build-angular/src/builders/browser-esbuild";
7 | import { Schema as BrowserBuilderOptions } from "@angular-devkit/build-angular/src/builders/browser-esbuild/schema";
8 | import { env, type DotenvRunOptions } from "@dotenv-run/core";
9 | import { join } from "path";
10 | import { from, switchMap, tap } from "rxjs";
11 | import { NgxEnvSchema } from "../ngx-env/ngx-env-schema";
12 | import { indexHtml } from "../utils/index-html-build";
13 | import { getEnvironment } from "../utils/get-environment";
14 | import { getProjectCwd } from "../utils/project";
15 |
16 | export const buildWithPlugin = (
17 | options: BrowserBuilderOptions & NgxEnvSchema,
18 | context: BuilderContext
19 | ) => {
20 | const dotEnvOptions: DotenvRunOptions = options.ngxEnv;
21 | return from(getProjectCwd(context)).pipe(
22 | switchMap((cwd) => {
23 | const { full, raw } = env({
24 | ...dotEnvOptions,
25 | cwd,
26 | global: "_NGX_ENV_",
27 | environment: getEnvironment(context.target.configuration),
28 | });
29 | (options as any).define = full;
30 | return fromAsyncIterable(
31 | buildEsbuildBrowser(options, context, undefined)
32 | ).pipe(
33 | tap(() => {
34 | indexHtml(
35 | join(
36 | context.workspaceRoot,
37 | options.outputPath.toString(),
38 | "browser"
39 | ),
40 | null, // no ssr support with browser-esbuild,
41 | Array.isArray(options.localize) ? options.localize : [],
42 | raw,
43 | dotEnvOptions.runtime
44 | );
45 | })
46 | );
47 | })
48 | );
49 | };
50 |
51 | export default createBuilder(buildWithPlugin);
52 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/browser/index.ts:
--------------------------------------------------------------------------------
1 | import { BuilderContext, createBuilder } from "@angular-devkit/architect";
2 | import {
3 | BrowserBuilderOptions,
4 | executeBrowserBuilder,
5 | } from "@angular-devkit/build-angular";
6 | import { from, switchMap, tap } from "rxjs";
7 | import { NgxEnvSchema } from "../ngx-env/ngx-env-schema";
8 | import { getEnvironment } from "../utils/get-environment";
9 | import { getProjectCwd } from "../utils/project";
10 | import { plugin } from "../utils/webpack-plugin";
11 | import { indexHtml } from "../utils/index-html-build";
12 | import { join } from "path";
13 |
14 | export const buildWithPlugin = (
15 | options: BrowserBuilderOptions & NgxEnvSchema,
16 | context: BuilderContext
17 | ): ReturnType => {
18 | return from(getProjectCwd(context)).pipe(
19 | switchMap((cwd: string) => {
20 | const { raw, webpackConfiguration } = plugin({
21 | ...options.ngxEnv,
22 | cwd,
23 | environment: getEnvironment(context.target.configuration),
24 | });
25 | return executeBrowserBuilder(options, context, {
26 | webpackConfiguration,
27 | }).pipe(
28 | tap(() => {
29 | indexHtml(
30 | join(context.workspaceRoot, options.outputPath.toString()),
31 | null, // no ssr support with browser,
32 | Array.isArray(options.localize) ? options.localize : [],
33 | raw,
34 | options.ngxEnv.runtime
35 | );
36 | })
37 | );
38 | })
39 | );
40 | };
41 |
42 | export default createBuilder(buildWithPlugin);
43 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/extract-i18n/extract-i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "http://json-schema.org/draft-07/schema",
3 | "title": "Extract i18n Target",
4 | "description": "Extract i18n target options for Build Facade.",
5 | "type": "object",
6 | "properties": {
7 | "buildTarget": {
8 | "type": "string",
9 | "description": "A builder target to extract i18n messages in the format of `project:target[:configuration]`. You can also pass in more than one configuration name as a comma-separated list. Example: `project:target:production,staging`.",
10 | "pattern": "^[^:\\s]*:[^:\\s]*(:[^\\s]+)?$"
11 | },
12 | "format": {
13 | "type": "string",
14 | "description": "Output format for the generated file.",
15 | "default": "xlf",
16 | "enum": ["xmb", "xlf", "xlif", "xliff", "xlf2", "xliff2", "json", "arb", "legacy-migrate"]
17 | },
18 | "progress": {
19 | "type": "boolean",
20 | "description": "Log progress to the console.",
21 | "default": true
22 | },
23 | "outputPath": {
24 | "type": "string",
25 | "description": "Path where output will be placed."
26 | },
27 | "outFile": {
28 | "type": "string",
29 | "description": "Name of the file to output."
30 | }
31 | },
32 | "additionalProperties": false
33 | }
34 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/extract-i18n/index.ts:
--------------------------------------------------------------------------------
1 | import {
2 | BuilderContext,
3 | createBuilder,
4 | targetFromTargetString,
5 | } from "@angular-devkit/architect";
6 | import {
7 | ExtractI18nBuilderOptions,
8 | executeExtractI18nBuilder,
9 | } from "@angular-devkit/build-angular";
10 | import { combineLatest, switchMap } from "rxjs";
11 | import { NgxEnvSchema } from "../ngx-env/ngx-env-schema";
12 | import { JsonObject } from "@angular-devkit/core";
13 |
14 | export const buildWithPlugin = (
15 | options: ExtractI18nBuilderOptions & NgxEnvSchema,
16 | context: BuilderContext
17 | ) => {
18 | const buildTarget = targetFromTargetString(options.buildTarget);
19 | // options.buildTarget = "@angular-devkit/build-angular:application";
20 | async function setup() {
21 | const targetOptions = await context.getTargetOptions(buildTarget);
22 | if ((await builderName()) === "@ngx-env/builder:application") {
23 | // Because of ngxEnv being removed from the options, we need to validate it here
24 | await context.validateOptions(
25 | targetOptions,
26 | "@ngx-env/builder:application"
27 | );
28 | }
29 | return targetOptions;
30 | }
31 | async function builderName() {
32 | return context.getBuilderNameForTarget(buildTarget);
33 | }
34 | return combineLatest([setup(), builderName()]).pipe(
35 | switchMap(([_options, builderName]) => {
36 | if (builderName === "@ngx-env/builder:browser") {
37 | return executeExtractI18nBuilder(options, context);
38 | } else {
39 | delete _options.ngxEnv;
40 | context.getTargetOptions = async () => _options as JsonObject;
41 | return executeExtractI18nBuilder(options, {
42 | ...context,
43 | getBuilderNameForTarget: async () =>
44 | "@angular-devkit/build-angular:" + builderName.split(":")[1],
45 | });
46 | }
47 | })
48 | );
49 | };
50 |
51 | export default createBuilder(buildWithPlugin);
52 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/karma/index.ts:
--------------------------------------------------------------------------------
1 | import { BuilderContext, createBuilder } from "@angular-devkit/architect";
2 | import {
3 | executeKarmaBuilder,
4 | KarmaBuilderOptions,
5 | } from "@angular-devkit/build-angular";
6 | import { NgxEnvSchema } from "../ngx-env/ngx-env-schema";
7 | // import { plugin } from "../utils/webpack-plugin";
8 | import { from, of, switchMap, throwError } from "rxjs";
9 | import { getProjectCwd } from "../utils/project";
10 | import { env } from "@dotenv-run/core";
11 | import { getEnvironment } from "../utils/get-environment";
12 | import { plugin } from "../utils/webpack-plugin";
13 | import { BuilderMode } from "@angular-devkit/build-angular/src/builders/karma/schema";
14 | // import { getEnvironment } from "../utils/get-environment";
15 | // import { env } from "@dotenv-run/core";
16 |
17 | export const buildWithPlugin = (
18 | options: KarmaBuilderOptions & NgxEnvSchema,
19 | context: BuilderContext
20 | ): ReturnType => {
21 | return from(getProjectCwd(context)).pipe(
22 | switchMap((cwd: string) => {
23 | const { full } = env({
24 | ...options.ngxEnv,
25 | cwd,
26 | environment: getEnvironment(context.target.configuration),
27 | });
28 | switch (options.builderMode) {
29 | case "application":
30 | case "detect":
31 | console.warn("@ngx-env/builder:");
32 | console.warn(
33 | " Application builder is not supported yet due to a limitation in the Angular CLI. "
34 | );
35 | console.warn(" Falling back to the Browser builder.");
36 | // (options as any).define = full;
37 | // Does not work with application builder yet see: https://github.com/chihab/dotenv-run/issues/113 and https://github.com/angular/angular-cli/issues/29003
38 | return executeKarmaBuilder(
39 | {
40 | ...options,
41 | builderMode: BuilderMode.Browser,
42 | },
43 | context,
44 | plugin(full)
45 | );
46 | case "browser":
47 | return executeKarmaBuilder(options, context, plugin(full));
48 | default:
49 | return throwError(() => "@ngx-env/builder: Invalid builder mode");
50 | }
51 | })
52 | );
53 | };
54 | export default createBuilder(buildWithPlugin);
55 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/ngx-env/ngx-env-schema.ts:
--------------------------------------------------------------------------------
1 | import { DotenvRunOptions } from "@dotenv-run/core";
2 |
3 | export interface NgxEnvSchema {
4 | ngxEnv?: DotenvRunOptions;
5 | }
6 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/ngx-env/ngx-env.json:
--------------------------------------------------------------------------------
1 | {
2 | "ngxEnv": {
3 | "type": "object",
4 | "properties": {
5 | "prefix": {
6 | "type": "string",
7 | "description": "Regexp prefix of the environment variables to be replaced",
8 | "default": "NG_APP"
9 | },
10 | "verbose": {
11 | "type": "boolean",
12 | "description": "Display environment files and variables in the console",
13 | "default": true
14 | },
15 | "runtime": {
16 | "type": "boolean",
17 | "description": "Load environment variables at runtime",
18 | "default": false
19 | },
20 | "define": {
21 | "type": "string",
22 | "description": "Global identifier to access environment variables",
23 | "default": "_NGX_ENV_"
24 | },
25 | "unsecure": {
26 | "type": "boolean",
27 | "description": "Display environment variables values in the console",
28 | "default": false
29 | },
30 | "root": {
31 | "type": "string",
32 | "description": "Root directory of the project to find .env files"
33 | },
34 | "files": {
35 | "type": "array",
36 | "description": "List of .env files to be loaded",
37 | "default": [".env"],
38 | "items": {
39 | "type": "string"
40 | }
41 | }
42 | },
43 | "additionalProperties": false
44 | }
45 | }
46 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/server/index.ts:
--------------------------------------------------------------------------------
1 | import { createBuilder, type BuilderContext } from "@angular-devkit/architect";
2 | import {
3 | ServerBuilderOptions,
4 | executeServerBuilder,
5 | } from "@angular-devkit/build-angular";
6 | import { from, switchMap } from "rxjs";
7 | import { type NgxEnvSchema } from "../ngx-env/ngx-env-schema";
8 | import { getEnvironment } from "../utils/get-environment";
9 | import { getProjectCwd } from "../utils/project";
10 | import { plugin } from "../utils/webpack-plugin";
11 |
12 | export const buildWithPlugin = (
13 | options: ServerBuilderOptions & NgxEnvSchema,
14 | context: BuilderContext
15 | ): ReturnType => {
16 | return from(getProjectCwd(context)).pipe(
17 | switchMap((cwd: string) => {
18 | return executeServerBuilder(
19 | options,
20 | context,
21 | plugin(
22 | {
23 | ...options.ngxEnv,
24 | cwd,
25 | environment: getEnvironment(context.target.configuration),
26 | },
27 | true
28 | )
29 | );
30 | })
31 | );
32 | };
33 |
34 | export default createBuilder(buildWithPlugin);
35 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/escape-string-regexp.ts:
--------------------------------------------------------------------------------
1 | export function escapeStringRegexp(str: string) {
2 | return str.replace(/[|\\{}()[\]^$+*?.]/g, "\\$&").replace(/-/g, "\\x2d");
3 | }
4 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/get-environment.ts:
--------------------------------------------------------------------------------
1 | export function getEnvironment(configuration: string) {
2 | return (
3 | process.env.NG_APP_ENV || // @deprecated
4 | process.env.NODE_ENV || // default in @dotenv-run/core
5 | configuration // default in @angular-devkit/build-angular
6 | );
7 | }
8 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/index-html-build.ts:
--------------------------------------------------------------------------------
1 | import { type Dict } from "@dotenv-run/core";
2 | import { readFileSync, writeFileSync } from "fs";
3 | import * as glob from "glob";
4 | import { variablesReducer } from "./variables-reducer";
5 |
6 | export function indexHtml(
7 | browserOutputDir: string,
8 | serverOutputDir: string | null,
9 | locales: string[] = [],
10 | raw: Dict,
11 | runtime = false
12 | ) {
13 | try {
14 | glob.sync(`${browserOutputDir}/**/index{.html,.csr.html}`).forEach((filePath) => {
15 | const html = readFileSync(filePath, "utf-8");
16 | const content = variablesReducer(html, raw); // Replace %VARIABLE% with the actual value
17 | try {
18 | writeFileSync(
19 | filePath,
20 | runtime
21 | ? content.replace(
22 | //,
23 | ``
24 | )
25 | : content
26 | );
27 | } catch (e) {
28 | console.log(`❌ Failed to replace variables in ${filePath} ❌`);
29 | throw e;
30 | }
31 | });
32 | if (serverOutputDir) {
33 | glob
34 | .sync(`${serverOutputDir}/**/index.server.html`)
35 | .forEach((filePath) => {
36 | const html = readFileSync(filePath, "utf-8");
37 | const content = variablesReducer(html, raw); // Replace %VARIABLE% with the actual value
38 | try {
39 | writeFileSync(filePath, content);
40 | } catch (e) {
41 | console.log(`❌ Failed to replace variables in ${filePath} ❌`);
42 | throw e;
43 | }
44 | });
45 | }
46 | if (runtime) {
47 | const runtimeStmt = `globalThis._NGX_ENV_ = ${JSON.stringify(
48 | raw,
49 | null,
50 | 2
51 | )};`;
52 | if (locales.length > 0) {
53 | locales.forEach((locale) => {
54 | console.log(
55 | `📦 Writing ngx-env.js to ${browserOutputDir}/${locale}/ngx-env.js`
56 | );
57 | writeFileSync(
58 | `${browserOutputDir}/${locale}/ngx-env.js`,
59 | runtimeStmt
60 | );
61 | });
62 | } else {
63 | console.log(`📦 Writing ngx-env.js to ${browserOutputDir}/ngx-env.js`);
64 | writeFileSync(`${browserOutputDir}/ngx-env.js`, runtimeStmt);
65 | }
66 | }
67 | } catch (e) {
68 | console.error(e);
69 | }
70 | }
71 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/index-html-serve.ts:
--------------------------------------------------------------------------------
1 | import type { Dict } from "@dotenv-run/core";
2 | import { variablesReducer } from "./variables-reducer";
3 |
4 | export function indexHtml(content: string, raw: Dict, runtime = false) {
5 | const html = variablesReducer(content, raw);
6 | return runtime
7 | ? html.replace(
8 | //,
9 | ``
10 | )
11 | : html;
12 | }
13 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/project.ts:
--------------------------------------------------------------------------------
1 | import { BuilderContext } from "@angular-devkit/architect";
2 | import * as path from "path";
3 |
4 | export async function getProjectCwd(context: BuilderContext) {
5 | const metadata = (await context.getProjectMetadata(
6 | context.target.project
7 | )) as { root: string };
8 | return path.resolve(context.workspaceRoot, metadata.root);
9 | }
10 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/variables-reducer.ts:
--------------------------------------------------------------------------------
1 | import { Dict } from "@dotenv-run/core";
2 | import { escapeStringRegexp } from "./escape-string-regexp";
3 |
4 | export const variablesReducer = (content: string, raw: Dict) => {
5 | return Object.keys(raw).reduce(
6 | (html, key) =>
7 | html.replace(
8 | new RegExp("%" + escapeStringRegexp(key) + "%", "g"),
9 | raw[key]
10 | ),
11 | content
12 | );
13 | };
14 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/webpack-plugin.ts:
--------------------------------------------------------------------------------
1 | import type { DotenvRunOptions } from "@dotenv-run/core";
2 | import { DotenvRunPlugin } from "@dotenv-run/webpack";
3 | import type { Configuration } from "webpack";
4 | import { indexHtml } from "./index-html-serve";
5 |
6 | export function plugin(options: DotenvRunOptions, ssr = false) {
7 | const dotEnvPlugin = new DotenvRunPlugin(
8 | { ...options, environment: process.env.NODE_ENV, nodeEnv: false },
9 | ssr
10 | );
11 | const raw = dotEnvPlugin.raw;
12 | return {
13 | raw,
14 | webpackConfiguration: (webpackConfig: Configuration) => {
15 | webpackConfig.plugins.push(dotEnvPlugin);
16 | return webpackConfig;
17 | },
18 | indexHtml: async (content: string) => {
19 | return indexHtml(content, raw, options.runtime);
20 | },
21 | };
22 | }
23 |
--------------------------------------------------------------------------------
/packages/angular/src/builders/utils/workspace.ts:
--------------------------------------------------------------------------------
1 | import { SchematicsException, Tree } from '@angular-devkit/schematics';
2 |
3 | export interface WorkspaceProject {
4 | projectType?: string;
5 | architect?: Record<
6 | string,
7 | { builder: string; options?: Record }
8 | >;
9 | }
10 |
11 | export interface Workspace {
12 | defaultProject?: string;
13 | projects: Record;
14 | }
15 |
16 | export function getWorkspace(host: Tree): {
17 | path: string;
18 | workspace: Workspace;
19 | } {
20 | const possibleFiles = ['/angular.json', './angular.json'];
21 | const path = possibleFiles.find((path) => host.exists(path));
22 | const configBuffer = path ? host.read(path) : undefined;
23 |
24 | if (!path || !configBuffer) {
25 | throw new SchematicsException(`Could not find angular.json`);
26 | }
27 |
28 | const content = configBuffer.toString();
29 | let workspace: Workspace;
30 | try {
31 | workspace = JSON.parse(content);
32 | } catch (e: any) {
33 | throw new SchematicsException(
34 | `Could not parse angular.json: ${e?.message}`
35 | );
36 | }
37 |
38 | return { path, workspace };
39 | }
40 |
--------------------------------------------------------------------------------
/packages/angular/src/schematics/ng-add/schema.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "http://json-schema.org/schema",
3 | "$id": "ngx-env-ng-add",
4 | "title": "ngx-env schematic",
5 | "type": "object",
6 | "properties": {
7 | "project": {
8 | "type": "string",
9 | "description": "The name of the project.",
10 | "$default": {
11 | "$source": "projectName"
12 | }
13 | }
14 | },
15 | "required": ["project"]
16 | }
17 |
--------------------------------------------------------------------------------
/packages/angular/src/schematics/ng-add/template/env.d.ts:
--------------------------------------------------------------------------------
1 | // Define the type of the environment variables.
2 | declare interface Env {
3 | readonly NODE_ENV: string;
4 | // Replace the following with your own environment variables.
5 | // Example: NGX_VERSION: string;
6 | [key: string]: any;
7 | }
8 |
9 | // Choose how to access the environment variables.
10 | // Remove the unused options.
11 |
12 | // 1. Use import.meta.env.YOUR_ENV_VAR in your code. (conventional)
13 | declare interface ImportMeta {
14 | readonly env: Env;
15 | }
16 |
17 | // 2. Use _NGX_ENV_.YOUR_ENV_VAR in your code. (customizable)
18 | // You can modify the name of the variable in angular.json.
19 | // ngxEnv: {
20 | // define: '_NGX_ENV_',
21 | // }
22 | declare const _NGX_ENV_: Env;
23 |
24 | // 3. Use process.env.YOUR_ENV_VAR in your code. (deprecated)
25 | declare namespace NodeJS {
26 | export interface ProcessEnv extends Env {}
27 | }
28 |
--------------------------------------------------------------------------------
/packages/angular/tools/cli-targets.ts:
--------------------------------------------------------------------------------
1 | export const cliTargets = [
2 | "application",
3 | "browser-esbuild",
4 | "browser",
5 | "dev-server",
6 | "extract-i18n",
7 | "karma",
8 | "server",
9 | ];
10 |
--------------------------------------------------------------------------------
/packages/angular/tools/schema-copy-run.ts:
--------------------------------------------------------------------------------
1 | import copySchematicsSchema from './schema-copy';
2 | import copyBuildersSchemas from './schema-generate';
3 |
4 | (async () => {
5 | await copySchematicsSchema();
6 | await copyBuildersSchemas();
7 | })();
8 |
--------------------------------------------------------------------------------
/packages/angular/tools/schema-copy.ts:
--------------------------------------------------------------------------------
1 | import * as cpy from "cpy";
2 |
3 | async function copySchema(name: string) {
4 | await cpy([`src/schematics/${name}/schema.json`], `dist/schematics/${name}`);
5 | await cpy(
6 | [`src/schematics/${name}/template`],
7 | `dist/schematics/${name}/template`
8 | );
9 | }
10 |
11 | export default async function () {
12 | await copySchema("ng-add");
13 | }
14 |
--------------------------------------------------------------------------------
/packages/angular/tools/schema-dist.ts:
--------------------------------------------------------------------------------
1 | import * as cpy from "cpy";
2 | import * as fs from "fs";
3 | import { cliTargets } from "./cli-targets";
4 |
5 | async function copyDistSchemas() {
6 | console.log("Copying Angular CLI target schemas");
7 | // All but the application target
8 | cliTargets
9 | .filter((target) => target != "application")
10 | .forEach(async (target) => {
11 | await cpy(
12 | [
13 | `./node_modules/@angular-devkit/build-angular/src/builders/${target}/schema.json`,
14 | ],
15 | `src/builders/${target}`
16 | );
17 | console.log(
18 | `./node_modules/@angular-devkit/build-angular/src/builders/${target}/schema.json ==> src/builders/${target} ✅`
19 | );
20 | fs.renameSync(
21 | `src/builders/${target}/schema.json`,
22 | `src/builders/${target}/${target}.json`
23 | );
24 | });
25 | // Application target
26 | await cpy(
27 | [`./node_modules/@angular/build/src/builders/application/schema.json`],
28 | `src/builders/application`
29 | );
30 | console.log(
31 | `./node_modules/@angular/build/src/builders/application/schema.json ==> src/builders/application ✅`
32 | );
33 | fs.renameSync(
34 | `src/builders/application/schema.json`,
35 | `src/builders/application/application.json`
36 | );
37 | }
38 | (async () => {
39 | await copyDistSchemas();
40 | })();
41 |
--------------------------------------------------------------------------------
/packages/angular/tools/schema-generate.ts:
--------------------------------------------------------------------------------
1 | import * as cpy from "cpy";
2 | import * as fs from "fs";
3 | import { cliTargets } from "./cli-targets";
4 |
5 | export default async function () {
6 | console.log("Adding @ngx-env/builder schema");
7 | const ngxEnvConf = JSON.parse(
8 | fs.readFileSync(`src/builders/ngx-env/ngx-env.json`, "utf-8")
9 | );
10 | await cpy(["src/builders/**/*.json"], "dist/builders/schemas");
11 | cliTargets.forEach(async (target) => {
12 | const builderConf = JSON.parse(
13 | fs.readFileSync(`src/builders/${target}/${target}.json`, "utf-8")
14 | );
15 | builderConf.properties = { ...builderConf.properties, ...ngxEnvConf };
16 | await fs.writeFileSync(
17 | `dist/builders/schemas/${target}.json`,
18 | JSON.stringify(builderConf, null, 4)
19 | );
20 | console.log(
21 | `src/builders/${target}/${target}.json ==> dist/builders/schemas/${target}.json ✅`
22 | );
23 | });
24 | }
25 |
--------------------------------------------------------------------------------
/packages/angular/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "module": "commonjs",
7 | "target": "es6",
8 | "lib": ["dom", "es2015", "es2016", "es2017"],
9 | "strict": true,
10 | "allowSyntheticDefaultImports": true,
11 | "forceConsistentCasingInFileNames": true,
12 | "strictPropertyInitialization": false,
13 | "strictNullChecks": false,
14 | "pretty": true,
15 | "sourceMap": false,
16 | "declaration": true,
17 | "stripInternal": true,
18 | "skipLibCheck": true
19 | },
20 | "exclude": ["node_modules"],
21 | "compileOnSave": false,
22 | "buildOnSave": false
23 | }
24 |
--------------------------------------------------------------------------------
/packages/cli/.env.dev:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.dev
--------------------------------------------------------------------------------
/packages/cli/.env.prod:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.app
--------------------------------------------------------------------------------
/packages/cli/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/cli",
3 | "version": "1.3.6",
4 | "description": "cli to load environment variables with monorepo support",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "type": "module",
7 | "main": "dist/index.mjs",
8 | "bin": {
9 | "dotenv-run": "dist/index.mjs"
10 | },
11 | "files": [
12 | "dist",
13 | "README.md"
14 | ],
15 | "scripts": {
16 | "dev": "tsc -w",
17 | "test": "vitest",
18 | "build": "tsc"
19 | },
20 | "keywords": [
21 | "dotenv",
22 | "run",
23 | "cli"
24 | ],
25 | "author": "Chihab Otmani ",
26 | "license": "ISC",
27 | "dependencies": {
28 | "@dotenv-run/core": "workspace:^1.3.6",
29 | "chalk": "^4.1.2",
30 | "cross-spawn": "^7.0.3",
31 | "minimist": "^1.2.8"
32 | },
33 | "devDependencies": {
34 | "@types/cross-spawn": "^6.0.6",
35 | "@types/minimist": "^1.2.5"
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/packages/cli/src/index.mts:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 |
3 | import { env } from "@dotenv-run/core";
4 | import minimist from "minimist";
5 | import { run } from "./run.js";
6 |
7 | const argv = minimist(process.argv.slice(2), {
8 | string: ["verbose", "env", "file", "root"],
9 | boolean: ["help", "unsecure", "override"],
10 | alias: {
11 | verbose: "v",
12 | unsecure: "u",
13 | env: "e",
14 | root: "r",
15 | file: "f",
16 | help: "h",
17 | override: "o",
18 | },
19 | default: {
20 | unsecure: false,
21 | help: false,
22 | override: false,
23 | },
24 | });
25 |
26 | function help() {
27 | console.log(`
28 | Usage: dotenv-run [options] --
29 |
30 | Options:
31 | -v, --verbose [regexp] print debug information, display environment variables filtered by regexp if provided
32 | -u, --unsecure display environment variables in debug output (default: false)
33 | -e, --env [environment] environment to load (default: NODE_ENV)
34 | -r, --root root directory to start searching for .env files (default: root workspace directory)
35 | -f, --file [.env,.secrets,.env.api] specific .env files to load (default: .env)
36 | -o, --override override existing environment variables (default: false)
37 | -h, --help output usage information
38 |
39 | Examples:
40 | dotenv-run -d
41 | dotenv-run -- npm start
42 | dotenv-run -f .env,.env.api -- npm start
43 | `);
44 | }
45 |
46 | function parseList(input: string | string[]): string[] {
47 | return typeof input === "string" ? input.split(",") : input;
48 | }
49 |
50 | if (argv.h) {
51 | help();
52 | } else {
53 | const cmd = argv._[0];
54 | const verbose = argv.hasOwnProperty("v");
55 | if (!verbose && !cmd) {
56 | help();
57 | process.exit(1);
58 | }
59 | const root = argv.r;
60 | const files = parseList(argv.f ?? ".env");
61 | const cwd = process.cwd();
62 | env({
63 | environment: argv.e ?? process.env.NODE_ENV,
64 | cwd,
65 | root,
66 | files,
67 | prefix: argv.v,
68 | verbose,
69 | unsecure: argv.u,
70 | dotenv: { override: argv.o },
71 | });
72 | if (cmd) run(cmd, argv._.slice(1));
73 | }
74 |
--------------------------------------------------------------------------------
/packages/cli/src/run.ts:
--------------------------------------------------------------------------------
1 | import spawn from "cross-spawn";
2 |
3 | export const run = (cmd: string, args: string[]) => {
4 | spawn(cmd, args, { stdio: "inherit" }).on(
5 | "exit",
6 | function (exitCode, signal) {
7 | if (typeof exitCode === "number") {
8 | process.exit(exitCode);
9 | } else {
10 | process.kill(process.pid, signal);
11 | }
12 | }
13 | );
14 | };
15 |
--------------------------------------------------------------------------------
/packages/cli/test/cli.test.ts:
--------------------------------------------------------------------------------
1 | import { execSync } from "child_process";
2 | import { describe, it, expect } from "vitest";
3 |
4 | describe("dotenv-run should give the expected output", () => {
5 | it("empty", () => {
6 | const actual = execSync(
7 | "node ./dist/index.mjs -- node -e 'console.log(process.env.API_USERS)'",
8 | { encoding: "utf8" }
9 | );
10 | expect(actual).not.toContain("https://dotenv-run");
11 | });
12 |
13 | it("dev", () => {
14 | const actual = execSync(
15 | "NODE_ENV=dev node ./dist/index.mjs -- node -e 'console.log(process.env.API_USERS)'",
16 | { encoding: "utf8" }
17 | );
18 | expect(actual).toContain("https://dotenv-run.dev/");
19 | });
20 |
21 | it("prod", () => {
22 | const actual = execSync(
23 | "NODE_ENV=prod node ./dist/index.mjs -- node -e 'console.log(process.env.API_USERS)'",
24 | { encoding: "utf8" }
25 | );
26 | expect(actual).toContain("https://dotenv-run.app/");
27 | });
28 | });
29 |
--------------------------------------------------------------------------------
/packages/cli/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": [
3 | "src"
4 | ],
5 | "compilerOptions": {
6 | "outDir": "dist",
7 | "moduleResolution": "node",
8 | "target": "ES2020",
9 | "module": "ES2020",
10 | "strict": true,
11 | "strictNullChecks": false,
12 | "pretty": true,
13 | "sourceMap": false,
14 | "declaration": false,
15 | "stripInternal": true,
16 | "skipLibCheck": true,
17 | "allowSyntheticDefaultImports": true
18 | },
19 | "exclude": [
20 | "node_modules"
21 | ],
22 | "compileOnSave": false,
23 | "buildOnSave": false
24 | }
--------------------------------------------------------------------------------
/packages/core/.env.dev:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.dev
--------------------------------------------------------------------------------
/packages/core/.env.prod:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.app
--------------------------------------------------------------------------------
/packages/core/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/core
2 |
3 | ## 1.3.6
4 |
5 | ### Patch Changes
6 |
7 | - chore: use pnpm workspace protocol for dependencies
8 |
9 | ## 1.3.4
10 |
11 | ### Patch Changes
12 |
13 | - docs: updates packages' README files
14 |
15 | ## 1.3.3
16 |
17 | ### Patch Changes
18 |
19 | - fix(cli): fix unsecure mode alias
20 |
21 | ## 1.3.2
22 |
23 | ### Patch Changes
24 |
25 | - feat(angular): add unsecure mode option
26 |
27 | ## 1.3.1
28 |
29 | ### Patch Changes
30 |
31 | - feat: add secure mode to debug info
32 |
33 | ## 1.3.0
34 |
35 | ### Minor Changes
36 |
37 | - refactor and docs initialization
38 |
39 | ## 1.2.3
40 |
41 | ### Patch Changes
42 |
43 | - feat(core): support sub-module level turbo.json
44 |
45 | ## 1.2.2
46 |
47 | ### Patch Changes
48 |
49 | - fix(core): filter out undefined env values
50 |
51 | ## 1.2.1
52 |
53 | ### Patch Changes
54 |
55 | - refactor(esbuild): usde esbuild define option
56 |
57 | ## 1.2.0
58 |
59 | ### Minor Changes
60 |
61 | - f63ecac: feat: add esbuild plugin
62 |
63 | ## 1.1.0
64 |
65 | ### Minor Changes
66 |
67 | - af82054: feat: add cjs format and doc
68 |
69 | ## 1.0.0
70 |
71 | ### Major Changes
72 |
73 | - feat: add bundler plugins
74 |
75 | ## 0.5.0
76 |
77 | ### Minor Changes
78 |
79 | - 5efdd8f: add environment option
80 |
81 | ## 0.4.1
82 |
83 | ### Patch Changes
84 |
85 | - fix(cli): fallback root workspace to package.json path
86 |
87 | ## 0.4.0
88 |
89 | ### Minor Changes
90 |
91 | - 98967ed: feat(cli): search for monorepo tools configuration file
92 |
93 | ## 0.3.0
94 |
95 | ### Minor Changes
96 |
97 | - feat(cli): search for root workspace
98 |
99 | ## 0.2.0
100 |
101 | ### Minor Changes
102 |
103 | - 3551e4d: @dotenv-run/cli a cli to load command line and .env environment variables with monorepo support
104 |
--------------------------------------------------------------------------------
/packages/core/README.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/core
2 |
3 | - ✅ Load environment variables from the command line `API_BASE=/v1/ core`
4 | - ✅ Load environment variables from `.env` files
5 | - ✅ Expand environment variables `API_URL=$API_BASE/users`
6 | - ✅ Define environment variables for a specific environment (e.g. `.env.production`)
7 | - ✅ Load priorities of `.env.*` files (e.g. `.env.production` > `.env`)
8 | - ✅ Hierarchical cascading configuration in monorepo projects ([Nx](https://nx.dev), [Turbo](https://turborepo.com/), etc.)
9 | `apps/next-app/.env` > `apps/.env` > `.env`
10 |
11 | # Install
12 |
13 | ```console
14 | npm add @dotenv-run/core
15 | ```
16 |
17 | # Usage
18 |
19 | ```js
20 | // index.js
21 | import { env } from "@dotenv-run/core";
22 | env({
23 | root: "../..",
24 | verbose: true,
25 | prefix: "^API_",
26 | files: [".env"],
27 | });
28 | console.log(process.env.API_USERS);
29 | ```
30 |
31 | given the following files:
32 |
33 | ```shell
34 | .env
35 | API_USERS=$API_BASE/v1/users
36 | API_AUTH=$API_BASE/v1/auth
37 | .env.dev
38 | API_BASE=https://localhost:3000
39 | .env.prod
40 | API_BASE=https://dotenv-run.app
41 | ```
42 |
43 | then:
44 |
45 | ```shell
46 | NODE_ENV=dev node index.js
47 | https://localhost:3000/v1/users
48 |
49 | NODE_ENV=prod node index.js
50 | https://dotenv-run.app/v1/users
51 | ```
52 |
53 | # License
54 |
55 | MIT © [Chihab Otmani](mailto:chihab@gmail.com)
56 |
--------------------------------------------------------------------------------
/packages/core/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/core",
3 | "version": "1.3.6",
4 | "description": "core library to load environment variables with monorepo support",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "dist/cjs/index.js",
7 | "module": "dist/esm/index.js",
8 | "types": "dist/index.d.ts",
9 | "scripts": {
10 | "dev": "tsc -w",
11 | "test": "vitest",
12 | "build": "concurrently npm:build:*",
13 | "build:esm": "tsc --module esnext --outDir dist/esm",
14 | "build:cjs": "tsc --module commonjs --outDir dist/cjs",
15 | "build:types": "tsc --emitDeclarationOnly --declaration --declarationMap --module esnext --outDir dist"
16 | },
17 | "files": [
18 | "dist",
19 | "README.md"
20 | ],
21 | "keywords": [
22 | "dotenv",
23 | "run",
24 | "cli"
25 | ],
26 | "author": "Chihab Otmani ",
27 | "license": "ISC",
28 | "dependencies": {
29 | "chalk": "^4.1.2",
30 | "dotenv": "^16.4.5",
31 | "dotenv-expand": "^10.0.0",
32 | "find-up": "^5.0.0"
33 | },
34 | "devDependencies": {
35 | "@types/node": "^16.18.112"
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/packages/core/src/build.ts:
--------------------------------------------------------------------------------
1 | export type Dict = Record;
2 |
3 | export type DotenvRun = {
4 | raw: Dict;
5 | stringified: Dict;
6 | full: Dict;
7 | };
8 |
9 | export function build(
10 | processEnv: Dict,
11 | runtime: boolean,
12 | globalVar: string,
13 | define?: string
14 | ) {
15 | const values = Object.keys(processEnv).reduce(
16 | (env, key) => {
17 | const value = runtime
18 | ? `globalThis.${globalVar}.${key}`
19 | : JSON.stringify(processEnv[key]);
20 | env.raw[key] = processEnv[key];
21 | env.stringified[key] = value;
22 | env.full[`process.env.${key}`] = value;
23 | env.full[`import.meta.env.${key}`] = value;
24 | return env;
25 | },
26 | {
27 | raw: {},
28 | stringified: define
29 | ? {
30 | [define]: runtime
31 | ? `globalThis.${globalVar}`
32 | : JSON.stringify(processEnv),
33 | }
34 | : {},
35 | full: define
36 | ? {
37 | [define]: runtime
38 | ? `globalThis.${globalVar}`
39 | : JSON.stringify(processEnv),
40 | }
41 | : {},
42 | }
43 | );
44 | return values;
45 | }
46 |
--------------------------------------------------------------------------------
/packages/core/src/expand.ts:
--------------------------------------------------------------------------------
1 | import { config, DotenvConfigOptions } from "dotenv";
2 | import { expand as dotenvExpand } from "dotenv-expand";
3 |
4 | export function expand(envPaths: string[], dotenvConfig?: DotenvConfigOptions) {
5 | envPaths.forEach((dotenvFile) => {
6 | dotenvExpand(
7 | config({
8 | path: dotenvFile,
9 | ...dotenvConfig,
10 | })
11 | );
12 | });
13 | }
14 |
--------------------------------------------------------------------------------
/packages/core/src/index.ts:
--------------------------------------------------------------------------------
1 | export * from "./env.js";
2 | export * from "./options.js";
3 | export * from "./root.js";
4 | export * from "./build.js";
5 |
6 | declare global {
7 | interface ImportMeta {
8 | env: ImportMetaEnv;
9 | }
10 |
11 | interface ImportMetaEnv {
12 | [key: string]: any;
13 | }
14 | }
15 |
--------------------------------------------------------------------------------
/packages/core/src/options.ts:
--------------------------------------------------------------------------------
1 | import type { DotenvConfigOptions } from "dotenv";
2 | import { Dict } from "./build";
3 |
4 | export interface DotenvRunOptions {
5 | cwd?: string; // Path to current working directory
6 | dotenv?: DotenvConfigOptions;
7 | environment?: string; // Environment to load
8 | files?: string[]; // Environment files to load
9 | prefix?: string | RegExp; // Filter keys to inject
10 | unsecure?: boolean; // Display environment variables in debug output
11 | root?: string; // Path to root workspace
12 | nodeEnv?: boolean; // Node environment
13 | verbose?: boolean; // Print verbose output
14 | builtIn?: Dict; // Built-in environment variables
15 | runtime?: boolean; // Whether to use runtime variables
16 | define?: string; // Define key to replace in code
17 | global?: string; // Global variable name
18 | }
19 |
--------------------------------------------------------------------------------
/packages/core/src/root.ts:
--------------------------------------------------------------------------------
1 | import * as findUp from "find-up";
2 | import { readFileSync } from "fs";
3 | import * as path from "path";
4 |
5 | /**
6 | * Return root `turbo.json` file path if found, else return original input.
7 | *
8 | * @param turboPath existing turbo.json file path.
9 | * @throws {Error} if `turboPath` is not exist.
10 | */
11 | function findTurboRootPath(turboPath: string): string {
12 | // test if file content has `"extends": ["//"]`
13 | const isSubProject = readFileSync(turboPath, "utf8").includes('"extends"');
14 | if (isSubProject) {
15 | const parent = path.dirname(path.dirname(turboPath));
16 | const rootPath = findUp.sync("turbo.json", { cwd: parent });
17 | if (rootPath) return rootPath;
18 | }
19 | return turboPath;
20 | }
21 |
22 | export function findRootPath() {
23 | if (process.env.NX_WORKSPACE_ROOT) {
24 | return process.env.NX_WORKSPACE_ROOT;
25 | }
26 | let p = findUp.sync([
27 | "turbo.json",
28 | "nx.json", // Just in case NX_WORKSPACE_ROOT is not set
29 | "lerna.json",
30 | "pnpm-workspace.yaml",
31 | ]);
32 |
33 | if (p && p.endsWith("turbo.json")) {
34 | p = findTurboRootPath(p);
35 | }
36 |
37 | if (!p) p = findUp.sync(["package.json"]);
38 | return p ? path.dirname(p) : process.cwd();
39 | }
40 |
--------------------------------------------------------------------------------
/packages/core/src/utils.ts:
--------------------------------------------------------------------------------
1 | import * as fs from "fs";
2 | import * as path from "path";
3 |
4 | export function isSubfolder(parent: string, child: string) {
5 | return path.relative(parent, child).startsWith("..");
6 | }
7 |
8 | export function getAbsoluteEnvPath(envPath: string, cwd: string) {
9 | const _envPath = path.isAbsolute(envPath)
10 | ? envPath
11 | : path.resolve(cwd, envPath);
12 | return fs.existsSync(_envPath)
13 | ? fs.lstatSync(_envPath).isDirectory()
14 | ? _envPath
15 | : path.dirname(_envPath)
16 | : cwd;
17 | }
18 |
19 | export function getPathsDownTo(envPath: string, destination: string) {
20 | let currentPath = destination;
21 | const paths = [currentPath];
22 | while (currentPath !== envPath && currentPath !== "/") {
23 | currentPath = path.dirname(currentPath);
24 | paths.push(currentPath);
25 | }
26 | return paths;
27 | }
28 |
--------------------------------------------------------------------------------
/packages/core/test/dev.test.ts:
--------------------------------------------------------------------------------
1 | import { it, expect } from "vitest";
2 | import { env } from "../src";
3 |
4 | it("should load dev environment from the root workspace", () => {
5 | process.env.NODE_ENV = "dev";
6 | const { full, stringified, raw } = env({
7 | root: "..",
8 | verbose: true,
9 | prefix: "^API_",
10 | files: [".env"],
11 | });
12 | expect(raw).toEqual({
13 | API_AUTH: "https://dotenv-run.dev/api/v1/auth",
14 | API_BASE: "https://dotenv-run.dev",
15 | API_USERS: "https://dotenv-run.dev/api/v1/users",
16 | NODE_ENV: "dev",
17 | });
18 | expect(stringified).toEqual({
19 | API_AUTH: '"https://dotenv-run.dev/api/v1/auth"',
20 | API_BASE: '"https://dotenv-run.dev"',
21 | API_USERS: '"https://dotenv-run.dev/api/v1/users"',
22 | NODE_ENV: '"dev"',
23 | });
24 | expect(full).toEqual({
25 | "import.meta.env.API_AUTH": '"https://dotenv-run.dev/api/v1/auth"',
26 | "import.meta.env.API_BASE": '"https://dotenv-run.dev"',
27 | "import.meta.env.API_USERS": '"https://dotenv-run.dev/api/v1/users"',
28 | "import.meta.env.NODE_ENV": '"dev"',
29 | "process.env.API_AUTH": '"https://dotenv-run.dev/api/v1/auth"',
30 | "process.env.API_BASE": '"https://dotenv-run.dev"',
31 | "process.env.API_USERS": '"https://dotenv-run.dev/api/v1/users"',
32 | "process.env.NODE_ENV": '"dev"',
33 | });
34 | expect(process.env.API_USERS).toBe("https://dotenv-run.dev/api/v1/users");
35 | });
36 |
--------------------------------------------------------------------------------
/packages/core/test/prod.test.ts:
--------------------------------------------------------------------------------
1 | import { expect, it } from "vitest";
2 | import { env } from "../src";
3 |
4 | it("should load prod environment", () => {
5 | process.env.NODE_ENV = "prod";
6 | const { full, stringified, raw } = env({
7 | root: "..",
8 | verbose: true,
9 | prefix: "^API_",
10 | });
11 | expect(raw).toEqual({
12 | API_AUTH: "https://dotenv-run.app/api/v1/auth",
13 | API_BASE: "https://dotenv-run.app",
14 | API_USERS: "https://dotenv-run.app/api/v1/users",
15 | NODE_ENV: "prod",
16 | });
17 | expect(stringified).toEqual({
18 | API_AUTH: '"https://dotenv-run.app/api/v1/auth"',
19 | API_BASE: '"https://dotenv-run.app"',
20 | API_USERS: '"https://dotenv-run.app/api/v1/users"',
21 | NODE_ENV: '"prod"',
22 | });
23 | expect(full).toEqual({
24 | "import.meta.env.API_AUTH": '"https://dotenv-run.app/api/v1/auth"',
25 | "import.meta.env.API_BASE": '"https://dotenv-run.app"',
26 | "import.meta.env.API_USERS": '"https://dotenv-run.app/api/v1/users"',
27 | "import.meta.env.NODE_ENV": '"prod"',
28 | "process.env.API_AUTH": '"https://dotenv-run.app/api/v1/auth"',
29 | "process.env.API_BASE": '"https://dotenv-run.app"',
30 | "process.env.API_USERS": '"https://dotenv-run.app/api/v1/users"',
31 | "process.env.NODE_ENV": '"prod"',
32 | });
33 | expect(process.env.API_USERS).toBe("https://dotenv-run.app/api/v1/users");
34 | });
35 |
--------------------------------------------------------------------------------
/packages/core/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "target": "ES2022",
7 | "module": "ES2022",
8 | "strict": true,
9 | "esModuleInterop": true,
10 | "forceConsistentCasingInFileNames": true,
11 | "strictPropertyInitialization": false,
12 | "strictNullChecks": false,
13 | "pretty": true,
14 | "sourceMap": true,
15 | "skipLibCheck": true
16 | },
17 | "exclude": ["node_modules"],
18 | "compileOnSave": false,
19 | "buildOnSave": false
20 | }
21 |
--------------------------------------------------------------------------------
/packages/esbuild/.env:
--------------------------------------------------------------------------------
1 | MY_API_BASE=https://dotenv-run.app
--------------------------------------------------------------------------------
/packages/esbuild/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/esbuild
2 |
3 | ## 1.5.0
4 |
5 | ### Minor Changes
6 |
7 | - 8f83f0c: feat: add compatibility with Angular 19
8 |
9 | ## 1.4.2
10 |
11 | ### Patch Changes
12 |
13 | - chore: use pnpm workspace protocol for dependencies
14 | - Updated dependencies
15 | - @dotenv-run/core@1.3.6
16 |
17 | ## 1.4.0
18 |
19 | ### Minor Changes
20 |
21 | - bump up webpack and esbuild versions
22 |
23 | ## 1.3.4
24 |
25 | ### Patch Changes
26 |
27 | - docs: updates packages' README files
28 | - Updated dependencies
29 | - @dotenv-run/core@1.3.4
30 |
31 | ## 1.3.3
32 |
33 | ### Patch Changes
34 |
35 | - fix(cli): fix unsecure mode alias
36 | - Updated dependencies
37 | - @dotenv-run/core@1.3.3
38 |
39 | ## 1.3.2
40 |
41 | ### Patch Changes
42 |
43 | - feat(angular): add unsecure mode option
44 | - Updated dependencies
45 | - @dotenv-run/core@1.3.2
46 |
47 | ## 1.3.1
48 |
49 | ### Patch Changes
50 |
51 | - feat: add secure mode to debug info
52 | - Updated dependencies
53 | - @dotenv-run/core@1.3.1
54 |
55 | ## 1.3.0
56 |
57 | ### Minor Changes
58 |
59 | - refactor and docs initialization
60 |
61 | ### Patch Changes
62 |
63 | - Updated dependencies
64 | - @dotenv-run/core@1.3.0
65 |
66 | ## 1.2.3
67 |
68 | ### Patch Changes
69 |
70 | - feat(core): support sub-module level turbo.json
71 | - Updated dependencies
72 | - @dotenv-run/core@1.2.3
73 |
74 | ## 1.2.2
75 |
76 | ### Patch Changes
77 |
78 | - fix(core): filter out undefined env values
79 | - Updated dependencies
80 | - @dotenv-run/core@1.2.2
81 |
82 | ## 1.2.1
83 |
84 | ### Patch Changes
85 |
86 | - refactor(esbuild): usde esbuild define option
87 | - Updated dependencies
88 | - @dotenv-run/core@1.2.1
89 |
90 | ## 1.2.0
91 |
92 | ### Minor Changes
93 |
94 | - f63ecac: feat: add esbuild plugin
95 |
96 | ### Patch Changes
97 |
98 | - Updated dependencies [f63ecac]
99 | - @dotenv-run/core@1.2.0
100 |
--------------------------------------------------------------------------------
/packages/esbuild/README.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/esbuild
2 |
3 | - ✅ Load environment variables from the command line `API_BASE=/v1/ node esbuild.mjs`
4 | - ✅ Load environment variables from `.env` files
5 | - ✅ Expand environment variables `API_URL=$API_BASE/users`
6 | - ✅ Define environment variables for a specific environment (e.g. `.env.production`)
7 | - ✅ Load priorities of `.env.*` files (e.g. `.env.production` > `.env`)
8 | - ✅ Hierarchical cascading configuration in monorepo projects ([Nx](https://nx.dev), [Turbo](https://turborepo.com/), etc.)
9 | `apps/next-app/.env` > `apps/.env` > `.env`
10 |
11 | ## Install
12 |
13 | ```console
14 | npm add @dotenv-run/esbuild --save-dev
15 | ```
16 |
17 | ## Usage
18 |
19 | ### Using define (recommended)
20 |
21 | ```js
22 | import { build } from "esbuild";
23 | import { env } from "@dotenv-run/esbuild";
24 |
25 | const { full } = env({
26 | prefix: "MY_",
27 | verbose: false,
28 | files: [".env"],
29 | });
30 |
31 | const results = await build({
32 | bundle: true,
33 | write: false,
34 | entryPoints: [`test/app.js`],
35 | define: full,
36 | });
37 | ```
38 |
39 | ### Using esbuild plugin
40 |
41 | ```js
42 | import { build } from "esbuild";
43 | import { dotenvRun } from "@dotenv-run/esbuild";
44 |
45 | await build({
46 | write: false,
47 | bundle: true,
48 | entryPoints: [`test/app.js`],
49 | plugins: [
50 | dotenvRun({
51 | verbose: true,
52 | root: "../../",
53 | prefix: "^API",
54 | }),
55 | ],
56 | });
57 | ```
58 |
--------------------------------------------------------------------------------
/packages/esbuild/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/esbuild",
3 | "version": "1.5.0",
4 | "description": "Run your scripts with dotenv variables",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "dist/cjs/index.js",
7 | "module": "dist/esm/index.js",
8 | "types": "dist/index.d.ts",
9 | "scripts": {
10 | "dev": "tsc -w",
11 | "test": "vitest",
12 | "build": "concurrently npm:build:*",
13 | "build:esm": "tsc --module esnext --outDir dist/esm",
14 | "build:cjs": "tsc --module commonjs --outDir dist/cjs",
15 | "build:types": "tsc --emitDeclarationOnly --declaration --declarationMap --module esnext --outDir dist"
16 | },
17 | "files": [
18 | "dist",
19 | "README.md"
20 | ],
21 | "keywords": [
22 | "dotenv",
23 | "run",
24 | "cli"
25 | ],
26 | "author": "Chihab Otmani ",
27 | "license": "ISC",
28 | "dependencies": {
29 | "@dotenv-run/core": "workspace:~1.3.6"
30 | },
31 | "peerDependencies": {
32 | "esbuild": "^0.21.0"
33 | },
34 | "devDependencies": {
35 | "@types/node": "^16.18.112",
36 | "esbuild": "^0.23.0"
37 | }
38 | }
39 |
--------------------------------------------------------------------------------
/packages/esbuild/src/index.ts:
--------------------------------------------------------------------------------
1 | import { Dict, env, type DotenvRunOptions } from "@dotenv-run/core";
2 | import type { Plugin, PluginBuild } from "esbuild";
3 |
4 | function definePluginBuild(build: PluginBuild, env: Dict): void {
5 | const define = build.initialOptions.define ?? {};
6 | build.initialOptions.define = {
7 | ...env,
8 | ...define,
9 | };
10 | }
11 |
12 | const dotenvRun = (options: DotenvRunOptions): Plugin => {
13 | return {
14 | name: "dotenv-run",
15 | setup(build) {
16 | const full = env(options).full;
17 | definePluginBuild(build, full);
18 | },
19 | };
20 | };
21 |
22 | const dotenvRunDefine = (env: Dict): Plugin => {
23 | return {
24 | name: "dotenv-run-define",
25 | setup(build) {
26 | definePluginBuild(build, env);
27 | },
28 | };
29 | };
30 |
31 | export { DotenvRunOptions, dotenvRun, dotenvRunDefine };
32 | export default dotenvRun;
33 |
--------------------------------------------------------------------------------
/packages/esbuild/test/__snapshots__/index.test.ts.snap:
--------------------------------------------------------------------------------
1 | // Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
2 |
3 | exports[`Usage with esbuild > should replace environment variables using define option 1`] = `
4 | "\\"use strict\\";
5 | (() => {
6 | // test/util.js
7 | function meta() {
8 | return \\"https://dotenv-run.app\\";
9 | }
10 |
11 | // test/app.js
12 | console.log(\\"https://dotenv-run.app\\");
13 | console.log(meta());
14 | })();"
15 | `;
16 |
17 | exports[`Usage with esbuild > should replace environment variables using esbuild plugin 1`] = `
18 | "\\"use strict\\";
19 | (() => {
20 | // test/util.js
21 | function meta() {
22 | return \\"https://dotenv-run.app\\";
23 | }
24 |
25 | // test/app.js
26 | console.log(\\"https://dotenv-run.app\\");
27 | console.log(meta());
28 | })();
29 | "
30 | `;
31 |
32 | exports[`Usage with esbuild > should replace environment variables using esbuild plugin and a custom define 1`] = `
33 | "\\"use strict\\";
34 | (() => {
35 | // test/util.js
36 | function meta() {
37 | return \\"https://dotenv-run.define\\";
38 | }
39 |
40 | // test/app.js
41 | console.log(\\"https://dotenv-run.define\\");
42 | console.log(meta());
43 | })();
44 | "
45 | `;
46 |
--------------------------------------------------------------------------------
/packages/esbuild/test/app.js:
--------------------------------------------------------------------------------
1 | import { meta } from './util.js';
2 |
3 | console.log(process.env.MY_API_BASE);
4 | console.log(meta());
--------------------------------------------------------------------------------
/packages/esbuild/test/index.test.ts:
--------------------------------------------------------------------------------
1 | import { build } from "esbuild";
2 | import { describe, expect, it } from "vitest";
3 | import { dotenvRun } from "../src/";
4 | import { env } from "@dotenv-run/core";
5 |
6 | describe("Usage with esbuild", () => {
7 | it("should replace environment variables using esbuild plugin", async () => {
8 | const results = await build({
9 | write: false,
10 | bundle: true,
11 | entryPoints: [`test/app.js`],
12 | plugins: [
13 | dotenvRun({
14 | prefix: "MY_",
15 | verbose: false,
16 | files: [".env"],
17 | }),
18 | ],
19 | });
20 |
21 | expect(results.outputFiles.at(0)?.text).toMatchSnapshot();
22 | });
23 |
24 |
25 | it("should replace environment variables using esbuild plugin and a custom define", async () => {
26 | const results = await build({
27 | write: false,
28 | bundle: true,
29 | entryPoints: [`test/app.js`],
30 | define: {
31 | "process.env.MY_API_BASE": '"https://dotenv-run.define"',
32 | "import.meta.env.MY_API_BASE": '"https://dotenv-run.define"',
33 | },
34 | plugins: [
35 | dotenvRun({
36 | prefix: "MY_",
37 | verbose: false,
38 | files: [".env"],
39 | }),
40 | ],
41 | });
42 |
43 | expect(results.outputFiles.at(0)?.text).toMatchSnapshot();
44 | });
45 |
46 | it("should replace environment variables using define option", async () => {
47 | const { full } = env({
48 | prefix: "MY_",
49 | verbose: false,
50 | files: [".env"],
51 | });
52 |
53 | const results = await build({
54 | bundle: true,
55 | write: false,
56 | entryPoints: [`test/app.js`],
57 | define: full,
58 | });
59 |
60 | expect(results.outputFiles.at(0)?.text.trim()).toMatchSnapshot();
61 | });
62 | });
63 |
--------------------------------------------------------------------------------
/packages/esbuild/test/util.js:
--------------------------------------------------------------------------------
1 | export function meta() {
2 | return import.meta.env.MY_API_BASE;
3 | }
--------------------------------------------------------------------------------
/packages/esbuild/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "module": "ES2022",
7 | "strict": true,
8 | "forceConsistentCasingInFileNames": true,
9 | "strictPropertyInitialization": false,
10 | "esModuleInterop": true,
11 | "strictNullChecks": false,
12 | "pretty": true,
13 | "sourceMap": true,
14 | "declaration": true,
15 | "skipLibCheck": true
16 | },
17 | "exclude": ["node_modules"],
18 | "compileOnSave": false,
19 | "buildOnSave": false
20 | }
21 |
--------------------------------------------------------------------------------
/packages/jest-angular/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/jest-angular
2 |
3 | ## 0.2.0
4 |
5 | ### Minor Changes
6 |
7 | - 8f83f0c: feat: add compatibility with Angular 19
8 |
--------------------------------------------------------------------------------
/packages/jest-angular/README.md:
--------------------------------------------------------------------------------
1 | ## Install
2 |
3 | The package requires `jest-preset-angular@14` to be installed as a peer dependency.
4 |
5 | ```sh
6 | npm install --save-dev @dotenv-run/jest-angular
7 | ```
8 |
9 | ## Usage
10 |
11 | Add the following to your `jest.config.js`, more information can be found in the [jest-preset-angular](https://thymikee.github.io/jest-preset-angular/docs/guides/esm-support/).
12 |
13 | ESM support is required for Jest to understand `import.meta.env` notation.
14 |
15 | ```js
16 | const jestConfig = {
17 | // Required for ESM support
18 | preset: "jest-preset-angular/presets/defaults-esm",
19 | setupFilesAfterEnv: ["/setup-jest.ts"],
20 | testMatch: ["/src/app/**/*.(spec|jest).ts"],
21 | moduleNameMapper: {
22 | "^rxjs(/operators$)?$":
23 | "/node_modules/rxjs/dist/bundles/rxjs.umd.js",
24 | tslib: "/node_modules/tslib/tslib.es6.mjs",
25 | },
26 |
27 | // @dotenv-run/jest-angular transformer
28 | transform: {
29 | "^.+\\.(ts)$": [
30 | "@dotenv-run/jest-angular",
31 | {
32 | useESM: true,
33 | stringifyContentPathRegex: "\\.(html|svg)$",
34 | },
35 | ],
36 | },
37 | };
38 |
39 | export default jestConfig;
40 | ```
41 |
42 | Add the following to your `setup-jest.ts` file.
43 |
44 | ```ts
45 | // Required for ESM support
46 | import "jest-preset-angular/setup-jest.mjs";
47 |
48 | // Load environment variables for Jest
49 | import { env } from "@dotenv-run/core";
50 | env({ root: "../../..", files: [".env", ".env.app"] });
51 | ```
52 |
53 | Run your tests with `jest`. More information can be found in the [Jest documentation](https://jestjs.io/docs/ecmascript-modules).
54 |
55 | ```sh
56 | NODE_OPTIONS=--experimental-vm-modules npx jest
57 | ```
58 |
59 | or
60 |
61 | ```sh
62 | node --experimental-vm-modules /path/to/node_modules/jest/bin/jest.js
63 | ```
64 |
65 | If you're using Nx
66 |
67 | ```sh
68 | NODE_OPTIONS=--experimental-vm-modules nx test
69 | ```
70 |
71 | ```sh
72 | node --experimental-vm-modules /path/to/node_modules/nx/bin/nx.js test
73 | ```
74 |
--------------------------------------------------------------------------------
/packages/jest-angular/index.mjs:
--------------------------------------------------------------------------------
1 | import { NgJestTransformer } from "jest-preset-angular/build/ng-jest-transformer.js";
2 | export default {
3 | createTransformer: (tsJestConfig) => {
4 | const ngT = new NgJestTransformer(tsJestConfig);
5 | return {
6 | process: (src, filename, config, options) => {
7 | if (/.ts$/.test(filename)) {
8 | src = `
9 | import.meta.env = process.env;
10 | ${src}
11 | `;
12 | }
13 | return ngT.process(src, filename, config, options);
14 | },
15 | };
16 | },
17 | };
18 |
--------------------------------------------------------------------------------
/packages/jest-angular/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/jest-angular",
3 | "version": "0.2.0",
4 | "description": "Run Jest with Angular CLI environment variables",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "sideEffects": true,
7 | "files": [
8 | "index.mjs",
9 | "README.md"
10 | ],
11 | "exports": {
12 | ".": {
13 | "import": "./index.mjs",
14 | "require": "./index.mjs"
15 | }
16 | },
17 | "keywords": [
18 | "dotenv",
19 | "run",
20 | "cli"
21 | ],
22 | "devDependencies": {
23 | "jest-preset-angular": "^14.0.0"
24 | },
25 | "peerDependencies": {
26 | "jest-preset-angular": "^14.0.0"
27 | },
28 | "author": "Chihab Otmani ",
29 | "license": "ISC"
30 | }
31 |
--------------------------------------------------------------------------------
/packages/jest/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/jest",
3 | "version": "0.1.0",
4 | "description": "Run Jest with import.meta.env",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "src/jest-env.mjs",
7 | "module": "src/jest-env.mjs",
8 | "files": [
9 | "src",
10 | "README.md"
11 | ],
12 | "keywords": [
13 | "dotenv",
14 | "run"
15 | ],
16 | "author": "Chihab Otmani ",
17 | "license": "ISC"
18 | }
19 |
--------------------------------------------------------------------------------
/packages/jest/src/jest-env.mjs:
--------------------------------------------------------------------------------
1 | export default {
2 | createTransformer: () => {
3 | return {
4 | process: (src, filename) => {
5 | if (/.ts$/.test(filename)) {
6 | src = `
7 | import.meta.env = process.env;
8 | ${src}
9 | `;
10 | }
11 | return { code: src };
12 | },
13 | };
14 | },
15 | };
16 |
--------------------------------------------------------------------------------
/packages/load/.env:
--------------------------------------------------------------------------------
1 | API_USERS=$API_BASE/api/v1/users
2 | API_AUTH=$API_BASE/api/v1/auth
--------------------------------------------------------------------------------
/packages/load/.env.dev:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.dev
--------------------------------------------------------------------------------
/packages/load/.env.prod:
--------------------------------------------------------------------------------
1 | API_BASE=https://dotenv-run.app
--------------------------------------------------------------------------------
/packages/load/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/load
2 |
3 | ## 1.3.6
4 |
5 | ### Patch Changes
6 |
7 | - chore: use pnpm workspace protocol for dependencies
8 | - Updated dependencies
9 | - @dotenv-run/core@1.3.6
10 |
11 | ## 1.3.4
12 |
13 | ### Patch Changes
14 |
15 | - docs: updates packages' README files
16 | - Updated dependencies
17 | - @dotenv-run/core@1.3.4
18 |
19 | ## 1.3.3
20 |
21 | ### Patch Changes
22 |
23 | - fix(cli): fix unsecure mode alias
24 | - Updated dependencies
25 | - @dotenv-run/core@1.3.3
26 |
27 | ## 1.3.2
28 |
29 | ### Patch Changes
30 |
31 | - feat(angular): add unsecure mode option
32 | - Updated dependencies
33 | - @dotenv-run/core@1.3.2
34 |
35 | ## 1.3.1
36 |
37 | ### Patch Changes
38 |
39 | - feat: add secure mode to debug info
40 | - Updated dependencies
41 | - @dotenv-run/core@1.3.1
42 |
43 | ## 1.3.0
44 |
45 | ### Minor Changes
46 |
47 | - refactor and docs initialization
48 |
49 | ### Patch Changes
50 |
51 | - Updated dependencies
52 | - @dotenv-run/core@1.3.0
53 |
54 | ## 1.2.3
55 |
56 | ### Patch Changes
57 |
58 | - feat(core): support sub-module level turbo.json
59 | - Updated dependencies
60 | - @dotenv-run/core@1.2.3
61 |
62 | ## 1.2.2
63 |
64 | ### Patch Changes
65 |
66 | - fix(core): filter out undefined env values
67 | - Updated dependencies
68 | - @dotenv-run/core@1.2.2
69 |
70 | ## 1.2.1
71 |
72 | ### Patch Changes
73 |
74 | - refactor(esbuild): usde esbuild define option
75 | - Updated dependencies
76 | - @dotenv-run/core@1.2.1
77 |
78 | ## 1.2.0
79 |
80 | ### Minor Changes
81 |
82 | - f63ecac: feat: add esbuild plugin
83 |
84 | ### Patch Changes
85 |
86 | - Updated dependencies [f63ecac]
87 | - @dotenv-run/core@1.2.0
88 |
89 | ## 1.1.0
90 |
91 | ### Minor Changes
92 |
93 | - af82054: feat: add cjs format and doc
94 |
95 | ### Patch Changes
96 |
97 | - Updated dependencies [af82054]
98 | - @dotenv-run/core@1.1.0
99 |
--------------------------------------------------------------------------------
/packages/load/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/load",
3 | "version": "1.3.6",
4 | "description": "Preload your scripts with dotenv variables",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "dist/index.js",
7 | "types": "dist/index.d.ts",
8 | "scripts": {
9 | "dev": "tsc -w",
10 | "test": "vitest",
11 | "build": "tsc"
12 | },
13 | "files": [
14 | "dist",
15 | "README.md"
16 | ],
17 | "keywords": [
18 | "dotenv",
19 | "run",
20 | "cli"
21 | ],
22 | "author": "Chihab Otmani ",
23 | "license": "ISC",
24 | "dependencies": {
25 | "@dotenv-run/core": "workspace:^1.3.6"
26 | },
27 | "devDependencies": {
28 | "@types/node": "^16.18.112"
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/packages/load/src/index.ts:
--------------------------------------------------------------------------------
1 | import { env, findRootPath } from "@dotenv-run/core";
2 | env({
3 | environment: process.env.NODE_ENV,
4 | cwd: process.cwd(),
5 | root: findRootPath(),
6 | files: [".env"]
7 | });
8 | env();
9 |
--------------------------------------------------------------------------------
/packages/load/test/load.test.ts:
--------------------------------------------------------------------------------
1 | import { execSync } from "child_process";
2 | import { describe, it, expect } from "vitest";
3 |
4 | describe("dotenv-run should give the expected output", () => {
5 | it("preload dev", () => {
6 | const actual = execSync(
7 | "NODE_ENV=dev node -r ./dist/index.js ./test/server.js",
8 | {
9 | encoding: "utf8",
10 | }
11 | );
12 | expect(actual).toContain("https://dotenv-run.dev/");
13 | });
14 |
15 | it("preload prod", () => {
16 | const actual = execSync(
17 | "NODE_ENV=prod node -r ./dist/index.js ./test/server.js",
18 | {
19 | encoding: "utf8",
20 | }
21 | );
22 | expect(actual).toContain("https://dotenv-run.app/");
23 | });
24 |
25 | it("NODE_OPTIONS prod", () => {
26 | const actual = execSync(
27 | "NODE_ENV=prod NODE_OPTIONS='-r ./dist/index.js' node ./test/server.js",
28 | {
29 | encoding: "utf8",
30 | }
31 | );
32 | expect(actual).toContain("https://dotenv-run.app/");
33 | });
34 | });
35 |
--------------------------------------------------------------------------------
/packages/load/test/server.js:
--------------------------------------------------------------------------------
1 | console.log(process.env.API_USERS)
--------------------------------------------------------------------------------
/packages/load/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "module": "CommonJS",
7 | "strict": true,
8 | "allowSyntheticDefaultImports": true,
9 | "forceConsistentCasingInFileNames": true,
10 | "strictPropertyInitialization": false,
11 | "strictNullChecks": false,
12 | "pretty": true,
13 | "sourceMap": true,
14 | "declaration": true,
15 | "skipLibCheck": true
16 | },
17 | "exclude": ["node_modules"],
18 | "compileOnSave": false,
19 | "buildOnSave": false
20 | }
21 |
--------------------------------------------------------------------------------
/packages/rollup/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/rollup
2 |
3 | ## 1.3.6
4 |
5 | ### Patch Changes
6 |
7 | - chore: use pnpm workspace protocol for dependencies
8 | - Updated dependencies
9 | - @dotenv-run/core@1.3.6
10 |
11 | ## 1.3.4
12 |
13 | ### Patch Changes
14 |
15 | - docs: updates packages' README files
16 | - Updated dependencies
17 | - @dotenv-run/core@1.3.4
18 |
19 | ## 1.3.3
20 |
21 | ### Patch Changes
22 |
23 | - fix(cli): fix unsecure mode alias
24 | - Updated dependencies
25 | - @dotenv-run/core@1.3.3
26 |
27 | ## 1.3.2
28 |
29 | ### Patch Changes
30 |
31 | - feat(angular): add unsecure mode option
32 | - Updated dependencies
33 | - @dotenv-run/core@1.3.2
34 |
35 | ## 1.3.1
36 |
37 | ### Patch Changes
38 |
39 | - feat: add secure mode to debug info
40 | - Updated dependencies
41 | - @dotenv-run/core@1.3.1
42 |
43 | ## 1.3.0
44 |
45 | ### Minor Changes
46 |
47 | - refactor and docs initialization
48 |
49 | ### Patch Changes
50 |
51 | - Updated dependencies
52 | - @dotenv-run/core@1.3.0
53 |
54 | ## 1.2.3
55 |
56 | ### Patch Changes
57 |
58 | - feat(core): support sub-module level turbo.json
59 | - Updated dependencies
60 | - @dotenv-run/core@1.2.3
61 |
62 | ## 1.2.2
63 |
64 | ### Patch Changes
65 |
66 | - fix(core): filter out undefined env values
67 | - Updated dependencies
68 | - @dotenv-run/core@1.2.2
69 |
70 | ## 1.2.1
71 |
72 | ### Patch Changes
73 |
74 | - refactor(esbuild): usde esbuild define option
75 | - Updated dependencies
76 | - @dotenv-run/core@1.2.1
77 |
78 | ## 1.2.0
79 |
80 | ### Minor Changes
81 |
82 | - f63ecac: feat: add esbuild plugin
83 |
84 | ### Patch Changes
85 |
86 | - Updated dependencies [f63ecac]
87 | - @dotenv-run/core@1.2.0
88 |
89 | ## 1.1.1
90 |
91 | ### Patch Changes
92 |
93 | - cea8c35: fix(rollup): upgrade rollup peerdep
94 |
95 | ## 1.1.0
96 |
97 | ### Minor Changes
98 |
99 | - af82054: feat: add cjs format and doc
100 |
101 | ### Patch Changes
102 |
103 | - Updated dependencies [af82054]
104 | - @dotenv-run/core@1.1.0
105 |
106 | ## 1.0.1
107 |
108 | ### Patch Changes
109 |
110 | - 429d699: refactor(webpack): export dotenv results
111 |
112 | ## 1.0.0
113 |
114 | ### Major Changes
115 |
116 | - feat: add bundler plugins
117 |
118 | ### Patch Changes
119 |
120 | - Updated dependencies
121 | - @dotenv-run/core@1.0.0
122 |
--------------------------------------------------------------------------------
/packages/rollup/README.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/rollup
2 |
3 | - ✅ Load environment variables from the command line `API_BASE=/v1/ rollup`
4 | - ✅ Load environment variables from `.env` files
5 | - ✅ Expand environment variables `API_URL=$API_BASE/users`
6 | - ✅ Define environment variables for a specific environment (e.g. `.env.production`)
7 | - ✅ Load priorities of `.env.*` files (e.g. `.env.production` > `.env`)
8 | - ✅ Hierarchical cascading configuration in monorepo projects ([Nx](https://nx.dev), [Turbo](https://turborepo.com/), etc.)
9 | `apps/next-app/.env` > `apps/.env` > `.env`
10 |
11 | ## Install
12 |
13 | ```sh
14 | npm add @dotenv-run/rollup --save-dev
15 | ```
16 |
17 | ## Usage
18 |
19 | Create a `rollup.config.js` [configuration file](https://www.rollupjs.org/guide/en/#configuration-files) and import the plugin:
20 |
21 | ```js
22 | import env from "@dotenv-run/rollup";
23 |
24 | export default {
25 | input: "src/index.js",
26 | output: {
27 | file: "dist/index.js",
28 | },
29 | plugins: [env({ prefix: "API", verbose: true, root: "../../.." })],
30 | };
31 | ```
32 |
33 | Then call `rollup` either via the [CLI](https://www.rollupjs.org/guide/en/#command-line-reference) or the [API](https://www.rollupjs.org/guide/en/#javascript-api).
34 |
--------------------------------------------------------------------------------
/packages/rollup/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/rollup",
3 | "version": "1.3.6",
4 | "description": "Run your scripts with dotenv variables",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "dist/index.js",
7 | "types": "dist/index.d.ts",
8 | "type": "module",
9 | "scripts": {
10 | "dev": "tsc -w",
11 | "build": "tsc"
12 | },
13 | "files": [
14 | "dist",
15 | "README.md"
16 | ],
17 | "keywords": [
18 | "dotenv",
19 | "run",
20 | "cli"
21 | ],
22 | "author": "Chihab Otmani ",
23 | "license": "ISC",
24 | "dependencies": {
25 | "@dotenv-run/core": "workspace:^1.3.6",
26 | "@rollup/plugin-replace": "^5.0.7"
27 | },
28 | "peerDependencies": {
29 | "rollup": "^3.0.0"
30 | },
31 | "devDependencies": {
32 | "@types/node": "^16.18.112",
33 | "rollup": "^3.29.5"
34 | }
35 | }
36 |
--------------------------------------------------------------------------------
/packages/rollup/src/index.ts:
--------------------------------------------------------------------------------
1 | import { type DotenvRunOptions, env } from "@dotenv-run/core";
2 | import replace from "@rollup/plugin-replace";
3 | import { Plugin } from "rollup";
4 |
5 | const dotenvRun = (options: DotenvRunOptions): Plugin => {
6 | const { full } = env(options);
7 | return {
8 | name: "dotenv-run",
9 | ...replace({
10 | preventAssignment: true,
11 | values: full,
12 | }),
13 | };
14 | }
15 |
16 | export { dotenvRun, DotenvRunOptions };
17 | export default dotenvRun;
18 |
--------------------------------------------------------------------------------
/packages/rollup/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "module": "ES2022",
7 | "strict": true,
8 | "allowSyntheticDefaultImports": true,
9 | "forceConsistentCasingInFileNames": true,
10 | "strictPropertyInitialization": false,
11 | "strictNullChecks": false,
12 | "pretty": true,
13 | "sourceMap": true,
14 | "declaration": true,
15 | "skipLibCheck": true
16 | },
17 | "exclude": ["node_modules"],
18 | "compileOnSave": false,
19 | "buildOnSave": false
20 | }
21 |
--------------------------------------------------------------------------------
/packages/rspack/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/rspack",
3 | "version": "1.0.0",
4 | "description": "Run your scripts with dotenv variables",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "dist/cjs/index.js",
7 | "module": "dist/esm/index.js",
8 | "types": "dist/index.d.ts",
9 | "scripts": {
10 | "dev": "tsc -w",
11 | "build": "concurrently npm:build:*",
12 | "build:esm": "tsc --module esnext --outDir dist/esm",
13 | "build:cjs": "tsc --module commonjs --outDir dist/cjs",
14 | "build:types": "tsc --emitDeclarationOnly --declaration --declarationMap --module esnext --outDir dist"
15 | },
16 | "files": [
17 | "dist",
18 | "README.md"
19 | ],
20 | "keywords": [
21 | "dotenv",
22 | "run",
23 | "cli"
24 | ],
25 | "author": "Chihab Otmani ",
26 | "license": "ISC",
27 | "dependencies": {
28 | "@dotenv-run/core": "workspace:^1.3.5"
29 | },
30 | "peerDependencies": {
31 | "@rspack/core": "^1.0.0"
32 | },
33 | "devDependencies": {
34 | "@types/node": "^16.18.101",
35 | "@rspack/core": "^1.0.4"
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/packages/rspack/src/index.ts:
--------------------------------------------------------------------------------
1 | import { type DotenvRunOptions, type Dict, env } from "@dotenv-run/core";
2 | import type { RspackPluginInstance, Compiler } from "@rspack/core";
3 | import { DefinePlugin } from "@rspack/core";
4 |
5 | class DotenvRunPlugin implements RspackPluginInstance {
6 | public raw: Dict = {};
7 | public full: Dict = {};
8 | public stringified: Dict = {};
9 |
10 | constructor(options: DotenvRunOptions, private ssr = false) {
11 | const { full, stringified, raw } = env(options);
12 | this.raw = raw;
13 | this.full = full;
14 | this.stringified = stringified;
15 | }
16 |
17 | apply(compiler: Compiler) {
18 | const definePlugin = new DefinePlugin(
19 | this.ssr
20 | ? { ...this.full }
21 | : {
22 | "process.env": this.stringified,
23 | "import.meta.env": this.stringified,
24 | "import.meta.env.NODE_ENV": JSON.stringify(process.env.NODE_ENV),
25 | }
26 | );
27 | definePlugin.apply(compiler);
28 | }
29 | }
30 |
31 | export { DotenvRunOptions, DotenvRunPlugin };
32 |
33 | export default DotenvRunPlugin;
34 |
--------------------------------------------------------------------------------
/packages/rspack/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "module": "ES2022",
7 | "strict": true,
8 | "allowSyntheticDefaultImports": true,
9 | "forceConsistentCasingInFileNames": true,
10 | "strictPropertyInitialization": false,
11 | "strictNullChecks": false,
12 | "pretty": true,
13 | "sourceMap": true,
14 | "declaration": true,
15 | "skipLibCheck": true
16 | },
17 | "exclude": ["node_modules"],
18 | "compileOnSave": false,
19 | "buildOnSave": false
20 | }
21 |
--------------------------------------------------------------------------------
/packages/vite/README.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/vite
2 |
3 | - ✅ Load environment variables from the command line `API_BASE=/v1/ vite`
4 | - ✅ Load environment variables from `.env` files
5 | - ✅ Expand environment variables `API_URL=$API_BASE/users`
6 | - ✅ Define environment variables for a specific environment (e.g. `.env.production`)
7 | - ✅ Load priorities of `.env.*` files (e.g. `.env.production` > `.env`)
8 | - ✅ Hierarchical cascading configuration in monorepo projects ([Nx](https://nx.dev), [Turbo](https://turborepo.com/), etc.)
9 | `apps/next-app/.env` > `apps/.env` > `.env`
10 |
11 | ## Install
12 |
13 | ```sh
14 | npm add @dotenv-run/vite --save-dev
15 | ```
16 |
17 | ## Usage
18 |
19 | Create a `vite.config.js` [configuration file](https://vite.dev/config) and import the plugin:
20 |
21 | ```js
22 | import env from "@dotenv-run/vite";
23 |
24 | export default {
25 | envPrefix: 'MY_PREFIX_',
26 | envDir: './my-env-directory',
27 | plugins: [env()],
28 | };
29 | ```
30 |
31 | Then call `vite` or `vite build` either via the [CLI](https://vite.dev/guide/cli.html).
32 |
33 | The available options are similar to those supported by [`@dotenv-run/core`](https://www.npmjs.com/package/@dotenv-run/core), but this plugin seamlessly integrates with Vite by automatically deriving the root, prefix, and environment values from its standard configuration, ensuring a more cohesive experience. For more details, refer to the API section.
34 |
--------------------------------------------------------------------------------
/packages/vite/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/vite",
3 | "version": "1.0.0",
4 | "description": "Run your scripts with dotenv variables",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "dist/index.js",
7 | "types": "dist/index.d.ts",
8 | "type": "module",
9 | "scripts": {
10 | "dev": "tsc -w",
11 | "build": "tsc"
12 | },
13 | "files": [
14 | "dist",
15 | "README.md"
16 | ],
17 | "keywords": [
18 | "dotenv",
19 | "run",
20 | "cli",
21 | "vite",
22 | "vite-plugin"
23 | ],
24 | "author": "Iacopo Ciao ",
25 | "license": "ISC",
26 | "dependencies": {
27 | "@dotenv-run/core": "workspace:^1.3.6",
28 | "@rollup/plugin-replace": "^5.0.7",
29 | "lodash-es": "^4.17.21",
30 | "vite": "^6.2.0"
31 | },
32 | "devDependencies": {
33 | "@types/lodash-es": "^4.17.12",
34 | "@types/node": "^16.18.112"
35 | }
36 | }
--------------------------------------------------------------------------------
/packages/vite/src/constants.ts:
--------------------------------------------------------------------------------
1 | export const DEFAULT_PREFIX = 'VITE_';
2 |
3 | export const DEFAULT_ENV_FILES = [
4 | /** vault file */ `.env.vault`,
5 | /** default file */ `.env`,
6 | ];
7 |
--------------------------------------------------------------------------------
/packages/vite/src/index.ts:
--------------------------------------------------------------------------------
1 | import { env as loadEnv } from "@dotenv-run/core";
2 | import { Plugin } from "vite";
3 | import { viteEnvPrefixToPrefix } from "./mapper.js";
4 | import { sanitizeOptions, ViteDotenvRunOptions } from "./options.js";
5 | import replace from "@rollup/plugin-replace";
6 | import { DEFAULT_ENV_FILES } from "./constants.js";
7 |
8 | /**
9 | * Vite plugin to load environment variables from .env files using `@dotenv-run/core`.
10 | *
11 | * This plugin seamlessly integrates with Vite by automatically deriving the root,
12 | * prefix and environment options from Vite's `envDir`, `envPrefix` and `mode`,
13 | * ensuring a more cohesive experience.
14 | *
15 | * @param {ViteDotenvRunOptions} [options] - Options for configuring the plugin.
16 | * See {@link ViteDotenvRunOptions} for more details.
17 | *
18 | * @returns {Plugin} Vite plugin object that enhances the Vite configuration.
19 | *
20 | * @example
21 | * // Usage in a Vite config file
22 | * import dotenvRun from 'vite-plugin-dotenv-run';
23 | *
24 | * export default {
25 | * envDir: '../..',
26 | * envPrefix: ['VITE_', 'CUSTOM_'],
27 | * plugins: [
28 | * dotenvRun(),
29 | * ],
30 | * };
31 | */
32 | const dotenvRun = (options?: ViteDotenvRunOptions): Plugin => {
33 | options = sanitizeOptions(options);
34 | const files = options?.files ?? DEFAULT_ENV_FILES;
35 |
36 | return {
37 | name: "vite-plugin-dotenv-run",
38 | config: (config, configEnv) => {
39 | const prefix = viteEnvPrefixToPrefix(config.envPrefix);
40 |
41 | const { full } = loadEnv({
42 | files,
43 | prefix,
44 | root: config.envDir,
45 | environment: configEnv.mode,
46 | ...options,
47 | });
48 |
49 | return {
50 | ...config,
51 | ...replace({
52 | preventAssignment: true,
53 | values: full,
54 | }),
55 | };
56 | },
57 | };
58 | };
59 |
60 | export { dotenvRun, ViteDotenvRunOptions };
61 | export default dotenvRun;
62 |
--------------------------------------------------------------------------------
/packages/vite/src/mapper.ts:
--------------------------------------------------------------------------------
1 | import {
2 | castArray,
3 | escapeRegExp,
4 | first,
5 | isEmpty,
6 | isNil,
7 | negate,
8 | } from "lodash-es";
9 | import { DEFAULT_PREFIX } from "./constants.js";
10 |
11 | /**
12 | * Converts a Vite `envPrefix` configuration value into a usable prefix or RegExp for @dotenv-run/core.
13 | *
14 | * @param {string | string[] | undefined} prefixes - The prefix or list of prefixes to filter environment variables.
15 | * @returns {string | RegExp} - A single prefix as a string if only one is provided, or a RegExp if multiple prefixes are given.
16 | *
17 | * @throws {Error} If an empty string (`''`) is included in the prefixes, as this could expose all environment variables.
18 | *
19 | * @example
20 | * viteEnvPrefixToPrefix("VITE_") // Returns: "VITE_"
21 | * viteEnvPrefixToPrefix(["VITE_", "CUSTOM_"]) // Returns: /^VITE_|CUSTOM_/
22 | * viteEnvPrefixToPrefix(undefined) // Returns: DEFAULT_PREFIX
23 | *
24 | * @see {@link https://vite.dev/config/shared-options.html#envprefix Vite Documentation on envPrefix}
25 | *
26 | * @security
27 | * The `envPrefix` option should **never** be set to an empty string (`''`),
28 | * as this will expose **all** environment variables, potentially leaking sensitive information.
29 | * Vite has a built-in safeguard that throws an error when detecting `''` as a prefix.
30 | *
31 | * If you need to expose an unprefixed environment variable, use the `define` option instead:
32 | *
33 | * ```
34 | * define: {
35 | * "process.env.MY_VAR": JSON.stringify(process.env.MY_VAR)
36 | * }
37 | * ```
38 | */
39 | export const viteEnvPrefixToPrefix = (
40 | prefixes: string | string[] | undefined
41 | ): string | RegExp => {
42 | prefixes = castArray(prefixes).filter(negate(isNil));
43 |
44 | if (isEmpty(prefixes)) {
45 | return DEFAULT_PREFIX;
46 | }
47 |
48 | if (prefixes.includes("")) {
49 | throw new Error(
50 | `envPrefix option contains value '', which could lead unexpected exposure of sensitive information.`
51 | );
52 | }
53 |
54 | if (prefixes.length === 1) {
55 | return first(prefixes);
56 | }
57 |
58 | return new RegExp(`^(${prefixes.map(escapeRegExp).join("|")})`);
59 | };
60 |
--------------------------------------------------------------------------------
/packages/vite/src/options.ts:
--------------------------------------------------------------------------------
1 | import type { DotenvRunOptions } from "@dotenv-run/core";
2 | import { pick } from "lodash-es";
3 |
4 | /**
5 | * Options for configuring the @dotenv-run/vite plugin.
6 | *
7 | * @interface ViteDotenvRunOptions
8 | * @extends {Pick}
9 | *
10 | * @property {DotenvConfigOptions} [dotenv] - Options for configuring dotenv.
11 | * @property {string[]} [files] - Environment files to load. Defaults to `['.env.vault', '.env']`.
12 | * @property {boolean} [unsecure] - Display environment variables in debug output.
13 | * @property {boolean} [nodeEnv] - Node environment.
14 | * @property {boolean} [verbose] - Print verbose output.
15 | * @property {Dict} [builtIn] - Built-in environment variables.
16 | * @property {boolean} [runtime] - Whether to use runtime variables.
17 | * @property {string} [global] - Global variable name.
18 | */
19 | export type ViteDotenvRunOptions = Pick;
20 |
21 | export const sanitizeOptions = (options?: T): ViteDotenvRunOptions | undefined => {
22 | return pick(options, 'verbose', 'unsecure', 'builtIn', 'global', 'nodeEnv', 'runtime', 'dotenv', 'files');
23 | }
--------------------------------------------------------------------------------
/packages/vite/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "module": "ES2022",
7 | "strict": true,
8 | "allowSyntheticDefaultImports": true,
9 | "forceConsistentCasingInFileNames": true,
10 | "strictPropertyInitialization": false,
11 | "strictNullChecks": false,
12 | "pretty": true,
13 | "sourceMap": true,
14 | "declaration": true,
15 | "skipLibCheck": true
16 | },
17 | "exclude": ["node_modules"],
18 | "compileOnSave": false,
19 | "buildOnSave": false
20 | }
21 |
--------------------------------------------------------------------------------
/packages/webpack/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/webpack
2 |
3 | ## 1.5.0
4 |
5 | ### Minor Changes
6 |
7 | - 8f83f0c: feat: add compatibility with Angular 19
8 |
9 | ## 1.4.1
10 |
11 | ### Patch Changes
12 |
13 | - chore: use pnpm workspace protocol for dependencies
14 | - Updated dependencies
15 | - @dotenv-run/core@1.3.6
16 |
17 | ## 1.4.0
18 |
19 | ### Minor Changes
20 |
21 | - bump up webpack and esbuild versions
22 |
23 | ## 1.3.4
24 |
25 | ### Patch Changes
26 |
27 | - docs: updates packages' README files
28 | - Updated dependencies
29 | - @dotenv-run/core@1.3.4
30 |
31 | ## 1.3.3
32 |
33 | ### Patch Changes
34 |
35 | - fix(cli): fix unsecure mode alias
36 | - Updated dependencies
37 | - @dotenv-run/core@1.3.3
38 |
39 | ## 1.3.2
40 |
41 | ### Patch Changes
42 |
43 | - feat(angular): add unsecure mode option
44 | - Updated dependencies
45 | - @dotenv-run/core@1.3.2
46 |
47 | ## 1.3.1
48 |
49 | ### Patch Changes
50 |
51 | - feat: add secure mode to debug info
52 | - Updated dependencies
53 | - @dotenv-run/core@1.3.1
54 |
55 | ## 1.3.0
56 |
57 | ### Minor Changes
58 |
59 | - refactor and docs initialization
60 |
61 | ### Patch Changes
62 |
63 | - Updated dependencies
64 | - @dotenv-run/core@1.3.0
65 |
66 | ## 1.2.3
67 |
68 | ### Patch Changes
69 |
70 | - feat(core): support sub-module level turbo.json
71 | - Updated dependencies
72 | - @dotenv-run/core@1.2.3
73 |
74 | ## 1.2.2
75 |
76 | ### Patch Changes
77 |
78 | - fix(core): filter out undefined env values
79 | - Updated dependencies
80 | - @dotenv-run/core@1.2.2
81 |
82 | ## 1.2.1
83 |
84 | ### Patch Changes
85 |
86 | - refactor(esbuild): usde esbuild define option
87 | - Updated dependencies
88 | - @dotenv-run/core@1.2.1
89 |
90 | ## 1.2.0
91 |
92 | ### Minor Changes
93 |
94 | - f63ecac: feat: add esbuild plugin
95 |
96 | ### Patch Changes
97 |
98 | - Updated dependencies [f63ecac]
99 | - @dotenv-run/core@1.2.0
100 |
101 | ## 1.1.0
102 |
103 | ### Minor Changes
104 |
105 | - af82054: feat: add cjs format and doc
106 |
107 | ### Patch Changes
108 |
109 | - Updated dependencies [af82054]
110 | - @dotenv-run/core@1.1.0
111 |
112 | ## 1.0.1
113 |
114 | ### Patch Changes
115 |
116 | - 429d699: refactor(webpack): export dotenv results
117 |
118 | ## 1.0.0
119 |
120 | ### Major Changes
121 |
122 | - feat: add bundler plugins
123 |
124 | ### Patch Changes
125 |
126 | - Updated dependencies
127 | - @dotenv-run/core@1.0.0
128 |
--------------------------------------------------------------------------------
/packages/webpack/README.md:
--------------------------------------------------------------------------------
1 | # @dotenv-run/webpack
2 |
3 | - ✅ Load environment variables from the command line `API_BASE=/v1/ webpack`
4 | - ✅ Load environment variables from `.env` files
5 | - ✅ Expand environment variables `API_URL=$API_BASE/users`
6 | - ✅ Define environment variables for a specific environment (e.g. `.env.production`)
7 | - ✅ Load priorities of `.env.*` files (e.g. `.env.production` > `.env`)
8 | - ✅ Hierarchical cascading configuration in monorepo projects ([Nx](https://nx.dev), [Turbo](https://turborepo.com/), etc.)
9 | `apps/next-app/.env` > `apps/.env` > `.env`
10 |
11 | ## Install
12 |
13 | ```console
14 | npm add @dotenv-run/webpack --save-dev
15 | ```
16 |
17 | ## Usage
18 |
19 | Create a `webpack.config.js` [configuration file](https://www.webpackjs.org/guide/en/#configuration-files) and import the plugin:
20 |
21 | ```js
22 | import { DotenvRunPlugin } from "@dotenv-run/webpack";
23 | import path from "path";
24 |
25 | const __dirname = path.resolve();
26 |
27 | export default {
28 | entry: "./src/index.js",
29 | output: {
30 | filename: "main.js",
31 | path: path.resolve(__dirname, "dist"),
32 | },
33 | plugins: [
34 | new DotenvRunPlugin(
35 | { prefix: "API", verbose: true, root: "../../.." },
36 | __dirname
37 | ),
38 | ],
39 | };
40 | ```
41 |
--------------------------------------------------------------------------------
/packages/webpack/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@dotenv-run/webpack",
3 | "version": "1.5.0",
4 | "description": "Run your scripts with dotenv variables",
5 | "homepage": "https://github.com/chihab/dotenv-run",
6 | "main": "dist/cjs/index.js",
7 | "module": "dist/esm/index.js",
8 | "types": "dist/index.d.ts",
9 | "scripts": {
10 | "dev": "tsc -w",
11 | "build": "concurrently npm:build:*",
12 | "build:esm": "tsc --module esnext --outDir dist/esm",
13 | "build:cjs": "tsc --module commonjs --outDir dist/cjs",
14 | "build:types": "tsc --emitDeclarationOnly --declaration --declarationMap --module esnext --outDir dist"
15 | },
16 | "files": [
17 | "dist",
18 | "README.md"
19 | ],
20 | "keywords": [
21 | "dotenv",
22 | "run",
23 | "cli"
24 | ],
25 | "author": "Chihab Otmani ",
26 | "license": "ISC",
27 | "dependencies": {
28 | "@dotenv-run/core": "workspace:^1.3.6"
29 | },
30 | "peerDependencies": {
31 | "webpack": "^5.0.0"
32 | },
33 | "devDependencies": {
34 | "@types/node": "^16.18.112",
35 | "webpack": "5.96.1"
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/packages/webpack/src/index.ts:
--------------------------------------------------------------------------------
1 | import { type DotenvRunOptions, type Dict, env } from "@dotenv-run/core";
2 | import type { WebpackPluginInstance, Compiler } from "webpack";
3 | import { DefinePlugin } from "webpack";
4 |
5 | class DotenvRunPlugin implements WebpackPluginInstance {
6 | public raw: Dict = {};
7 | public full: Dict = {};
8 | public stringified: Dict = {};
9 |
10 | constructor(options: DotenvRunOptions, private ssr = false) {
11 | const { full, stringified, raw } = env(options);
12 | this.raw = raw;
13 | this.full = full;
14 | this.stringified = stringified;
15 | }
16 |
17 | apply(compiler: Compiler) {
18 | const definePlugin = new DefinePlugin(
19 | this.ssr
20 | ? { ...this.full }
21 | : {
22 | "process.env": this.stringified,
23 | "import.meta.env": this.stringified,
24 | "import.meta.env.NODE_ENV": JSON.stringify(process.env.NODE_ENV),
25 | }
26 | );
27 | definePlugin.apply(compiler);
28 | }
29 | }
30 |
31 | export { DotenvRunOptions, DotenvRunPlugin };
32 |
33 | export default DotenvRunPlugin;
34 |
--------------------------------------------------------------------------------
/packages/webpack/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "include": ["src"],
3 | "compilerOptions": {
4 | "outDir": "dist",
5 | "moduleResolution": "node",
6 | "module": "ES2022",
7 | "strict": true,
8 | "forceConsistentCasingInFileNames": true,
9 | "strictPropertyInitialization": false,
10 | "strictNullChecks": false,
11 | "pretty": true,
12 | "sourceMap": true,
13 | "declaration": true,
14 | "skipLibCheck": true
15 | },
16 | "exclude": ["node_modules"],
17 | "compileOnSave": false,
18 | "buildOnSave": false
19 | }
20 |
--------------------------------------------------------------------------------
/pnpm-workspace.yaml:
--------------------------------------------------------------------------------
1 | packages:
2 | - "examples/nx-workspace-old"
3 | - "examples/nx-workspace-old/**/*"
4 | - "packages/*"
5 | - "docs"
6 |
--------------------------------------------------------------------------------
/turbo.json:
--------------------------------------------------------------------------------
1 | {
2 | "$schema": "https://turborepo.com/schema.json",
3 | "pipeline": {
4 | "build": {
5 | "dependsOn": [
6 | "^build"
7 | ],
8 | "outputs": [
9 | "dist"
10 | ]
11 | },
12 | "test": {
13 | "dependsOn": [
14 | "^test"
15 | ]
16 | },
17 | "dev": {
18 | "dependsOn": [
19 | "^dev"
20 | ]
21 | }
22 | }
23 | }
24 |
--------------------------------------------------------------------------------