According to these docs:
Next.js allows you to set defaults in
.env(all environments)
Further down on the same page:
Apart from
developmentandproductionenvironments, there is a 3rd option available:test. In the same way you can set defaults for development or production environments, you can do the same with.env.testfile for testing environment
But variables in .env and .env.test are not being loaded when running tests.
Basic setup and .env:
create-next-app -e with-jest and enter a namecd <name>echo MY_VAR=my_value >.envnpm run test:ci -- envThe test fails: process.env.MY_VAR is undefined.
.env.test:
mv .env .env.testnpm run test:ci -- envThe test fails: process.env.MY_VAR is undefined.
The test should pass in both situations (with the file named either .env or .env.test). At least, if I'm understanding the docs correctly and I'm not doing anything silly.
As of v9.5.5, you can just do
import { loadEnvConfig } from '@next/env'
export default async () => {
loadEnvConfig(process.env.PWD)
}
if you add that your jest setup (e.g. globalSetup), should be good to go
So the docs are out of date?
So the docs are out of date?
maybe, 9.5.5 is only out a few days
Well the problem also exists on 9.5.4. It's either an application bug or a documentation bug regardless, unless I have something wrong.
Next.js does not set up your test environment currently so it can't load environment variables for you. You can boot up the Next.js server though which loads the environment variables:
const next = require('next')
// `.env` / `.env.test` is loaded during initialization.
const app = next()
I too have just noticed this. NODE_ENV is set to to test, but when running Jest unit tests the .env.test file is not loaded. The docs do indicate that they should.
As per @erkde comment, I have fixed this with by loading the env files in jest.config.js
const { loadEnvConfig } = require('@next/env')
loadEnvConfig(process.env.PWD)
A documentation bug then.
Regarding booting Next, do you suggest doing that globally (such as in jest config) or per test file which needs it?
For my purposes, it made sense to make the change globally as I had an env var that disables auth checks during tests.
The loading if .env.test does work for my Cypress tests as documented
But only after booting Next, right? That ought to be documented.
Sorry, what do you mean by 'booting Next'?
As above in @timneutkens's comment:
You can boot up the Next.js server though which loads the environment variables:
const next = require('next')
Ah. Sorry, I didn't seem to need this step. Programmatically setting the env vars using loadEnvConfig was enough
Right, so it sounds like either loadEnvConfig or require('next') get the vars loaded up. Just saying that the docs should mention this when it talks about env vars for tests.
My temporary workaround has been to add a global setup file in my Jest configuration:
/**
* @file jest.config.js
*/
module.exports = {
globalSetup: '<rootDir>/test/setup.ts',
};
and to load a particular environment configuration with dotenv:
/**
* @file test/setup.ts
*/
import dotenv from 'dotenv';
dotenv.config({ path: '.env.test' });
I know it doesn't solve the problem, but hopefully it can be helpful in the meantime.
Also, you may be able to run dotenv.config(...) with multiple paths to load in a few configs (please note I have not tested this):
dotenv.config({ path: '.env' });
dotenv.config({ path: '.env.test' });
My workaround was actually simpler (but arguably worse) since I only need
two very specific things set: I forego the .env files for test purposes and
just directly set process.env.whatever = "whatever" in the setup file. Does
the trick.
I needed the .env.test file loaded for both Jest and out Cypress integration tests. My workaround was to use https://www.npmjs.com/package/dotenv-load which behaves as expected.