Published on
NodeJS

วิธีการดึงข้อมูล API ด้วยการใช้ axios

fetch-api-with-axios
Discord

ต้องบอกว่า axios เป็น HTTP Client Library ตัวนึงที่คนนิยมใช้งานมากๆ เผลอๆ จะมากกว่า Fetch API ที่เป็น global module ของ Browser ซะอีก (รวมถึงฝั่ง Node.js ที่เพิ่งจะ built-in support ใน v18.0) วันนี้เลยมาเขียนบทความการใช้งาน axios ในแบบคร่าวๆ ไว้ครับ จริงๆ เรียกว่าสรุปและอ่านจาก Docs มากกว่า 🤣

Axios คืออะไร?

axios เป็น Promise based HTTP Client Library เพื่อทำการดึงข้อมูล ส่งข้อมูล และเชื่อมต่อกับ API โดยสามารถใช้งานได้ทั้งผ่าน Browser และ Node.js ซึ่ง Features หลักๆ ที่น่าสนใจของ axios คือ:

  • รองรับ Promise API
  • การแปลงข้อมูล reauest และ response
  • รองรับการ cancel request
  • ทำ Intercept headers ได้
  • ป้องกัน XSRF
  • รองรับ TypeScript (จริงๆ ต้องบอกว่าเป็นมาตรฐานไปแล้ว Library ไหนไม่รองรับน่าจะแปลกกว่า)

Browser Support

ChromeFirefoxSafariOperaEdgeIE
Latest ✔Latest ✔Latest ✔Latest ✔Latest ✔11 ✔

การติดตั้ง

เราสามารถใช้งาน axios ได้ทั้งผ่าน Browser หรือ Node.js ก็ได้

ติดตั้งด้วย NPM หรือ Yarn:

npm install axios
# yarn add axios

หรือถ้าใช้งานผ่าน Browser ก็แทรกไปใน HTML ผ่าน CDN ได้เลย

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

ตัวอย่างการใช้งาน

ถ้าเราใช้งานแบบ CommonJS เวลา import ด้วย require() เราจะใช้แบบด้านล่างนี้ เพื่อให้ Editor มันสามารถที่จะ support Autocomplete / Intellisense

const axios = require('axios').default;

แบบ ES Module

import axios from 'axios';

GET Request

ตัวอย่างการใช้ GET

const url = 'https://your-api-server';

axios.get(url).then((response) => {
  // handle success
  console.log(response);
})
.catch((error) => {
  // handle errors
});

ใช้งาน GET แบบส่ง Params

const url = 'https://your-api-server/users?id=12345';

axios.get(url).then((response) => {
  // handle success
  console.log(response);
})
.catch((error) => {
  // handle errors
});

ซึ่งจะมีค่าเท่ากับแบบนี้ (เอา query params ออกจาก URL แล้วใช้ options ส่งเป็น args ไปใน axios.get())

const url = 'https://your-api-server/users';

const options = {
  params: {
    id: 12345
  }
};

axios.get(url, options).then((response) => {
  // handle success
  console.log(response);
})
.catch((error) => {
  // handle errors
});

async/await

เราสามารถที่จะใช้การเขียนแบบ async/await ได้ เช่นกัน

async function getUser() {
  try {
    const response = await axios.get('/your-api');
    console.log(response);
  } catch (error) {
    console.error(error);
  }
}

POST Request แบบ JSON

การส่ง POST Request แบบ JSON ใช้ การส่ง payload เป็น args ตัวที่ 2 แบบนี้

const payload = { title: 'Hello Axios' };
axios.post('/posts', payload);

โดยที่ default ตัว payload จะเป็น JSON และก็ Content-Type จะเป็น application/json

POST Request แบบ application/x-www-form-urlencoded

เราสามารถส่ง POST Request แบบ application/x-www-form-urlencoded ได้นอกเหนือจาก JSON โดยการใช้ URLSearchParams (ตัวนี้ไม่ได้รองรับทุก Browser นะ)

const params = new URLSearchParams({ title: 'Hello Axios' });
axios.post('/posts', params);

POST Request แบบ multipart/form-data

