ગુજરાતી

આ સંપૂર્ણ માર્ગદર્શિકા સાથે રિએક્ટ ટેસ્ટિંગ લાઇબ્રેરી (RTL) માં નિપુણતા મેળવો. શ્રેષ્ઠ પદ્ધતિઓ અને વાસ્તવિક-દુનિયાના ઉદાહરણો પર ધ્યાન કેન્દ્રિત કરીને, તમારી રિએક્ટ એપ્લિકેશનો માટે અસરકારક, જાળવી શકાય તેવા અને વપરાશકર્તા-કેન્દ્રિત ટેસ્ટ લખવાનું શીખો.

રિએક્ટ ટેસ્ટિંગ લાઇબ્રેરી: એક વિસ્તૃત માર્ગદર્શિકા

આજના ઝડપી વેબ ડેવલપમેન્ટના પરિદ્રશ્યમાં, તમારી રિએક્ટ એપ્લિકેશન્સની ગુણવત્તા અને વિશ્વસનીયતા સુનિશ્ચિત કરવી સર્વોપરી છે. રિએક્ટ ટેસ્ટિંગ લાઇબ્રેરી (RTL) એ વપરાશકર્તાના દ્રષ્ટિકોણ પર ધ્યાન કેન્દ્રિત કરતા ટેસ્ટ લખવા માટે એક લોકપ્રિય અને અસરકારક ઉકેલ તરીકે ઉભરી આવ્યું છે. આ માર્ગદર્શિકા RTLની સંપૂર્ણ ઝાંખી પૂરી પાડે છે, જેમાં મૂળભૂત ખ્યાલોથી લઈને અદ્યતન તકનીકો સુધી બધું જ આવરી લેવામાં આવ્યું છે, જે તમને મજબૂત અને જાળવી શકાય તેવી રિએક્ટ એપ્લિકેશનો બનાવવામાં સશક્ત બનાવે છે.

રિએક્ટ ટેસ્ટિંગ લાઇબ્રેરી શા માટે પસંદ કરવી?

પારંપરિક ટેસ્ટિંગ અભિગમો ઘણીવાર અમલીકરણની વિગતો પર આધાર રાખે છે, જે ટેસ્ટને નાજુક બનાવે છે અને નાના કોડ ફેરફારો સાથે તૂટી જવાની સંભાવના ધરાવે છે. બીજી બાજુ, RTL તમને તમારા કમ્પોનન્ટ્સને તે રીતે ટેસ્ટ કરવા માટે પ્રોત્સાહિત કરે છે જે રીતે વપરાશકર્તા તેમની સાથે ક્રિયાપ્રતિક્રિયા કરશે, વપરાશકર્તા શું જુએ છે અને અનુભવે છે તેના પર ધ્યાન કેન્દ્રિત કરે છે. આ અભિગમ ઘણા મુખ્ય ફાયદાઓ પ્રદાન કરે છે:

તમારું ટેસ્ટિંગ પર્યાવરણ સેટ કરવું

તમે RTL નો ઉપયોગ શરૂ કરો તે પહેલાં, તમારે તમારું ટેસ્ટિંગ પર્યાવરણ સેટ કરવાની જરૂર છે. આમાં સામાન્ય રીતે જરૂરી ડિપેન્ડન્સીઝ ઇન્સ્ટોલ કરવી અને તમારા ટેસ્ટિંગ ફ્રેમવર્કને ગોઠવવાનો સમાવેશ થાય છે.

પૂર્વજરૂરીયાતો

ઇન્સ્ટોલેશન

npm અથવા yarn નો ઉપયોગ કરીને નીચેના પેકેજો ઇન્સ્ટોલ કરો:

npm install --save-dev @testing-library/react @testing-library/jest-dom jest babel-jest @babel/preset-env @babel/preset-react

અથવા, yarn નો ઉપયોગ કરીને:

yarn add --dev @testing-library/react @testing-library/jest-dom jest babel-jest @babel/preset-env @babel/preset-react

પેકેજોનું સ્પષ્ટીકરણ:

કન્ફિગરેશન

તમારા પ્રોજેક્ટના રૂટમાં નીચેની સામગ્રી સાથે `babel.config.js` ફાઇલ બનાવો:

