Skip to main content

Front-End Development

Mastering Advanced Features and Techniques of JEST React Testing Library

Shot Of A Young Man Using His Digital Tablet And Computer In A Modern Office

Welcome to a deeper journey into the JEST React Testing Library world! We’ll explore advanced methods and tricks that enhance your testing expertise here. If you’re new to JEST, don’t worry! We’ve got you covered with “Exploring JEST React Testing Library: A Complete Overview,” which helps you understand basic and advanced insights, ensuring a comprehensive understanding of JEST Testing. Go and check this out right here.

Now, let’s start exploring advanced features and techniques.

1. Simulating User Interactions

JEST React Testing Library allows you to simulate user interactions with your components. This feature lets you test how your components respond to different user actions. Here are some examples:

       a. Simulating button clicks

The below code defines a simple functional component named “Button” that takes a prop named “label” and renders a button element with the provided label.

Button.js:

import React from "react";
const Button = ({ label, onClick }) => {
  return <button onClick={onClick}>{label}</button>;
};
export default Button;

Button.test.js:

import React from "react";
import { render, screen, fireEvent } from "@testing-library/react";
import Button from "./Button";
test("button click triggers an action", () => {
  const handleClick = jest.fn();
  render(<Button label="Click me" onClick={handleClick} />);
  const buttonElement = screen.getByText(/click me/i);
  fireEvent.click(buttonElement);
  expect(handleClick).toHaveBeenCalledTimes(1);
});

In this example, we define a mock function “handleClick” using “jest.fn()”. We pass this function as a prop to the “Button” component. After rendering the component, we simulate a button click using “fireEvent.click” and assert that the “handleClick” function is called once. Below is a screenshot of the output showing the successful execution of the test cases:

Buttonclick

       b. Simulating Input value change

The below code defines a simple functional component named “LoginForm” that includes a controlled input field for capturing a username. The “useState” hook manages the username state, and the input is associated with a label, allowing users to input their username. Any changes trigger the “handleInputChange” function, keeping the username state synchronized with the input value.

LoginForm.js:

import React, { useState } from "react";
const LoginForm = () => {
  const [username, setUsername] = useState("");
  const handleInputChange = (e) => {
    setUsername(e.target.value);
  };
  return (
    <div>
      <label htmlFor="username">Username:</label>
      <input
        type="text"
        id="username"
        value={username}
        onChange={handleInputChange}
      />
    </div>
  );
};
export default LoginForm;

LoginForm.test.js:

import React from "react";
import { render, screen, fireEvent } from "@testing-library/react";
import LoginForm from "./LoginForm";
test("Typing in username field updates the value", () => {
  render(<LoginForm />);
  const usernameInput = screen.getByLabelText(/username/i);
  fireEvent.change(usernameInput, { target: { value: "testuser" } });
  expect(usernameInput.value).toBe("testuser");
});

In this example, we render a “LoginForm” component that contains an input field for the username. We use “screen.getByLabelText” to find the input field and “fireEvent.change” to simulate the change in input value in the field. Finally, we assert that the input field’s value is updated correctly. Below is a screenshot of the output showing the successful execution of the test cases:

Loginform

2. Testing Asynchronous Behaviour

The “ProductInformation” component is a React functional component that fetches product data from “https://fakestoreapi.com/products/1” using the “fetchProductData” function. The data is stored in the data state using “useState”. The “useEffect” hook ensures data fetching occurs when the component mounts. The component conditionally renders either the “title” of the data or a “Loading…” message based on the data’s availability.

ProductInformation.js:

import React, { useEffect, useState } from 'react';
const ProductInformation = () => {
  const [data, setData] = useState(null);
  const fetchProductData = async () => {
    const response = await fetch('https://fakestoreapi.com/products/1');
    const data = await response.json();
    setData(data);
  };
  useEffect(() => {
    fetchProductData();
  }, []);
  return (
    <div>
      {data ? (
        <div>
          <p>title: {data.title}</p>
        </div>
      ) : (
        <p>Loading...</p>
      )}
    </div>
  );
};
export default ProductInformation;

ProductInformation.test.js:

import React from "react";
import { render, screen, waitFor } from "@testing-library/react";
import ProductInformation from "./ProductInformation";

test("displays fetched data", async () => {
  render(<ProductInformation />);
  const loadingElement = screen.getByText(/loading/i);
  expect(loadingElement).toBeInTheDocument();
  await waitFor(() => {
    const dataElement = screen.getByText(/title: /i);
    expect(dataElement).toBeInTheDocument();
  });
});

In this example, we render the “ProductInformation” component, which fetches data asynchronously. Initially, we expect to see a loading message. Using “waitFor” and “await”, we wait for the data to be fetched and then assert that the data is displayed. Below is a screenshot of the output showing the successful execution of the test cases:

Productinformation

Conclusion

In this second part of our guide, we delved into advanced features and techniques of the JEST React Testing Library. We explored simulating user interactions and handling asynchronous behaviour. Combining the knowledge from both parts of this guide allows you to write comprehensive tests for your React components, ensuring their reliability and robustness.

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Sufiyan Akbani

Sufiyan Akbani is an Associate Technical Consultant at Perficient, with a keen interest in UI development. With over 2 years of experience in this field, Sufiyan is passionate about exploring the latest trends and emerging technologies in UI and front-end development. He finds joy in watching fiction movies and immersing himself in nature by hiking in hill stations during his free time.

More from this Author

Follow Us
TwitterLinkedinFacebookYoutubeInstagram