In the world of React development, fetching data from external APIs is a common task that can significantly enhance the functionality and user experience of your application. Axios, a promise-based HTTP client, has become a go-to solution for such operations, offering an easy-to-use and flexible API that integrates seamlessly with React. This article explores how to utilize Axios within React applications for effective data fetching, manipulation, and state management.

Introduction to Axios

Axios is a lightweight HTTP client based on the XMLHttpRequests service. It can be used in both browser and node.js environments. Its main features include making HTTP requests from the browser, intercepting requests and responses, transforming request and response data, and automatically converting JSON data.

Methods of Using Axios

Method 1: Executing CRUD Operations Using Axios

Setting Up Axios in a React Project

Ensure Axios is included in your project. If not, add them via npm or Yarn:

npm install axiosoryarn add axios

Preparing the Form Component

The form component collects user inputs for name, email, and allows for an image file to be selected:

import React, { useState } from 'react';
import axios from 'axios';

function FormDataComponent() {
    const [formData, setFormData] = useState({
        name: '',
        email: '',
        image: null,
    });

    const handleInputChange = (e) => {
        const { name, value, files } = e.target;
        if (name === 'image') {
            setFormData({...formData, image: files[0]});
        } else {
            setFormData({...formData, [name]: value});
        }
    };

    const handleSubmit = async (e) => {
        e.preventDefault();
        const dataToSubmit = new FormData();
        dataToSubmit.append('name', formData.name);
        dataToSubmit.append('email', formData.email);
        if (formData.image) {
            dataToSubmit.append('image', formData.image);
        }

        await submitData(dataToSubmit); // This function to be defined based on the CRUD operation
    };

    return (
        <form onSubmit={handleSubmit}>
            <input type="text" name="name" onChange={handleInputChange} placeholder="Name" />
            <input type="email" name="email" onChange={handleInputChange} placeholder="Email" />
            <input type="file" name="image" onChange={handleInputChange} />
            <button type="submit">Submit</button>
        </form>
    );
}

Axios CRUD Operations with above Form Data

Axios simplifies interacting with APIs for CRUD operations. Below, we detail each operation’s implementation.

Read Operation

Fetching data (the Read operation) is a common requirement. Here’s how to accomplish it with Axios:

import React, { useState, useEffect } from 'react';
import axios from 'axios';

const FetchData = () => {
  const [data, setData] = useState([]);

  useEffect(() => {
    axios.get('https://api.example.com/data')
      .then((response) => setData(response.data))
      .catch((error) => console.error("Fetching error:", error));
  }, []);

  return (
    <ul>
      {data.map(item => <li key={item.id}>{item.title}</li>)}
    </ul>
  );
};

export default FetchData;
Create Operation

To add new data, including the form data collected:

const submitData = async (dataToSubmit) => {
    try {
        const response = await axios.post('https://api.example.com/data', dataToSubmit, {
            headers: { 'Content-Type': 'multipart/form-data' },
        });
        console.log("Data added", response.data);
    } catch (error) {
        console.error("Adding error:", error);
    }
};
Update Operation

To update existing data with new form data:

const submitData = async (dataToSubmit, id) => { // Assume 'id' is the ID of the data to update
    try {
        const response = await axios.put(`https://api.example.com/data/${id}`, dataToSubmit, {
            headers: { 'Content-Type': 'multipart/form-data' },
        });
        console.log("Data updated", response.data);
    } catch (error) {
        console.error("Updating error:", error);
    }
};
For the update operation, you would need to adjust the form submission handler to include the id of the item being updated.
Delete Operation
const deleteData = (id) => {
  axios.delete(`https://api.example.com/data/${id}`)
    .then(() => {
      console.log("Data deleted");
    })
    .catch((error) => console.error("Deleting error:", error));
};

Method 2: Configuring Axios with Redux for CRUD Operations

To create more maintainable and scalable React applications, leveraging Redux for state management in combination with Axios for HTTP requests offers a powerful solution. This approach centralizes your application’s state management and cleanly separates concerns, enhancing overall code organization and efficiency. Here’s a step-by-step guide on integrating CRUD operations into your React application using Axios and Redux.

