【俺的理解】Ajaxとは

公開日: 

【俺的理解】シリーズは、自分が調べた内容を噛み砕いて、実際に試してみたり、まとめたりした記事です。 全力で調べて、自分が納得したことしか書きませんが、万が一間違っていることがありましたら twitter などで指摘していただけるとありがたいです。

雑な概要

Ajax というのは

  • asynchronous
  • JavaScript
  • XML

の 3 つの単語を組み合わせた造語です。単語からなんとなく想像できますが、雑に概要を説明するとブラウザで JavaScript を使用して、非同期的な通信をおこなうことです。

歴史から辿る Ajax

web サイトの歴史を説明している記事があり、とてもわかりやすかったのでそれを参考に内容を噛み砕いてまとめます。

https://blog.jxck.io/entries/2022-09-30/XMLHttpRequest.html

1. HTML と CSS の動かない web サイト時代

これは特に難しいことはないような気はします。

本当に HTML で構成された見た目を、CSS で装飾しただけのサイト。

2. JS により web サイトに少し動きが出てきた時代

JavaScript の台頭

新世界に進出した麦わら海賊団のように、ブラウザ上で JavaScript が暴れ出します。JavaScript が普及してくると、ボタンを押すと何かの大きさが変わったり、web サイトに動きが出てくるようになります。

この時代の動きが生まれた HTML のことを、動きがない HTML と比較して、 Dynamic HTML(DHTML) と呼ぶようなこともあったらしいです。

ただし

まだ Ajax は生まれていないので、データの更新は画面の更新と同時に行われるのが普通。今でこそ、Google Map などで常にデータを更新しながらスクロールや拡大をしていますが、非同期的にデータを取得する術がなかったときは拡大などの操作のたびに画面遷移を伴っていました。

3. そして生まれる Ajax

XMLHttpRequests の出現

ここで XMLHttpRequests(XHR) というものが出現します。今までは画面更新と共に、データを取得してそれを表示するのが普通だったんですが、これを利用することで画面更新を伴わずにデータを非同期的に取得して画面に反映させることができるようになります。

Web は XHR と DHTML で大きく変わるという発想自体に名前をつけたのが Ajax である

こういう文章が参考記事の中で書かれていて、とても腑に落ちたような気がしました。この 1 文にこの記事の答えが詰まっています。

実際にやってみよう

理屈はわかったので実際に Ajax してみましょう。PokeAPIを利用し

  • XMLHttpRequests
  • fetch
  • axios

の 3 種類の方法を使用して非同期的にピカチュウの情報を取得してみます。

このデータ取得時にはもちろん、画面遷移を伴っていませんし、リクエストが終わるまで画面がフリーズするようなこともありません。

全体のコード

React を用いて書かれていますが、別に React はこの内容の本質ではないので気にしないでください。

sample.js
import { useState } from 'react';
import axios from 'axios';

const AjaxSample = () => {
  const [xhrResponse, setXhrResponse] = useState();
  const [fetchResponse, setFetchResponse] = useState();
  const [axiosResponse, setAxiosResponse] = useState();

  // ピカチュウの情報を取得
  const url = 'https://pokeapi.co/api/v2/pokemon/pikachu';

  // XMLHttpRequestsを利用してリクエストを送る
  const requestWithXHR = () => {
    function reqListener() {
      console.log('response from XHR', this.responseText);
      setXhrResponse('get from XHR');
    }
    const req = new XMLHttpRequest();
    req.addEventListener('load', reqListener);
    req.open('GET', url);
    req.send();
  };

  // fetch APIを利用してリクエストを送る
  const requestWithFetch = () => {
    fetch(url).then((response) => {
      console.log('response from fetch', response);
      setFetchResponse('get from fetch');
    });
  };

  // axiosを利用してリクエストを送る
  const requestWithAxios = () => {
    axios.get(url).then((response) => {
      console.log('response from axios', response);
      setAxiosResponse('get from axios');
    });
  };

  return (
    <>
      <>
        <button onClick={requestWithXHR}>XHR</button>
        <div>{xhrResponse}</div>
      </>
      <>
        <button onClick={requestWithFetch}>fetch</button>
        <div>{fetchResponse}</div>
      </>
      <>
        <button onClick={requestWithAxios}>axios</button>
        <div>{axiosResponse}</div>
      </>
    </>
  );
};

function App() {
  return <AjaxSample />;
}

export default App;

全体のコードはこんな感じ。ボタンを押すとそれぞれの方法で通信をし、データを取得してきます。取得できたら、ラベルで取得できたことを表示します。

それぞれの処理を見ていきます。

XMLHttpRequests

https://developer.mozilla.org/ja/docs/Web/API/XMLHttpRequest

Ajax の始まりと言っても過言ではなさそうな、XMLHttpRequests を利用してみます。

sample.js
const requestWithXHR = () => {
  function reqListener() {
    console.log('response from XHR', this.responseText);
    setXhrResponse('get from XHR');
  }
  const req = new XMLHttpRequest();
  req.addEventListener('load', reqListener);
  req.open('GET', url);
  req.send();
};

XMLHttpRequests はライブラリなどではなく、JavaScript の組み込みオブジェクトです。

Promise を返すわけではなく、イベントに対してハンドラを登録してデータ取得後の処理をするスタイル。

初めて書きましたが、めんどくさいなっていう印象。

fetch

https://developer.mozilla.org/ja/docs/Web/API/Fetch_API

sample.js
const requestWithFetch = () => {
  fetch(url).then((response) => {
    console.log('response from fetch', response);
    setFetchResponse('get from fetch');
  });
};

fetch もライブラリなどではなく、ブラウザの標準 API です。

XMLHttpRequests のより良い代替として、用意されたらしいです。

そこそこ見知った書き方。Promise が返ってくるので、then などを使用して、データ取得後の処理を開くことができます。

axios

https://github.com/axios/axios

sample.js
const requestWithAxios = () => {
  axios.get(url).then((response) => {
    console.log('response from axios', response);
    setAxiosResponse('get from axios');
  });
};

axios はライブラリとして npm などを用いて導入する必要があります。

使い勝手としては、fetch と似ている印象でしたが、どっちかといえば axios の方が色々便利そうだなぁという印象。

そこらへんの違いの詳細などは今回はあまり触れないでおきます。

比較

返り値はそれぞれ

  • XMLHttpRequests: string
  • fetch: object(Response)
  • axios: object

使い勝手の点で言うと、圧倒的に fetchaxios の方が使いやすく、XMLHttpRequests を使う理由は特にないかと思います。

まとめ

3 つの方法で Ajax してみました。

やはり歴史的な背景が絡むと面白みも増すし、頭に入ってきやすいですね。だいぶ理解しました。

自分が Ajax って何?と聞かれたらこう答えます。

クライアント側で JavaScript を用いて非同期的にデータを取得してくる概念の名前のこと

では

Bye