การส่งแบบ multipart/form-data เราจะใช้ FormData ใน Browser เราสามารถเรียกใช้ FormData API ได้ ส่วนถ้าเป็น Node.js ต้องใช้ Library เพิ่มเติม เช่น form-data

const formData = new FormData();
formData.append('title', 'Hello Axios');

axios.post('/posts', formData);

ถ้าเป็น Node.js จะใช้ form-data library

const FormData = require('form-data');
const form = new FormData();

axios.post('/posts', form)

Auto Serialization to FormData

ตัว Axios ก็ยังรองรับการ Serialize JSON เป็น FormData ให้อัตโนมัติ ถ้า Content-Type เป็น multipart/form-data เช่น

import axios from 'axios';

axios.post('/posts', { title: 'Hello Axios' }, {
  headers: {
    'Content-Type': 'multipart/form-data'
  }
}).then(({data})=> console.log(data));

Method ของ Axios

นอกจากนี้ ตัว axios ยังรองรับ HTTP Method เป็นชื่อเดียวกับ function เลย ตัวอย่าง

axios.get(url);

axios.post(url, payload);

axios.put(url, payload);

axios.patch(url, payload);

axios.delete(url);

การ Custom Instance

เราสามารถ custom instance เพื่อกำหนดค่า config เองได้ เช่น กำหนด headers หรือกำหนด baseURL หรือ timeout เป็นต้น

// Set config defaults when creating the instance
const instance = axios.create({
  baseURL: 'https://api.example.com',
  headers: {
    'My-Custom-Header': 'custom-header'
  }
  timeout: 5000
});

instance.defaults.headers.common['Authorization'] = 'token';

ตัวอย่างการ set token กรณีมีต้อง require token ในบาง Request แบบคร่าวๆ

const instance = axios.create();

instance.interceptors.request.use(
  (config) => {
    // get token from cookies / session / localStorage
    const token = getSessionToken();
    if (token) {
      config.headers['x-access-token'] = token;
    }
    return config;
  },
  (error) => {
    return Promise.reject(error);
  }
);

การจัดการ Error

ตัว Error ที่ server ตอบกลับมาจะเข้า catch() กรณีที่ไม่ใช่ HTTP 2xx โดยเราจะได้ response อยู่ในรูปแบบ error.response ตัวอย่างเช่น

axios.get('/some-api')
.catch(function (error) {
  if (error.response) {
    // The request was made and the server responded with a status code
    // that falls out of the range of 2xx
    console.log(error.response.data);
    console.log(error.response.status);
    console.log(error.response.headers);
  } else if (error.request) {
    // The request was made but no response was received
    // `error.request` is an instance of XMLHttpRequest in the browser and an instance of
    // http.ClientRequest in node.js
    console.log(error.request);
  } else {
    // Something happened in setting up the request that triggered an Error
    console.log('Error', error.message);
  }
  console.log(error.config);
});

หรือเราสามารถ ใช้ toJSON เพื่อจัดการข้อมูลของ HTTP error ได้

axios.get('/some-api').catch(function (error) {
  console.log(error.toJSON());
});

การ Cancel Request

เป็น feature ที่ค่อนข้างมีประโยชน์ กรณีที่เราทำการเรียก request ไปแล้ว และอยากยกเลิกมัน ก็สามารถทำได้ผ่านตัว AbortController

const controller = new AbortController();

axios.get('/path/to/api', {
   signal: controller.signal
}).then(function(response) {
   //...
});
// cancel the request
controller.abort();

Credentials

Request ที่ยุ่งกับ cookies และ cross-site Access-Control เราสามารถใช้ withCredentials ได้ ตัวอย่าง

import axios from 'axios';

const instance = axios.create({
  withCredentials: true
});

instance.get('/todos');

# หรือ
axios.post('/login', { email, password }, { withCredentials: true });

ทั้งหมดนี้ก็เป็นการใช้งาน axios แบบคร่าวๆ ซึ่งจริงๆ ก็ไม่มีอะไรมาก การ custom อื่นๆ หรือการประยุกต์ใช้งานในรายละเอียดอื่นๆ สามารถอ่านเพิ่มเติมได้ที่ Docs ของ axios ได้เลยครับ

Happy Coding ❤️

Authors
Discord