module.exports = {
  presets: ['@babel/preset-env', '@babel/preset-react'],
};

ટેસ્ટ સ્ક્રિપ્ટ શામેલ કરવા માટે તમારી `package.json` ફાઇલ અપડેટ કરો:

{
  "scripts": {
    "test": "jest"
  }
}

Jest ને ગોઠવવા માટે તમારા પ્રોજેક્ટના રૂટમાં `jest.config.js` ફાઇલ બનાવો. એક ન્યૂનતમ રૂપરેખાંકન આના જેવું દેખાઈ શકે છે:

module.exports = {
  testEnvironment: 'jsdom',
  setupFilesAfterEnv: ['/src/setupTests.js'],
};

નીચેની સામગ્રી સાથે `src/setupTests.js` ફાઇલ બનાવો. આ સુનિશ્ચિત કરે છે કે Jest DOM મેચર્સ તમારા બધા ટેસ્ટમાં ઉપલબ્ધ છે:

import '@testing-library/jest-dom/extend-expect';

તમારો પ્રથમ ટેસ્ટ લખવો

ચાલો એક સરળ ઉદાહરણથી શરૂઆત કરીએ. ધારો કે તમારી પાસે એક રિએક્ટ કમ્પોનન્ટ છે જે શુભેચ્છા સંદેશ દર્શાવે છે:

// src/components/Greeting.js
import React from 'react';

function Greeting({ name }) {
  return <h1>Hello, {name}!</h1>;
}

export default Greeting;

હવે, ચાલો આ કમ્પોનન્ટ માટે એક ટેસ્ટ લખીએ:

// src/components/Greeting.test.js
import React from 'react';
import { render, screen } from '@testing-library/react';
import Greeting from './Greeting';

test('શુભેચ્છા સંદેશ રેન્ડર કરે છે', () => {
  render(<Greeting name="World" />);
  const greetingElement = screen.getByText(/Hello, World!/i);
  expect(greetingElement).toBeInTheDocument();
});

સ્પષ્ટીકરણ:

ટેસ્ટ ચલાવવા માટે, તમારા ટર્મિનલમાં નીચેનો કમાન્ડ ચલાવો:

npm test

જો બધું બરાબર ગોઠવેલું હોય, તો ટેસ્ટ પાસ થવો જોઈએ.

સામાન્ય RTL ક્વેરીઝ

RTL DOM માં એલિમેન્ટ્સ શોધવા માટે વિવિધ ક્વેરી પદ્ધતિઓ પ્રદાન કરે છે. આ ક્વેરીઝ વપરાશકર્તાઓ તમારી એપ્લિકેશન સાથે કેવી રીતે ક્રિયાપ્રતિક્રિયા કરે છે તેની નકલ કરવા માટે ડિઝાઇન કરવામાં આવી છે.

`getByRole`

આ ક્વેરી એલિમેન્ટને તેના ARIA રોલ દ્વારા શોધે છે. શક્ય હોય ત્યારે `getByRole` નો ઉપયોગ કરવો એ એક સારી પ્રથા છે, કારણ કે તે એક્સેસિબિલિટીને પ્રોત્સાહન આપે છે અને સુનિશ્ચિત કરે છે કે તમારા ટેસ્ટ અંતર્ગત DOM સ્ટ્રક્ચરમાં થતા ફેરફારો સામે સ્થિતિસ્થાપક છે.

<button role="button">Click me</button>
const buttonElement = screen.getByRole('button');
expect(buttonElement).toBeInTheDocument();

`getByLabelText`

આ ક્વેરી એલિમેન્ટને તેના સંકળાયેલ લેબલના ટેક્સ્ટ દ્વારા શોધે છે. તે ફોર્મ એલિમેન્ટ્સના ટેસ્ટિંગ માટે ઉપયોગી છે.

<label htmlFor="name">Name:</label>
<input type="text" id="name" />
const nameInputElement = screen.getByLabelText('Name:');
expect(nameInputElement).toBeInTheDocument();

`getByPlaceholderText`

આ ક્વેરી એલિમેન્ટને તેના પ્લેસહોલ્ડર ટેક્સ્ટ દ્વારા શોધે છે.

<input type="text" placeholder="Enter your email" />
const emailInputElement = screen.getByPlaceholderText('Enter your email');
expect(emailInputElement).toBeInTheDocument();

