Flutter初心者のRetrofit学習自分用メモ
やりたいこと
FlutterのAPI通信をRetrofitを使用して行いたい!
過去にRetrofitのみでAPI連携の学習をしていたけど、今回はfreezedとdioを使用した方法で学習しました!
プログラミング初心者の自分用に用語も一緒にまとめているので要所要所で少し脱線してしまっているかもです…
1. インストール
今回はRetrofitが推奨しているライブラリ+freezedとdioを使用します。
pubspec.yamlは下記のように設定しました。(コメントはライブラリの簡単な説明です。)
dependencies:
retrofit:
logger://ログ出力
json_annotation://JSONファイルを扱うやつ
dio://HTTPリクエストの実行に使用
dev_dependencies:
retrofit_generator://APIクライアントを自動生成
build_runner://自動生成させるために必要
json_serializable://シリアライズ・デシリアライズ部分の処理を自動生成
freezed://データクラスとそれに必要な機能を自動生成
終わったらpubgetします
flutter pub get
2. データモデルを作成する
HTTPリクエストとレスポンスの構造を定義します。モデルクラスも定義し、どのようにシリアライズ/デシリアライズされるかを指定します。
import 'package:freezed_annotation/freezed_annotation.dart';
part 'example.freezed.dart';
part 'example.g.dart';
class Task with _$Task {
const factory Task({
required String id,
required String name,
}) = _Task;
factory Task.fromJson(Map<String, dynamic> json) => _$TaskFromJson(json);
//↑ここでデシリアライズしている!
}
※シリアライズ(DartオブジェクトからJSONへの変換)の部分はretrofit
とjson_serializable
が裏側で行っているので記述の必要はないです!
以下のコマンドを実行してデータモデルの関連ファイル(example.freezed.dartとexample.g.dart)を自動生成します。
flutter pub run build_runner build --delete-conflicting-outputs
ここまででいきなり出てきた用語のまとめ…
モデルクラス: データを整理・管理するためのクラス。
シリアライズ: オブジェクトをデータ(JSON)に変換すること。
デシリアライズ: データ(JSON)をオブジェクトに変換すること。
3. APIクライアントを生成する
HTTPリクエストとレスポンスの構造を定義します。
import 'package:dio/dio.dart';
import 'package:retrofit/retrofit.dart';
part 'example_api_client.g.dart';
(baseUrl: 'https://api.example.com')
//APIエンドポイントを呼び出すメソッドを定義
abstract class RestClient {
factory RestClient(Dio dio, {String? baseUrl}) = _RestClient;
//DioインスタンスとbaseUrlをパラメータとして受け取る
('/tasks')//APIからデータの取得を行うメソッド
Future<List<Task>> getTasks();//取得結果が`List<Task>`として返される
//他にもPOSTとかAPI通信で行いたいメソッドをここに入れる…
}
以下のコマンドを実行してAPIクライアント(part 'example_api_client.g.dart';)を自動生成します。
flutter pub run build_runner build --delete-conflicting-outputs
補足:URLとパラメータ
パラメータとはユーザーが特定のウェブページやアプリケーションに要求する内容をURLの末尾に入れてカスタマイズできるやつのことです。パラメータは通常、「クエリパラメータ」または「クエリ文字列」と呼ばれ、URLの末尾に「?」記号の後に追加されます。
http://example.com/page?parameter1=value1¶meter2=value2
ttp://example.com/page →ベースURL
? →?の後にクエリパラメータが続く
parameter1=value1 →キーと値のペア
& →クエリパラメータ同士を区切るための記号
4. リポジトリクラスを作成する
import 'package:dio/dio.dart';
import 'package:your_project_name/your_path/rest_client.dart';
import 'package:your_project_name/your_path/task.dart';
class TaskRepository {
final RestClient _client;//先ほど別ファイルで作成したAPIクライアントを作成
TaskRepository([RestClient? client])
: _client = client ?? RestClient(Dio());
Future<List<Task>> getTasks() async {
try {
// APIからタスクを取得し、成功したらそのままリターン
return await _client.getTasks();
} catch (e) {
// エラーが発生した場合は例外をスロー
throw e;
}
}
}
4. リポジトリを呼び出して使用する
void main() async {
final repository = TaskRepository(); //先ほど別ファイルで作成したリポジトリを作成
try {
// APIを呼び出して結果を取得
final tasks = await repository.getTasks();
print(tasks);
} catch (e) {
// API呼び出し中にエラーが発生した場合はここでキャッチ
print('Failed to load tasks: $e');
}
}
まとめ
Retrofit
とDio
、freezed
といったライブラリやパッケージを組み合わせることで、APIクライアントの開発をより簡単かつ効率的に行うことができました!
初心者の自分は先輩エンジニアが開発の際にライブラリを選定する理由や、どのライブラリがコードの簡素化や効率化に寄与するのか、というポイントも学習することが大事だな…と感じました。
アルサーガパートナーズ株式会社のエンジニアによるテックブログです。11月14(木)20時〜 エンジニア向けセミナーを開催!詳細とご応募は👉️ arsaga.jp/news/pressrelease-cheer-up-project-november-20241114/
Discussion