Using Axios In React

Using Axios In React

Various ways Axios can be used in your react application.

Hello react 👋,

Most projects on the web, including mobile apps needs to communicate with a REST API at some point. They use HTTP requests to communicate with APIs. One popular way of consuming these APIs in react can be done with AXIOS

Axios is a promise-based and lightweight JavaScript library used to make HTTP requests and can be used both in a node.js environment and in the browser. By using Axios it’s easy to send asynchronous HTTP request to REST endpoints and perform CRUD operations.

We can make get and post requests. Axios also has a powerful feature called Interceptors that allows us to modify our request or response before they reach their destination.

We are going to consume API from a dummy API - https://jsonplaceholder.typicode.com/users

In this article, we are going to be covering;

  • GET requests with axios
  • POST requests with axios
  • Setting headers with axios
  • Axios Interceptors
  • Making multiple requests with axios
  • Using async and await

Setting up axios in react

In order to use axios in our react app, we need to install and import it in our project. There are various ways to install axios, using npm, yarn, etc.

Using yarn

$ yarn add axios

Using npm

$ npm install axios

Using unpkg CDN

<script src="https://unpkg.com/axios/dist/axios.min.js"></script>

Using jsDelivr CDN

<script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script>

For the article we are going to use the npm package, In your terminal, run;

npx create-react-app my-app

cd my-app

npm start

When the new project has started running in the localhost, install axios using the npm package.

Making GET requests

In this section, we are going to get the names and usernames of users. Inside the src folder, create a new components folder and make a User.js file. Then import React and axios.

import React from 'react';
import axios from 'axios';

Now for this project we are going to use a class based component and initialize state.

 class User extends React.Component {
        state = {
            persons: [],
        } 
  }

export default User;

Next we will use a lifecycle method componentDidMount, here we call axios.get(url) which returns a promise that will resolve to either a response object or an error object. We capture the response in res.

  componentDidMount() {
      axios.get(`https://jsonplaceholder.typicode.com/users`)
      .then(res => {
        const persons = res.data;
        this.setState({ persons });
      })
      .catch(err => {
          console.log(err)
      })
  }

We capture the response and store it in res retrieving the data in res.data, which we store in const persons. Then setState to persons, which updates this.state

We catch any error that occurs and store it in err which is a function and console.log() the error statement.

Finally, we render the data

  render() {
    return (
      <>
        { this.state.persons.map(person =>
        <div style={{borderBottom: "2px solid black"}} >
            <p>NAME - {person.name}</p>
            <p>BRED FOR - {person.username}</p>
       </div>
        )}
      </>
    )
  }
}

We iterate through the response gotten from the API and then display in the render function. We dynamically add some styles to add a border bottom on each on each of the items gotten from the API response.

To make this show up in our browser, import the User.js file in the App.js file.

import User from "./components/User";

function App() {
  return (
    <div className="App">
      <User />
    </div>
  );
}

export default App;

There are different response objects for when our request to the server is successfull.

  • res.data payload returned from the server. By default, Axios expects JSON and will parse this back into a JavaScript object for you.
  • res.status HTTP code returned from the server.
  • res.statusText HTTP status message returned by the server.
  • res.headers The headers sent back by the server.
  • res.config The original request configuration.
  • res.request It is the actual XMLHttpRequest object (when it is running in a browser)

Making POST requests

Now let us make post requests that allow us to add new users to the API.

Make a new file AddUser.js in the components folder. We will create a form that allows for users input and a submit button that enables us to post to the API.

As usual, import react and axios, then create a class based component.

import React from 'react';
import axios from 'axios';

 class AddUser extends React.Component {
       state = {
            NewPerson: [],
        }
 }

export default NewPerson

Let us add a handleChange function, which captures the value of the input field in the form in the setState and updates the state.

 handleChange = event => {
    this.setState({ NewPerson: event.target.value });
  }