Setting Up Redux and Axios

Ensure Axios and Redux are included in your project. If not, add them via npm:

npm install axios redux react-redux

This setup assumes you have a basic understanding of Redux and have it configured in your project. If not, you may need to set up your Redux store and provider first.

Action Creators for CRUD Operations

Action creators in Redux serve to encapsulate the process of creating actions. When paired with Axios, they can also handle asynchronous requests to perform CRUD operations.

Configure Axios

Create an Axios instance to set base URLs and other configurations:

// src/api/axiosConfig.js
import axios from 'axios';

const instance = axios.create({
    baseURL: 'https://api.example.com',
});

export default instance;
Defining Action Types

Specify action types for CRUD operations in src/redux/actionTypes.js:

export const FETCH_DATA_SUCCESS = 'FETCH_DATA_SUCCESS';
export const CREATE_DATA_SUCCESS = 'CREATE_DATA_SUCCESS';
export const UPDATE_DATA_SUCCESS = 'UPDATE_DATA_SUCCESS';
export const DELETE_DATA_SUCCESS = 'DELETE_DATA_SUCCESS';
Create Actions

In src/redux/actions/dataActions.js, define your actions and use Axios for HTTP requests:

import axios from '../api/axiosConfig';
import {
  FETCH_DATA_SUCCESS,
  CREATE_DATA_SUCCESS,
  UPDATE_DATA_SUCCESS,
  DELETE_DATA_SUCCESS,
} from './actionTypes';

// Fetch data action
export const fetchData = () => async (dispatch) => {
  axios.get('/data')
    .then(response => dispatch({ type: FETCH_DATA_SUCCESS, payload: response.data }))
    .catch(error => console.error('Fetching error:', error));
};

// Create data action
export const submitFormData = (formData) => async (dispatch) => {
try {
        const response = await axios.post('/submit-form', formData, {
            headers: { 'Content-Type': 'multipart/form-data' },
        });
        dispatch({ type: CREATE_DATA_SUCCESS, payload: response.data }); // Assuming CREATE_DATA_SUCCESS updates the state appropriately
    } catch (error) {
        console.error('Form submission error:', error);
    } };

// Update data action
export const updateData = (id, formData) => async (dispatch) => {
  axios.put(`/data/${id}`, formData, {
    headers: { 'Content-Type': 'multipart/form-data' },
  })
  .then(response => dispatch({ type: UPDATE_DATA_SUCCESS, payload: response.data }))
  .catch(error => console.error('Updating error:', error));
};// Delete data action
export const deleteData = (id) => async (dispatch) => {
  axios.delete(`/data/${id}`)
    .then(() => dispatch({ type: DELETE_DATA_SUCCESS, id }))
    .catch(error => console.error('Deleting error:', error));
};
Reducers

Reducers will handle actions dispatched by the action creators and update the application state accordingly.

// src/redux/reducers/dataReducer.js
import {
  FETCH_DATA_SUCCESS,
  CREATE_DATA_SUCCESS,
  UPDATE_DATA_SUCCESS,
  DELETE_DATA_SUCCESS,
} from '../actionTypes';

const initialState = { data: [] };

const dataReducer = (state = initialState, action) => {
  switch (action.type) {
    case FETCH_DATA_SUCCESS:
      return { ...state, data: action.payload };
    case CREATE_DATA_SUCCESS:
      return { ...state, data: [...state.data, action.payload] };
    case UPDATE_DATA_SUCCESS:
      return {
        ...state,
        data: state.data.map(item => item.id === action.payload.id ? action.payload : item),
      };
    case DELETE_DATA_SUCCESS:
      return { ...state, data: state.data.filter(item => item.id !== action.id) };
    default:
      return state;
  }
};

export default dataReducer;
Connecting Components with Redux

Finally, connect your React components to the Redux store using connect() or the useSelector and useDispatch hooks from react-redux. Use the actions you’ve created to interact with your backend API and update the state in your components accordingly.

