LeCoda
LeCoda

Reputation: 1026

How to load environment variable in tests with Next.js?

I'm trying to run a simple test with JavaScript as below.

import React from 'react';
import Customization from 'components/onboarding/customization';
import '@testing-library/jest-dom';
import { render, screen, fireEvent } from '@testing-library/react';

describe('customization render', () => {
  it('should render the Hero page with no issue', () => {
    render(<Customization />);

    const heading = screen.getByText(
      /All the Moodmap at one place!/i
    );

    expect(heading).toBeInTheDocument();
  });
  it("should call onCLick method on click", () => {
    const mockOnClick = jest.fn()

    const {container} = render(<Customization />);

    const button = getByTestId(container, 'alreadyDownloaded');
    fireEvent.click(button);
    expect(mockOnClick).toHaveBeenCalledTimes(1)


    // const mockOnClick = jest.fn()
    // const utils = render(<Customization onClick={mockOnClick} />)
    // fireEvent.click(screen.getByText(/already downloaded ⟶/i))
    // expect(mockOnClick).toHaveBeenCalledTimes(1)
  })
});

When running the tests I'm getting this error

No google analytics trackingId defined

   8 |   debug: process.env.NODE_ENV !== 'production',
   9 |   plugins: [
> 10 |     googleAnalyticsPlugin({
     |     ^
  11 |       trackingId: process.env.NEXT_PUBLIC_GA_TRACKING_ID,
  12 |     }),

How do I make this error go away - surely it shouldn't require Google Analytics code given the above, it's not in production when running the test?

Update

So I need to make sure the .env file is being loaded!

In my package.json I've got this Jest setup:

"jest": {
    "testMatch": [
      "**/?(*.)(spec|test).?(m)js?(x)"
    ],
    "moduleNameMapper": {
      "\\.(css|less|scss)$": "identity-obj-proxy"
    },
    "moduleDirectories": [
      "node_modules",
      "src"
    ],
    "rootDir": "src",
    "moduleFileExtensions": [
      "js",
      "jsx",
      "mjs"
    ],
    "transform": {
      "^.+\\.m?jsx?$": "babel-jest"
    },
    "coverageThreshold": {
      "global": {
        "branches": 80,
        "functions": 80,
        "lines": 80,
        "statements": -10
      }
    }
  },

updated code to use jest.setup - can't get env to load

So

import { configure } from 'enzyme';
import Adapter from 'enzyme-adapter-react-16';
import "@testing-library/jest-dom";

configure({
    adapter: new Adapter()
});

module.exports = {
  testMatch: [
    "**/?(*.)(spec|test).?(m)js?(x)"
  ],
  moduleNameMapper: {
    "\\.(css|less|scss)$": "identity-obj-proxy"
    },
  moduleDirectories: [
    "node_modules",
    "src"
    ],
    rootDir: "src",
  moduleFileExtensions: [
    "js",
    "jsx",
    "mjs"
  ],
  transform: {
    "^.+\\.m?jsx?$": "babel-jest"
    },
coverageThreshold: {
    "global": {
        "branches": 80,
        "functions": 80,
        "lines": 80,
        "statements": -10
    }
    },
    setupFiles: ["../<rootDir>/.config.env.test"]

};

The environment variable files is here:

process.env.NEXT_PUBLIC_GA_TRACKING_ID=xxx

And this is the code that is not loading the environment variables properly.

import Analytics from 'analytics';
import googleAnalyticsPlugin from '@analytics/google-analytics';
import Router from 'next/router';

    // Initialize analytics and plugins
    // Documentation: https://getanalytics.io
    const analytics = Analytics({
      debug: process.env.NODE_ENV !== 'production',
      plugins: [
        googleAnalyticsPlugin({
          trackingId: process.env.NEXT_PUBLIC_GA_TRACKING_ID,
        }),
      ],
    });

Upvotes: 7

Views: 8541

Answers (3)

CyberT33N
CyberT33N

Reputation: 144

Load environment variables

  1. Add to jest.config.ts:
setupFiles: ['<rootDir>/test/setup-tests.ts']
  1. Create test/setup-tests.ts
import { loadEnvConfig } from '@next/env'
loadEnvConfig(process.cwd())
  1. Create in your root .env.test
ANY_ENV=test

Upvotes: 0

juliomalves
juliomalves

Reputation: 50418

You can leverage loadEnvConfig from @next/env in your tests to make sure environment variables are loaded the same way Next.js does.


First setup a .env.test to be used in the tests.

NEXT_PUBLIC_GA_TRACKING_ID=ga-test-id

Next, create a Jest global setup file if you don't have one yet, and reference it in your jest.config.js.

// jest.config.js

module.exports = {
    //...
    setupFilesAfterEnv: ['./jest.setup.js'],
};

Then add the following code into your Jest global setup file.

// jest.setup.js
import { loadEnvConfig } from '@next/env'

loadEnvConfig(process.cwd())

Upvotes: 15

Ahmad Alfy
Ahmad Alfy

Reputation: 13381

This message means that the trackingId is not defined. As you can see it read from the process.env. You need to create this file in the root of your project and call it .env. Note that the dot is at the beginning of the filename. The content of the file should be as follow:

NEXT_PUBLIC_GA_TRACKING_ID=insert-key-here

If your env file is not being read by jest you can do the following:

// In jest.config.js : 

module.exports = {
 ....
    setupFiles: ["<rootDir>/test/setup-tests.ts"]
}


// The file test/test-setup.ts:

import dotenv from 'dotenv';
dotenv.config({path: './config.env.test'});

You can also check this article for more details.

Upvotes: 2

Related Questions