こんにちは。
名古屋スタジオでクライアントエンジニアを担当している松下です。
今回はUnityでGraphQLを使った通信を行う方法を紹介します。
GraphQLについて
GraphQLはAPI向けに作られたクエリ言語およびランタイムです。
イメージとしてはSQLでクエリを書く感覚と似ています。
欲しい情報はクエリを書いてリクエストするためエンドポイントは1つで柔軟なデータ取得ができます。
データの取得 (Query)、更新 (Mutation)、購読 (Subscription) の3つをサポートしており、
Subscriptionを活用するとリアルタイムな通信もできるのが特徴です。
GraphQLのサンプルを実行してみる
ひとまずGraphQLを体験するために公開されているGraphQLのAPIのサンプルを試してみます。
ありがたいことに検索するとGraphQLのPublicなAPIがいくつも見つかります。
https://github.com/APIs-guru/graphql-apis
今回はその中で特定の都市の天気情報を返してくれるGraphQL Weather APIを実行してみます。
https://graphql-weather-api.herokuapp.com/
上記のリンクをクリックするとブラウザ上で試すことができます。
GraphQLのクエリを書くのに必要なスキーマ情報は画面右端のDOCSを開くことで確認できるので、一度どんなスキーマが用意されているか確認してみるとよいでしょう。
試しに名古屋の天気を取得してみます。
query {
getCityByName(name: "Nagoya") {
id
name
country
coord {
lon
lat
}
weather {
summary {
title
description
icon
}
timestamp
}
}
}
結果は以下のようになりました。
現在の名古屋の天気はclear sky(晴れ)ですね。良い感じに取得できています。
ブラウザ上で簡単に試せる環境が整ってるのはかなり嬉しいですね。
ブラウザを利用しない場合はAltairというクライアントアプリをインストールしておくのがオススメです。
https://altair.sirmuel.design/
上記のサンプルは、データの取得(Query)のみですが、認証が必要になったり、リアルタイムな購読(Subscription)を活用する場合はクライアントアプリのほうが便利です。
サーバにAWS AppSyncなどを活用した場合、エンドポイントがQueryとSubscriptionでわかれることがあるのですが、そうした柔軟な設定はAltairでないとできませんでした。
UnityからGraphQLを使った通信を試してみる
UnityからGraphQLでAPIにアクセスするためにgraphQL-client-unityを使ってみます。
ひとまず上記からUnityプロジェクトごとダウンロードします。
Unityのパッケージも用意されており、graphQl-client-unity-v2.unitypackageをimportすることでも導入できるのですが、必要なPluginが不足しています。
パッケージから導入する場合は別途入れる必要があり、動作確認するだけでしたらプロジェクトごと起動した方がスムーズです。
付属のシーンを起動する
プロジェクト内のDemoにUsers/userExampleが用意されており、起動してすぐにテスト用の接続が試せます。
下記の画像はDemoのuserExampleでユーザの取得(Query)、保存(Mutation)、登録時の購読(Subscription)を試した様子です。
Query、Mutation、Subscriptionと一通りの通信方法が実行できます。
Queryを実行すると今までに登録されたUserの情報が確認でき、Mutationを実行すると新たにUserの登録ができます。
また、Subscriptionを実行した状態でMutationを行うと、Subscription側にMutationで登録したUserの反映を確認できます。
サンプルのソースコードは一般的なUnityWebRequestやClientWebSocketで実装されているため自身の要件に合わせてカスタマイズできそうです。
特にSubscriptionのコードに関しては情報が少ないため参考になります。
新しい接続先を追加する
もちろんサンプルの接続先以外にも新しい接続先を追加できます。
例としてブラウザから試したGraphQL Weather APIにUnityから繋いでみます。
Projectで右クリックして新しいApiReferenceを作成します。
適当にWeatherと命名しブラウザで実行したものと同じUrlを入力してIntrospectを実行します。
その後「Create New Query」から新しいクエリ「GetWeather」を定義します。
GraphQLでは指定できるスキーマ情報が取得できるため、プルダウンから取得したいパラメータを指定するだけでクエリの生成ができます。
ApiReferenceができたら、userExampleのシーンをコピーしてWeather用のシーンを作成します。
今回はQueryのみ実行するため、MutationとSubscriptionのGameObjectは削除しました。
またWetherのクエリの実行には都市名を入力するInputFieldが必要なので追加しておきます。
シーンの準備ができたらUserのコンポーネントの代わりに以下のようなWeatherのコンポーネントを作成してアタッチします。
public class Weather : MonoBehaviour
{
public GameObject loading;
[Header("API")]
public GraphApi weatherApi;
[Header("Query")]
public InputField cityName;
public Text queryDisplay;
public async void GetQuery(){
loading.SetActive(true);
GraphApi.Query query = weatherApi.GetQueryByName("GetWeather", GraphApi.Query.Type.Query);
query.SetArgs(new{name = cityName.text});
UnityWebRequest request = await weatherApi.Post(query);
loading.SetActive(false);
queryDisplay.text = HttpHandler.FormatJson(request.downloadHandler.text);
}
}
実行すると以下のような結果が得られました。
ブラウザ上で取得した結果と同じものがUnityからでも取得できました。
認証が必要な場合について
今回のサンプルの実行では認証が不要だったのでスムーズですが、
認証が必要なAPIを叩く場合、ApiReferenceのIntrospectが通らなかったりします。
その場合、HttpHandler.csにHeader情報を設定できる箇所があります。
request.SetRequestHeader("Content-Type", "application/json");
request.SetRequestHeader("Authorization", "Bearer " + authToken);
サーバ側の設定に応じて認証が変わったりしますので必要に応じて設定をしてみるとよいでしょう。
まとめ
今回はGraphQLの簡単なサンプルの実行方法についてご紹介しました。
データ取得のみのご紹介でしたが、Subscriptionなども利用すればリアルタイム性の高い便利な機能も実装できます。
また、手軽に手を動かしながら試せる環境があるのは学習しやすく感じました。
よければ試してみてはどうでしょうか。