`getByAltText`

આ ક્વેરી ઇમેજ એલિમેન્ટને તેના alt ટેક્સ્ટ દ્વારા શોધે છે. એક્સેસિબિલિટી સુનિશ્ચિત કરવા માટે બધી છબીઓ માટે અર્થપૂર્ણ alt ટેક્સ્ટ પ્રદાન કરવું મહત્વપૂર્ણ છે.

<img src="logo.png" alt="Company Logo" />
const logoImageElement = screen.getByAltText('Company Logo');
expect(logoImageElement).toBeInTheDocument();

`getByTitle`

આ ક્વેરી એલિમેન્ટને તેના ટાઇટલ એટ્રિબ્યુટ દ્વારા શોધે છે.

<span title="Close">X</span>
const closeElement = screen.getByTitle('Close');
expect(closeElement).toBeInTheDocument();

`getByDisplayValue`

આ ક્વેરી એલિમેન્ટને તેની ડિસ્પ્લે વેલ્યુ દ્વારા શોધે છે. આ પૂર્વ-ભરેલા મૂલ્યો સાથે ફોર્મ ઇનપુટ્સના ટેસ્ટિંગ માટે ઉપયોગી છે.

<input type="text" value="Initial Value" />
const inputElement = screen.getByDisplayValue('Initial Value');
expect(inputElement).toBeInTheDocument();

`getAllBy*` ક્વેરીઝ

`getBy*` ક્વેરીઝ ઉપરાંત, RTL `getAllBy*` ક્વેરીઝ પણ પ્રદાન કરે છે, જે મેચિંગ એલિમેન્ટ્સનો એરે પરત કરે છે. જ્યારે તમારે ખાતરી કરવાની જરૂર હોય કે DOM માં સમાન લાક્ષણિકતાઓવાળા બહુવિધ એલિમેન્ટ્સ હાજર છે ત્યારે આ ઉપયોગી છે.

<li>Item 1</li>
<li>Item 2</li>
<li>Item 3</li>
const listItems = screen.getAllByRole('listitem');
expect(listItems).toHaveLength(3);

`queryBy*` ક્વેરીઝ

`queryBy*` ક્વેરીઝ `getBy*` ક્વેરીઝ જેવી જ છે, પરંતુ જો કોઈ મેચિંગ એલિમેન્ટ ન મળે તો તે એરર ફેંકવાને બદલે `null` પરત કરે છે. જ્યારે તમે ખાતરી કરવા માંગો છો કે DOM માં કોઈ એલિમેન્ટ હાજર *નથી* ત્યારે આ ઉપયોગી છે.

const missingElement = screen.queryByText('Non-existent text');
expect(missingElement).toBeNull();

`findBy*` ક્વેરીઝ

`findBy*` ક્વેરીઝ `getBy*` ક્વેરીઝના એસિંક્રોનસ વર્ઝન છે. તે એક પ્રોમિસ પરત કરે છે જે મેચિંગ એલિમેન્ટ મળ્યા પછી ઉકેલાય છે. આ એસિંક્રોનસ ઓપરેશન્સના ટેસ્ટિંગ માટે ઉપયોગી છે, જેમ કે API માંથી ડેટા મેળવવો.

// એસિંક્રોનસ ડેટા ફેચનું અનુકરણ
const fetchData = () => new Promise(resolve => {
  setTimeout(() => resolve('Data Loaded!'), 1000);
});

function MyComponent() {
  const [data, setData] = React.useState(null);

  React.useEffect(() => {
    fetchData().then(setData);
  }, []);

  return <div>{data}</div>;
}
test('ડેટા એસિંક્રોનસ રીતે લોડ કરે છે', async () => {
  render(<MyComponent />);
  const dataElement = await screen.findByText('Data Loaded!');
  expect(dataElement).toBeInTheDocument();
});

વપરાશકર્તાની ક્રિયાપ્રતિક્રિયાઓનું અનુકરણ

RTL વપરાશકર્તાની ક્રિયાપ્રતિક્રિયાઓ, જેમ કે બટન ક્લિક કરવું, ઇનપુટ ફીલ્ડમાં ટાઇપ કરવું અને ફોર્મ સબમિટ કરવાનું અનુકરણ કરવા માટે `fireEvent` અને `userEvent` APIs પ્રદાન કરે છે.

