Let's take a React application that uses REACT_APP_...
values from the .env
file in its code base. We can take the app from the blog post "Using .env file in React js" as an example. It's .env
file has the following variable values:
1 | REACT_APP_TITLE=How To React |
The App.js
component uses these values in its output
1 | import React from 'react' |
If we start the application locally and visit localhost:3000
we see these values on the page
Nice.
Text substitution
If we inspect the JavaScript bundle created by the react-scripts
and served in the browser, we won't find process.env.REACT_APP_TITLE
Instead, the bundler substitutes the string values right into the source code
If we print the entire process.env
object, it gets substituted into the source bundle
1 | function App() { |
This means, we cannot even overwrite a property of the process.env
object!
1 | function App() { |
Hmm, can we dynamically replace those values while running Cypress tests?
Make it testable
Just like we sometimes add attributes to make our HTML elements easy to find from our tests, we should adjust the source code in the App.js
a little to make the process.env
possible to overwrite. Here is my trick: check the window.process.env
object with fallback to the process.env
text. React bundler does not overwrite window.process.env
object.
1 | import React from 'react' |
If window.process.env
object exists, it overwrites anything in the process.env
inserted by the bundler. Thus we can overwrite only the properties we want by setting them on the application's window
object. Here is a typical test example:
1 | it('mocks process.env', () => { |
Mocking via network intercept
We can mock the text in the JavaScript bundle in other ways. We can intercept the bundle.js
resource loaded by the page. We can find and replace any text strings we want there using cy.intercept command.
1 | it('replaces strings in the JS bundle', () => { |
If React bundler can overwrite process.env.REACT_APP_TITLE
with "How To React"
, then we can certainly overwrite it with "How To Test"
.
š If you want to master Cypress network testing in depth, consider studying my course Cypress Network Testing Exercises.
Component testing
What about Cypress Component testing? We cannot use cy.intercept
to intercept the bundle loaded by the page during cy.visit('/')
unfortunately. The bundle is already served by the time the test runs. We can still use the window.process.env
trick:
1 | import React from 'react' |