728x90
1. 배경
데이터베이스에서 데이터를 가져와 앱 프론트에 표시할 때, 서버와 API통신하는 경우가 많은데, API 통신 코드를 모듈화하여 유지보수가 용이하게 할 필요성이 있었다. 다양한 기능을 가진 Interceptor를 옵션에 추가해 개발 시 디버깅이 편하게 해야 했다.
2. 요구사항
2.1. dio
인기있는 http 라이브러리다. 다양한 기능이 포함되어있다.
2.2. alice
https://pub.dev/packages/alice
api 통신을 디버깅하거나 receiveTimeout 등의 설정을 할 수 있다.
2.3. hive
로그인 시 jwt token을 hive에 저장하고, API 통신 시 헤더에 이를 추가하여 유저임을 인증할 수 있다.
2. 코드
import 'dart:async';
import 'package:alice/alice.dart';
import 'package:hive/hive.dart';
import 'package:papsm/app/data/environment/environment.dart';
import 'package:papsm/app/dio/constant_dio.dart';
import 'package:dio/dio.dart';
import 'package:dio_cache_interceptor/dio_cache_interceptor.dart';
import 'package:flutter/material.dart';
import 'package:papsm/app/dio/interceptor/logging_interceptor.dart';
class DioHelper {
Dio? dio;
Alice? alice;
DioHelper() {
alice = Alice(showNotification: false);
final options = BaseOptions(
receiveTimeout: ConstantDio.timeout,
connectTimeout: ConstantDio.timeout,
);
options.baseUrl = EnvironmentConstant.config ?? 'test';
dio = Dio(
options,
);
dio!.interceptors.add(LoggingInterceptors());
dio!.interceptors.add(alice!.getDioInterceptor());
dio!.interceptors.add(DioCacheInterceptor(options: dioCacheOptions));
}
Future<Map<String, dynamic>> get(String url,
{dynamic param, bool? refresh}) async {
final userModelBox = await Hive.openBox('userModelBox');
String? token = userModelBox.get('token');
dio!.options.headers["authorization"] = 'Bearer $token';
final response = await dio!.get(
url,
queryParameters: param,
options: refresh == true
? dioCacheOptions.copyWith(policy: CachePolicy.refresh).toOptions()
: null,
);
return response.data as Map<String, dynamic>;
}
Future<Map<String, dynamic>> post(String url, dynamic body) async {
final userModelBox = await Hive.openBox('userModelBox');
String? token = userModelBox.get('token');
dio!.options.headers["authorization"] = 'Bearer $token';
final response = await dio!.post(url, data: body);
return response.data as Map<String, dynamic>;
}
Future<Map<String, dynamic>> patch(String url, dynamic body) async {
final userModelBox = await Hive.openBox('userModelBox');
String? token = userModelBox.get('token');
dio!.options.headers["authorization"] = 'Bearer $token';
final response = await dio!.patch(url, data: body);
debugPrint('[Response] ${response.data.runtimeType} ${response.data}');
return response.data as Map<String, dynamic>;
}
Future<Map<String, dynamic>> put(String url, dynamic body) async {
final userModelBox = await Hive.openBox('userModelBox');
String? token = userModelBox.get('token');
dio!.options.headers["authorization"] = 'Bearer $token';
final response = await dio!.put(url, data: body);
debugPrint('[Response] ${response.data.runtimeType} ${response.data}');
return response.data as Map<String, dynamic>;
}
Future<Map<String, dynamic>> delete(String url, dynamic body) async {
final userModelBox = await Hive.openBox('userModelBox');
String? token = userModelBox.get('token');
dio!.options.headers["authorization"] = 'Bearer $token';
final response = await dio!.delete(url, data: body);
debugPrint('[Response] ${response.data.runtimeType} ${response.data}');
return response.data as Map<String, dynamic>;
}
void errorCheck(Map<String, dynamic> result, String err) {
if (result['code'] != 200) {
throw err;
}
}
}
CacheOptions dioCacheOptions = CacheOptions(
store: MemCacheStore(),
hitCacheOnErrorExcept: [401, 403],
maxStale: const Duration(hours: 6),
);
DioHelper 생성자에서 .env 파일에서 저장된 서버의 주소로 baseUrl을 설정하였다.
dio interceptor로 LoggingInterceptor를 추가하여 API 통신 시 보내는 데이터와 받는 데이터를 로깅하는 기능을 추가했다.
dio interceptor로 CacheInterceptor를 추가하여 동일한 API 통신 시 6시간 마다 MemCacheStore에 저장하여 재활용할 수 있도록 하였다. (새로 요청하려면 refresh option을 true로 두면 된다.)
hitCacheOnErrorExcept에서 401, 403 error가 발생했을 때는 다시 요청하도록 했다.
'개발 > Flutter' 카테고리의 다른 글
Flutter :: Color 저장해서 변수로 재사용하기 (0) | 2023.08.14 |
---|---|
Flutter :: TextStyle 저장하여 관리하기 (0) | 2023.08.14 |
Flutter :: 앱 아이콘(app_icon.png) 설정하기 (4) | 2023.01.26 |
Flutter 츠누봇 [Pull Request] :: [학식] 페이지 UI 퍼블리싱 (2) | 2022.12.07 |
Flutter 츠누봇 [Pull Request] :: [소식] 페이지 API 연동 (0) | 2022.12.07 |