`fireEvent`

`fireEvent` તમને પ્રોગ્રામેટિકલી DOM ઇવેન્ટ્સને ટ્રિગર કરવાની મંજૂરી આપે છે. તે એક નીચલા-સ્તરનું API છે જે તમને ફાયર થયેલી ઇવેન્ટ્સ પર સૂક્ષ્મ-સ્તરનું નિયંત્રણ આપે છે.

<button onClick={() => alert('Button clicked!')}>Click me</button>
import { fireEvent } from '@testing-library/react';

test('બટન ક્લિકનું અનુકરણ કરે છે', () => {
  const alertMock = jest.spyOn(window, 'alert').mockImplementation(() => {});
  render(<button onClick={() => alert('Button clicked!')}>Click me</button>);
  const buttonElement = screen.getByRole('button');
  fireEvent.click(buttonElement);
  expect(alertMock).toHaveBeenCalledTimes(1);
  alertMock.mockRestore();
});

`userEvent`

`userEvent` એ એક ઉચ્ચ-સ્તરનું API છે જે વપરાશકર્તાની ક્રિયાપ્રતિક્રિયાઓનું વધુ વાસ્તવિક રીતે અનુકરણ કરે છે. તે ફોકસ મેનેજમેન્ટ અને ઇવેન્ટ ઓર્ડરિંગ જેવી વિગતોને હેન્ડલ કરે છે, જે તમારા ટેસ્ટને વધુ મજબૂત અને ઓછા નાજુક બનાવે છે.

<input type="text" onChange={e => console.log(e.target.value)} />
import userEvent from '@testing-library/user-event';

test('ઇનપુટ ફીલ્ડમાં ટાઇપિંગનું અનુકરણ કરે છે', () => {
  const inputElement = screen.getByRole('textbox');
  userEvent.type(inputElement, 'Hello, world!');
  expect(inputElement).toHaveValue('Hello, world!');
});

એસિંક્રોનસ કોડનું ટેસ્ટિંગ

ઘણી રિએક્ટ એપ્લિકેશન્સમાં એસિંક્રોનસ ઓપરેશન્સ સામેલ હોય છે, જેમ કે API માંથી ડેટા મેળવવો. RTL એસિંક્રોનસ કોડના ટેસ્ટિંગ માટે ઘણા ટૂલ્સ પ્રદાન કરે છે.

`waitFor`

`waitFor` તમને ખાતરી કરતા પહેલા કોઈ શરત સાચી થાય તેની રાહ જોવાની મંજૂરી આપે છે. તે એસિંક્રોનસ ઓપરેશન્સના ટેસ્ટિંગ માટે ઉપયોગી છે જેને પૂર્ણ થવામાં થોડો સમય લાગે છે.

function MyComponent() {
  const [data, setData] = React.useState(null);

  React.useEffect(() => {
    setTimeout(() => {
      setData('Data loaded!');
    }, 1000);
  }, []);

  return <div>{data}</div>;
}
import { waitFor } from '@testing-library/react';

test('ડેટા લોડ થવાની રાહ જુએ છે', async () => {
  render(<MyComponent />);
  await waitFor(() => screen.getByText('Data loaded!'));
  const dataElement = screen.getByText('Data loaded!');
  expect(dataElement).toBeInTheDocument();
});

`findBy*` ક્વેરીઝ

પહેલા ઉલ્લેખ કર્યો તેમ, `findBy*` ક્વેરીઝ એસિંક્રોનસ છે અને એક પ્રોમિસ પરત કરે છે જે મેચિંગ એલિમેન્ટ મળ્યા પછી ઉકેલાય છે. આ એસિંક્રોનસ ઓપરેશન્સના ટેસ્ટિંગ માટે ઉપયોગી છે જે DOM માં ફેરફારોમાં પરિણમે છે.

હુક્સનું ટેસ્ટિંગ

રિએક્ટ હુક્સ એ પુનઃઉપયોગી ફંક્શન્સ છે જે સ્ટેટફુલ લોજિકને સમાવે છે. RTL કસ્ટમ હુક્સને અલગથી ટેસ્ટ કરવા માટે `@testing-library/react-hooks` (જે v17 થી સીધા `@testing-library/react` ના પક્ષમાં નાપસંદ કરવામાં આવ્યું છે) માંથી `renderHook` યુટિલિટી પ્રદાન કરે છે.

