I have an error in my tests that flag up a window env variable as undefined. I understand the error as it is based on the runtime of the app using the variables and maybe they are undefined on running the app. But I don't know where in the setupTests.tsx, I would need to define it. So far the variable is used as so:
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<link rel="icon" href="%PUBLIC_URL%/favicon.ico" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<script src="%PUBLIC_URL%/config.js"></script>
</head>
<body>
<noscript>You need to enable JavaScript to run this app.</noscript>
<div id="root"></div>
</body>
</html>
config.js
window._env_ = {
REACT_APP_URL: "https://apiurl.com"
}
how it is used in the app:
declare const window: Window &
typeof globalThis & {
_env_: any
}
const url = window._env_.REACT_APP_URL;
export const apiUrl = url;
setupTests.tsx I did try adding it here but it's still not working
import '@testing-library/jest-dom';
import { setLogger } from 'react-query'
import { server } from './mocks/server'
declare const window: Window &
typeof globalThis & {
_env_: any
}
window._env_.REACT_APP_URL = "https://wwww.xxxxx.com"
beforeAll(() => server.listen())
// Reset any request handlers that we may add during the tests,
// so they don't affect other tests.
afterEach(() => server.resetHandlers())
// Clean up after the tests are finished.
afterAll(() => server.close())
The error that stops the tests:
● Test suite failed to run
TypeError: Cannot read properties of undefined (reading 'REACT_APP_URL')
4 | }
5 |
> 6 | const url = window._env_.REACT_APP_URL;
| ^
7 | export const apiUrl = url;
8 |
9 |
at Object.<anonymous> (src/utils/Url.tsx:6:26)
at Object.<anonymous> (src/mocks/handlers.tsx:3:1)
at Object.<anonymous> (src/mocks/server.tsx:2:1)
at Object.<anonymous> (src/setupTests.tsx:7:1)
The reason why you are seeing an error: The jest library that automatically comes with a new create-react-app project has already been pre-configured to use jsdom as it's test environment (ref), meaning that the window property will be defined during the runtime of your tests. However, _env_ is a not a default property of the window variable, meaning that it is undefined and an attempt to access its properties will give you an error. This issue can be fixed by assigning a new object to the _env_ property, however there is another problem which stands in our way. The following assignment const url = window._env_.REACT_APP_URL; will always be evaluated before your tests get executed. The reason for that is because when a file (in this case the setupTests.tsx file) imports another file (e.g. Url.tsx), the imported file's logic gets immediately evaluated (almost like triggering an implicitly invoked function) and any variable assignments within it get immediately executed, hence overwriting the _env_ property in your tests will not work as it will be too late.
To fix this problem: you can mock out the entire file that contains the variables and have it return what you need using the following code which should be placed at the top of the test file:
jest.mock('./src/utils/Url', () => ({
get apiUrl () {
return "https://wwww.xxxxx.com";
}
}));