Adam
Adam

Reputation: 549

share env variable beween turborepo monorepo project

I ve setup a basic turborepo project and I want to share .env variables across the all the apps and some of packages. If I set one .env file in the root of project and how can all apps and packages access them. Or for my requirement do I need to set multiple .env files in all apps and packages?

Upvotes: 24

Views: 25623

Answers (8)

Chris Josh
Chris Josh

Reputation: 475

Following turbo docs - Using environment variables

Steps:

  1. Add dotenv-cli to the project root.
# Installs dotenv-cli in the root workspace
yarn add dotenv-cli --ignore-workspace-root-check
  1. Update the root script (what runs your project with turbo), in my case "dev"
"scripts": {
    "dev": "dotenv -- turbo run dev",
    ...
}   

you may leave the turbo default globalDependencies setup in turbo.json

"globalDependencies": ["**/.env.*local"]

Optional:

  1. If you have a CRA, create a .env.local in the CRA app root and expand the variable

in workspace root .env:

VARIABLE=value

in CRA root .env.local:

REACT_APP_VARIABLE=${VARIABLE}

Restart server.

Upvotes: 4

prakhar tomar
prakhar tomar

Reputation: 1125

  1. Add dotenv-cli, in your project root
npm add -D dotenv-cli
  1. update script
"dev": "dotenv -- turbo run dev",
  1. Add .env file to the project root

From Docs

Upvotes: 1

chihab
chihab

Reputation: 41

This package @dotenv-run/cli might help.

.env.* files can be defined in the root workspace and overriden by each application

/workspace
 apps
    frontend1
       .env.local # API_USERS=http://localhost:3001/users
       src/
.env.dev # API_BASE=https://dotenv-run.dev
.env.prod # API_BASE=https://dotenv-run.app
.env # API_USERS=$API_BASE/api/v1/users API_AUTH=https://$API_BASE/auth
package.json
turbo.json
$> cd /workspace/apps/frontend1
$> NODE_ENV=dev dotenv-run -- bash -c 'printf "✨API_USERS $API_USERS\n✨ API_AUTH $API_AUTH"'
✔ /workspace/apps/frontend1/.env.local
✔ /workspace/.env.dev
✔ /workspace/.env
✨ API_USERS http://localhost:3001/users
✨ API_AUTH https://dotenv-run.dev/api/v1/auth

Upvotes: 1

ewulff
ewulff

Reputation: 2259

As of December'22, the recommended way of doing this as per the official turbo docs is as follows:

  1. cd root-directory-of-your-project.
  2. npm add -D dotenv-cli (or with pnpm: pnpm add -D dotenv-cli -w).
  3. Create a .env file in the root directory of your project.
    • Add your .env to your project's root .gitignore.
  4. Add your variables to the newly created .env file.
    • If you are using nextjs remember to prefix your public variables with NEXT_PUBLIC_* (example: NEXT_PUBLIC_GOOGLE_ANALYTICS_TOKEN=1234).
  5. On your turbo.json file, add the variables on which each pipeline job depends.
    • Example:
    {
      "$schema": "https://turborepo.org/schema.json",
      "pipeline": {
        "dev:frontend": {
          "outputs": ["dist/**", ".next/**"],
          "env": ["NEXT_PUBLIC_GOOGLE_ANALYTICS_TOKEN"]
        },
        "dev:backend": {
          "outputs": ["dist/**", ".next/**"],
          "env": ["DATABASE_URL"]
        }
      }
    }
    
  6. Restart your local development server. Try logging process.env.NEXT_PUBLIC_GOOGLE_ANALYTICS_TOKEN.

Once finished, the structure of the project should look similar to the following:

apps
    backend     <<< Your backend code. You don't need to keep any .env file here.
    frontend    <<< Your frontend code. You don't need to keep any .env file here.
package.json    <<< Where you should install dotenv-cli as a dev dependency.
turbo.json      <<< Where pipeline jobs and their dependencies on environment variables are specified.
.env            <<< Where all your environment variables will be stored.

Upvotes: 15

Marco Cesarato
Marco Cesarato

Reputation: 11

The globalDependencies mentioned on the other answers is like the docs says:

A list of file globs for implicit global hash dependencies. The contents of these files will be included in the global hashing algorithm and affect the hashes of all tasks. This is useful for busting the cache based on .env files (not in Git) or any root level file that impacts workspace tasks

So, it's needed to cache that specific task, build etc... on turbo caching but not to load it on the application.

To load env variables from a centralized .env file into multiple processes, you may use my new package https://www.npmjs.com/package/dotenv-mono, which was designed specifically for this purpose.

  1. Install dotenv-mono (yarn add dotenv-mono or npm install dotenv-mono --save)

  2. Place your .env file in the root of your project

  3. Then load it as follows on your packages/applications init file (index.{js,ts}, next.config.js, etc...):

    require("dotenv-mono").load();
    

Check out the github page for more documentation https://github.com/marcocesarato/dotenv-mono

Upvotes: 1

matsko
matsko

Reputation: 22193

I've found this approach to work.

  1. Install env-cmd (yarn install env-cmd)
  2. Make a shell script called turbo-run.sh that does the following:
# remember to use direct paths to files because yarn has a habit
# of stripping out `--` flags (which are used in turborepo to pass
# in extra args to turbo commands)
./node_modules/.bin/env-cmd \
  --file $ENV_FILE \
    ./node_modules/.bin/turbo run \
      $@

(also chmod +x it so that you can execute it)

  1. Then setup your package.json scripts to have a turbo-run command that calls ./turbo-run.sh
  2. Now you can do yarn turbo-run foo and ensure that it always calls env-cmd with the appropriate ENV_FILE file.

Upvotes: 0

Kevin K.
Kevin K.

Reputation: 650

To load the env variables from .env into the process env you can use https://www.npmjs.com/package/dotenv.

Then to share the env variables in your monorepo :

In each workspace/app add require('dotenv').config({path: /custom/path/to/.env}) (assuming common js module resolution here) as early as possible as per docs (meaning e.g. for a next js app in next.config.js), where /custom/path/to/.env would be the relative path to your root .env (e.g. two folders up:../../.env)

Upvotes: 2

hanshs
hanshs

Reputation: 49

You can specify the globalDependencies option in your turbo config or use the --global-deps CLI flag.

{ 
   // ... rest of the turbo config
   globalDependencies: ['.env']
}

or

turbo run build --global-deps=".env.*"

References from docs:

https://turborepo.org/docs/reference/configuration#globaldependencies https://turborepo.org/docs/reference/command-line-reference#--global-deps

Upvotes: 0

Related Questions