import React, { useState, useEffect } from 'react';
import { useDispatch, useSelector } from 'react-redux';
import { fetchData, submitFormData, updateData } from './redux/actions/dataActions';

function DataComponent() {
    const [formData, setFormData] = useState({
        name: '',
        email: '',
        image: null,
    });
    const [isUpdateMode, setIsUpdateMode] = useState(false);
    const [updateId, setUpdateId] = useState(null);

    const dispatch = useDispatch();
    const data = useSelector(state => state.data.data);

    useEffect(() => {
        dispatch(fetchData());
    }, [dispatch]);

    const handleInputChange = (event) => {
        const { name, value, files } = event.target;
        if (name === 'image') {
            setFormData({...formData, image: files[0]});
        } else {
            setFormData({...formData, [name]: value});
        }
    };

    const handleSubmit = (event) => {
        event.preventDefault();
        const dataToSubmit = new FormData();
        dataToSubmit.append('name', formData.name);
        dataToSubmit.append('email', formData.email);
        if (formData.image) {
            dataToSubmit.append('image', formData.image);
        }

        if (isUpdateMode && updateId) {
            // Dispatch the update action if in update mode
            dispatch(updateData(updateId, dataToSubmit));
        } else {
            // Dispatch the create action if not in update mode
            dispatch(submitFormData(dataToSubmit));
        }

        // Optionally reset form fields and mode here
        setFormData({ name: '', email: '', image: null });
        setIsUpdateMode(false);
        setUpdateId(null);
    };

    // Function to set form data and mode for updating
const handleEdit = (item) => {
    setFormData({
        name: item.name,
        email: item.email,
        image: null // Keep this to null since the file input can't be programmatically set
    });
    setIsUpdateMode(true);
    setUpdateId(item.id);

    // Optionally, store the existing image URL in a state if you're displaying it
    setCurrentImageUrl(item.imageUrl); // Assume your item has an `imageUrl` field
};return (
        <div>
          <form onSubmit={handleSubmit}>
    <input type="text" name="name" value={formData.name} onChange={handleInputChange} placeholder="Name" />
    <input type="email" name="email" value={formData.email} onChange={handleInputChange} placeholder="Email" />
    {isUpdateMode && currentImageUrl && (
        <div>
            <img src={currentImageUrl} alt="Current" style={{width: '100px', height: '100px'}} />
            <p>Change Image:</p>
        </div>
    )}
    <input type="file" name="image" onChange={handleInputChange} />
    <button type="submit">{isUpdateMode ? 'Update' : 'Submit'}</button>
</form>
            <h2>Data List</h2>
            <ul>
                {data.map(item => (
                    <li key={item.id}>
                        {item.name} - {item.email}
                        <button onClick={() => handleEdit(item)}>Edit</button>
                    </li>
                ))}
            </ul>
        </div>
    );
}

export default DataComponent;

Conclusion

Axios provides a powerful solution for React developers to handle CRUD operations, form data, and image uploads, enhancing application interactivity. Whether used directly or with Redux, Axios ensures data management processes are efficient and scalable, fitting the needs of modern web development.

Axios in React JS – FAQs

How to install Axios in React?

Install Axios in your React project by running npm install axios in your project directory. This command adds Axios to your project dependencies.

How to use Axios?

Use Axios to make HTTP requests by importing it into your component (import axios from ‘axios’;) and then calling methods like axios.get(url) or axios.post(url, data) to fetch or send data.

How to import Axios in React?

Import Axios into a React component by adding import axios from ‘axios’; at the top of your component file. This makes Axios available to use within the component.

Can Axios handle concurrent requests in React?

Yes, Axios can handle concurrent requests using axios.all([requestOne, requestTwo]) to efficiently manage multiple API calls simultaneously in React applications.

How to handle errors with Axios in React?

Handle errors with Axios by using the .catch() method on your request or by using a try-catch block with async/await syntax to catch any errors that occur during the request.

Newsletter

I am a Software developer

My name is muhammad adnan and i am a professtional software developer. specialize in designing and developing efficient software applications.

Check out My Portfolio