Then add a handleSubmit function, which submits the form

  handleSubmit = event => {
    event.preventDefault();

    const user = {
     NewPerson: this.state.NewPerson
    };

    axios.post(`https://jsonplaceholder.typicode.com/users`, { user })
      .then(res => {
        console.log(res);
        console.log(res.data);
      })
  }

In the handleSubmit function, you prevent the default action of the form. Then update the state to the user input. When using the post request, we get the same response object with information that can be used inside the then call. we capture the user input which is then put along the postrequest. We console.log the response because we won't actually modify the API.

Add, the render function that has the form, which makes all this work

  render() {
    return (
      <div>
        <form onSubmit={this.handleSubmit}>
          <label>
            Person Name:
            <input type="text" name="name" onChange={this.handleChange} />
          </label>
          <button type="submit">Add</button>
        </form>
      </div>
    )
  }
}

Lastly we import it to our App.js file.

import User from "./components/User";
import AddUser from "./components/AddUser";

function App() {
  return (
    <div className="App">
      <AddUser />
      <User />
    </div>
  );
}

export default App;

Setting headers with axios

When using an API, it is recommended to go through it's documentation as most APIs have different ways of implementaion.

An API, could require headers. Headers are a key–value pair in clear-text string format separated by a colon.

{

 "key1": "value1",

 "key2": " value2",

}

An API could require you to specify that the content type should be in JSON format.

const config = { headers: { "Content-type": "application/json"}}

Then pass in the object containing the headers as the last argument.

 axios.get(`https://api.thedogapi.com/v1/breeds`, config)

Axios Interceptors

Axios Interceptor is a function that gets called for every HTTP request made and response received by our application. Interceptors transforms/updates each requests before sending it and checks/filters the response before returning it. There are two types of interceptors: request interceptors and response interceptors. They both have 2 callback functions.

How Interceptors work

It is ideal, to put our interceptors in the index.js file, incase we have much files we are working with axios and we dont want to repeat the Interceptors in each file.

import React from "react";
import ReactDOM from "react-dom";
import App from "./App";
import axios from "axios";

//CODE GOES HERE

ReactDOM.render(
  <React.StrictMode>
    <App />
  </React.StrictMode>,
  document.getElementById("root")
);

For instance, we want to show/hide loading statement on every call. and an error message if there is one;

//AN INTERCEPTOR FOR EVERY REQUEST WE SEND

axios.interceptors.request.use(function(config) {
  console.log('Start Ajax Call');
  return config;
}, function(error) {

  console.log('Error');
  return Promise.reject(error);
});
//AN INTERCEPTOR FOR RESPONSE WE GET

axios.interceptors.response.use(function(response) {
  console.log('Done with Ajax call');
  return response;
}, function(error) {
  console.log('Error fetching the data');
  return Promise.reject(error);
});

For every response we get, we can check for status code and work with it.

axios.interceptors.response.use(function(response) {
   if (res.status === 201) {
         console.log('Successfull');
      }

   if(res.status === 404) {
         console.log("Not Found")
    }

      return response;
}, function(error) {
  console.log('Error fetching the data');
  return Promise.reject(error);
});

Making multiple requests with axios

With axios, we can make multiple HTTP requests and handle them simultaneously. We use the axios.all() method which takes in an array of arguments and return single promise object that only resolves when all the arguments passed in the array have been resolved.

  componentDidMount() {
        axios.all([
          axios.get(`https://jsonplaceholder.typicode.com/users`),
          axios.get(`https://jsonplaceholder.typicode.com/posts`)
        ])
        .then(response => {
        console.log(response[0])
        console.log(response[1])
        });
    }

Using async and await

We can use async and await to work with promises. await resolves the promise and returns a value which is then assigned to a variable. .then() is replaced and the promise is resolved with the value stored inside the response variable.

  async componentDidMount() {
      const response = await axios.get(`https://jsonplaceholder.typicode.com/users`)
      console.log(response.data)
  }

Notice that the code is cleaner now.

We have seen multiple ways axios can be used in our react application to create HTTP requests and handle responses and why it is a better approach than using a normal fetch API

Source code at Github