はじめに
こんにちは、nukkyです。
今回はReactでhttpリクエストを行ってみようと思います。使用するライブラリは「axios(アクシオス)」になります。
axiosとは
axiosとは、HTTP通信を簡単に扱えることができるJavaScriptライブラリです。HTTPリクエストを送ったり、JSONを取得したりするのが簡単に実装することが出来ます。
Make XMLHttpRequests from the browser
Make http requests from node.js
Supports the Promise API
https://github.com/axios/axios
特徴としては作者のページに上のような記述があります。内容を簡単に訳すと以下になります。
- ブラウザからXMLHttpRequestが出来ます。
- node.jsからhttp requestsが出来ます。
- Promiseを扱うことが出来ます。
XMLHttpRequest
簡単に言ってしまえばAjaxの事です。以下Wikipediaより引用。
XMLHttpRequest (XHR) は、JavaScriptなどのウェブブラウザ搭載のスクリプト言語でサーバとのHTTP通信を行うための、組み込みオブジェクト(API)である。
すでに読み込んだページからさらにHTTPリクエストを発することができ、ページ遷移することなしにデータを送受信できるAjaxの基幹技術である。
XMLHttpRequestを利用したWebアプリケーションは非常に多く存在し、例として、Google マップ、Facebookなどが挙げられる。
出典: フリー百科事典『ウィキペディア(Wikipedia)』
Promise
PromiseはJavaScriptで非同期処理を扱う際に最終的な完了もしくは失敗を表すオブジェクトです。
Promiseを使うと、(コールバックのように)特定のコードの実行完了を待ってから次のコード片を実行できるようになります。
Promiseは、以下の3つのステートの1つを取ります。
- pending: 非同期操作が完了していない
- fulfilled: 操作が完了し、Promiseが値を1つ持つ
- rejected : 操作がエラーまたは失敗で終了した
pending状態でないPromiseは安定しています。いったん安定したPromiseのステートは更新されず、他のステートに移行することはできません。
準備
インストールしたいプロジェクトで以下のコマンドを実行します。
1 | $ npm install axios |
私はnpmを使用していますが作者のページでは、bower、yarn、cdnでのインストール方法も記載されているので、そちらを扱う際は参照していただければと思います。
https://github.com/axios/axios
実装
axiosはGETやPOSTなど、様々なHTTPリクエストを投げることが出来ます。
まずはGETリクエストを送るメソッドの構文について解説します。
1 2 3 4 5 6 7 8 | axios .get('https://hogehoge', { params: {送りたいパラメーターの指定} }) .then((results) => { // 通信に成功してレスポンスが返ってきた時に実行したい処理 } .catch((error) => { // 通信に失敗してレスポンスが返ってこなかった時に実行したい処理 } |
axios.getは引数を二つとり、第一引数にはエンドポイント、第二引数に渡したいパラメータをparamsで指定します。
そして、上記の書き方だとレスポンスが返ってきたかどうかで挙動が変わります。
レスポンスが返ってきた時
– 返ってきたデータがresultsの中に入り、thenが走る。
レスポンスが返ってこなかった時
– errorメッセージがerrorに入り、catchが走る。
このような流れでaxios.get()は動きます。
resultsの中身
成功パラメータであるresultsの中身は様々なデータが入ってるので、今一度確認しておきましょう。
1 2 3 4 5 | results.data; // レスポンスデータ results.status; // ステータスコード results.statusText; // ステータステキスト results.headers; // レスポンスヘッダ results.config; // config |
基本的にはレスポンスデータを取得します。デフォルトではステータスコードが2xx系以外だと、レスポンスはエラーとして返されます。次に、エラーハンドリングの方法を解説します。
エラーハンドリング
axiosのエラーハンドリングは以下のサンプルのように直感的に書くことが出来ます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | .catch((error) => { if (error.response) { // このリクエストはステータスコードとともに作成されます // 2xx系以外の時にエラーが発生します console.log(error.response.data); console.log(error.response.status); console.log(error.response.headers); } else if (error.request) { // このリクエストはレスポンスが返ってこない時に作成されます。 // `error.request`はXMLHttpRequest のインスタンスです。 console.log(error.request); } else { //それ以外で何か以上が起こった時 console.log('Error', error.message); } console.log(error.config); } |
上でステータスコードが2xx系以外だとエラーとして解釈されると書きましたが、自分でそのレンジを設定することも可能です。
1 2 3 4 5 6 | axios .get('https://hogehoge', { validateStatus: function (status) { return status < 500; // ステータスコードが500以上の時リジェクト } } }) |
上の場合は5xx以外ならthen()の処理に入るレンジに設定しています。
カスタムヘッダーの付与
アプリによっては独自のカスタムヘッダをリクエストに付与する必要があることが多いですが、axiosならそれも簡単に行うことができます。
1 | axios.get(エンドポイント, { headers: {'X-SPECIAL-TOKEN': 'abcde'} }) |
React+axiosでhttpリクエストのサンプル
axiosの基本は抑えたと思うので、最後にタイトル通りReactでaxiosを使用するサンプルを書きたいと思います。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 | import React, { Component } from 'react'; import axios from 'axios'; const GEOCODE_ENDPOINT = 'https://maps.googleapis.com/maps/api/geocode/json'; class App extends Component { constructor(props) { super(props); this.state = { place: '東京タワー', }; } handleGetLatAndLng() { // Google Maps APIが指定した必須パラメータ(この場合はaddress)をparamsに渡す。 axios .get(GEOCODE_ENDPOINT, { params: { address: this.state.place } }) .then((results) => { // 以下のGoogle API のレスポンスの例を元に欲しいデータを取得 const data = results.data; const result = data.results[0]; const location = result.geometry.location; this.setState({ address: result.formatted_address, lat: location.lat, lng: location.lng, }); }, ) .catch((error) => { if (error.response) { // このリクエストはステータスコードとともに作成されます // 2xx系以外の時にエラーが発生します console.log(error.response.data); console.log(error.response.status); console.log(error.response.headers); } else if (error.request) { // このリクエストはレスポンスが返ってこない時に作成されます。 // `error.request`はXMLHttpRequest のインスタンスです。 console.log(error.request); } else { //それ以外で何か以上が起こった時 console.log('Error', error.message); } console.log(error.config); }); } render() { return ( <div className="app"> <h1 className="app-title">緯度軽度検索</h1> <p> 土地名: {this.state.place} </p> <p> 経度: {this.state.lat}</p> <p> 経度: {this.state.lng}</p> <input type="button" value="経度・緯度を検索" onClick={() => this.handleGetLatAndLng()} /> </div> ); } } export default App; |
POST
POSTの場合は引数にPOSTパラメータを付与する形になります。
1 2 | const data = { id : '1234', name : 'nukky' }; axios.post('http://hogehoge', data) |
さいごに
axios如何だったでしょうか、駆け足での説明となってしまいましたが、クライアントのアプリで使用するような直感的でこちらの手間がかなり簡略化されるいいライブラリだと思いました。