// src/hooks/useCounter.js
import { useState } from 'react';

function useCounter(initialValue = 0) {
  const [count, setCount] = useState(initialValue);

  const increment = () => {
    setCount(prevCount => prevCount + 1);
  };

  const decrement = () => {
    setCount(prevCount => prevCount - 1);
  };

  return { count, increment, decrement };
}

export default useCounter;
// src/hooks/useCounter.test.js
import { renderHook, act } from '@testing-library/react';
import useCounter from './useCounter';

test('કાઉન્ટરમાં વધારો કરે છે', () => {
  const { result } = renderHook(() => useCounter());

  act(() => {
    result.current.increment();
  });

  expect(result.current.count).toBe(1);
});

સ્પષ્ટીકરણ:

અદ્યતન ટેસ્ટિંગ તકનીકો

એકવાર તમે RTL ની મૂળભૂત બાબતોમાં નિપુણતા મેળવી લો, પછી તમે તમારા ટેસ્ટની ગુણવત્તા અને જાળવણીક્ષમતા સુધારવા માટે વધુ અદ્યતન ટેસ્ટિંગ તકનીકો શોધી શકો છો.

મોડ્યુલ્સનું મોકિંગ

કેટલીકવાર, તમારે તમારા કમ્પોનન્ટ્સને અલગ કરવા અને ટેસ્ટિંગ દરમિયાન તેમના વર્તનને નિયંત્રિત કરવા માટે બાહ્ય મોડ્યુલો અથવા ડિપેન્ડન્સીઝને મોક કરવાની જરૂર પડી શકે છે. Jest આ હેતુ માટે એક શક્તિશાળી મોકિંગ API પ્રદાન કરે છે.

// src/api/dataService.js
export const fetchData = async () => {
  const response = await fetch('/api/data');
  const data = await response.json();
  return data;
};
// src/components/MyComponent.js
import React, { useState, useEffect } from 'react';
import { fetchData } from '../api/dataService';

function MyComponent() {
  const [data, setData] = useState(null);

  useEffect(() => {
    fetchData().then(setData);
  }, []);

  return <div>{data}</div>;
}
// src/components/MyComponent.test.js
import { render, screen, waitFor } from '@testing-library/react';
import MyComponent from './MyComponent';
import * as dataService from '../api/dataService';

jest.mock('../api/dataService');

test('API માંથી ડેટા મેળવે છે', async () => {
  dataService.fetchData.mockResolvedValue({ message: 'Mocked data!' });

  render(<MyComponent />);

  await waitFor(() => screen.getByText('Mocked data!'));

  expect(screen.getByText('Mocked data!')).toBeInTheDocument();
  expect(dataService.fetchData).toHaveBeenCalledTimes(1);
});

સ્પષ્ટીકરણ:

કંટેક્સ્ટ પ્રોવાઇડર્સ

જો તમારો કમ્પોનન્ટ કંટેક્સ્ટ પ્રોવાઇડર પર આધાર રાખે છે, તો તમારે ટેસ્ટિંગ દરમિયાન તમારા કમ્પોનન્ટને પ્રોવાઇડરમાં લપેટવાની જરૂર પડશે. આ સુનિશ્ચિત કરે છે કે કમ્પોનન્ટને કંટેક્સ્ટ વેલ્યુઝની ઍક્સેસ છે.

// src/contexts/ThemeContext.js
import React, { createContext, useState } from 'react';

export const ThemeContext = createContext();

export function ThemeProvider({ children }) {
  const [theme, setTheme] = useState('light');

  const toggleTheme = () => {
    setTheme(prevTheme => (prevTheme === 'light' ? 'dark' : 'light'));
  };

  return (
    <ThemeContext.Provider value={{ theme, toggleTheme }}>
      {children}
    </ThemeContext.Provider>
  );
}
// src/components/MyComponent.js
import React, { useContext } from 'react';
import { ThemeContext } from '../contexts/ThemeContext';

function MyComponent() {
  const { theme, toggleTheme } = useContext(ThemeContext);

  return (
    <div style={{ backgroundColor: theme === 'light' ? '#fff' : '#000', color: theme === 'light' ? '#000' : '#fff' }}>
      <p>Current theme: {theme}</p>
      <button onClick={toggleTheme}>Toggle Theme</button>
    </div>
  );
}
// src/components/MyComponent.test.js
import { render, screen, fireEvent } from '@testing-library/react';
import MyComponent from './MyComponent';
import { ThemeProvider } from '../contexts/ThemeContext';

test('થીમ ટૉગલ કરે છે', () => {
  render(
    <ThemeProvider>
      <MyComponent />
    </ThemeProvider>
  );

  const themeParagraph = screen.getByText(/Current theme: light/i);
  const toggleButton = screen.getByRole('button', { name: /Toggle Theme/i });

  expect(themeParagraph).toBeInTheDocument();

  fireEvent.click(toggleButton);

  expect(screen.getByText(/Current theme: dark/i)).toBeInTheDocument();
});

સ્પષ્ટીકરણ:

રાઉટર સાથે ટેસ્ટિંગ

જ્યારે રિએક્ટ રાઉટરનો ઉપયોગ કરતા કમ્પોનન્ટ્સનું ટેસ્ટિંગ કરો, ત્યારે તમારે મોક રાઉટર કંટેક્સ્ટ પ્રદાન કરવાની જરૂર પડશે. તમે `react-router-dom` માંથી `MemoryRouter` કમ્પોનન્ટનો ઉપયોગ કરીને આ પ્રાપ્ત કરી શકો છો.

// src/components/MyComponent.js
import React from 'react';
import { Link } from 'react-router-dom';

function MyComponent() {
  return (
    <div>
      <Link to="/about">Go to About Page</Link>
    </div>
  );
}
// src/components/MyComponent.test.js
import { render, screen } from '@testing-library/react';
import { MemoryRouter } from 'react-router-dom';
import MyComponent from './MyComponent';

test('અબાઉટ પેજની લિંક રેન્ડર કરે છે', () => {
  render(
    <MemoryRouter>
      <MyComponent />
    </MemoryRouter>
  );

  const linkElement = screen.getByRole('link', { name: /Go to About Page/i });
  expect(linkElement).toBeInTheDocument();
  expect(linkElement).toHaveAttribute('href', '/about');
});

સ્પષ્ટીકરણ:

અસરકારક ટેસ્ટ લખવા માટેની શ્રેષ્ઠ પદ્ધતિઓ

અહીં RTL સાથે ટેસ્ટ લખતી વખતે અનુસરવા માટેની કેટલીક શ્રેષ્ઠ પદ્ધતિઓ છે:

નિષ્કર્ષ

રિએક્ટ ટેસ્ટિંગ લાઇબ્રેરી તમારી રિએક્ટ એપ્લિકેશનો માટે અસરકારક, જાળવી શકાય તેવા અને વપરાશકર્તા-કેન્દ્રિત ટેસ્ટ લખવા માટે એક શક્તિશાળી સાધન છે. આ માર્ગદર્શિકામાં દર્શાવેલ સિદ્ધાંતો અને તકનીકોને અનુસરીને, તમે તમારા વપરાશકર્તાઓની જરૂરિયાતોને પૂર્ણ કરતી મજબૂત અને વિશ્વસનીય એપ્લિકેશનો બનાવી શકો છો. વપરાશકર્તાના દ્રષ્ટિકોણથી ટેસ્ટિંગ પર ધ્યાન કેન્દ્રિત કરવાનું યાદ રાખો, અમલીકરણની વિગતોનું ટેસ્ટિંગ ટાળો, અને સ્પષ્ટ અને સંક્ષિપ્ત ટેસ્ટ લખો. RTL અપનાવીને અને શ્રેષ્ઠ પદ્ધતિઓ અપનાવીને, તમે તમારા સ્થાન અથવા તમારા વૈશ્વિક પ્રેક્ષકોની ચોક્કસ જરૂરિયાતોને ધ્યાનમાં લીધા વિના, તમારા રિએક્ટ પ્રોજેક્ટ્સની ગુણવત્તા અને જાળવણીક્ષમતામાં નોંધપાત્ર સુધારો કરી શકો છો.