You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

202 lines
6.0 KiB

import 'package:dating_touchme_app/controller/global.dart';
import 'package:dating_touchme_app/controller/message/conversation_controller.dart';
import 'package:dating_touchme_app/controller/discover/room_controller.dart';
import 'package:dating_touchme_app/controller/overlay_controller.dart';
import 'package:dating_touchme_app/im/im_manager.dart';
import 'package:dio/dio.dart';
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
import 'package:get/get.dart' hide Response;
import 'package:get_storage/get_storage.dart';
import '../config/env_config.dart';
import '../pages/mine/login_page.dart';
/// API类型枚举,用于区分不同的baseUrl
enum ApiType {
main, // 主API
}
/// 网络请求配置类
class NetworkConfig {
static const int connectTimeout = 30000;
static const int receiveTimeout = 30000;
/// 创建Dio实例
static Dio createDio({ApiType type = ApiType.main}) {
// 使用主API的baseUrl
String currentBaseUrl = EnvConfig.mainBaseUrl;
final dio = Dio(
BaseOptions(
baseUrl: currentBaseUrl,
connectTimeout: Duration(milliseconds: connectTimeout),
receiveTimeout: Duration(milliseconds: receiveTimeout),
contentType: 'application/json',
responseType: ResponseType.json,
),
);
// 添加请求拦截器
dio.interceptors.add(AuthInterceptor());
// 添加响应拦截器
dio.interceptors.add(ResponseInterceptor());
// 添加日志拦截器
dio.interceptors.add(LogInterceptor(
requestBody: true,
responseBody: true,
error: true,
));
return dio;
}
}
/// 请求拦截器
class AuthInterceptor extends Interceptor {
@override
void onRequest(
RequestOptions options,
RequestInterceptorHandler handler,
) async {
// 添加token等认证信息
final token = _getToken();
if (token != null && token.isNotEmpty) {
options.headers['Authorization'] = token;
}
// 添加其他通用请求头
options.headers['X-APP-ID'] = '50325897884795885';
handler.next(options);
}
String? _getToken() {
// 从本地存储获取token
// 这里可以使用get_storage或其他存储方式
return GetStorage().read('token');
}
}
/// 响应拦截器
class ResponseInterceptor extends Interceptor {
@override
void onResponse(
Response response,
ResponseInterceptorHandler handler,
) {
// 统一处理响应数据
final data = response.data;
// 检查响应状态码
if (response.statusCode == 200) {
// 假设后端返回的数据格式为 {"code": 0, "message": "success", "data": {...}}
if (data is Map<String, dynamic>) {
final code = data['code'] ?? 0;
if (code == 0) {
// 请求成功
handler.next(response);
} else if(code == 401) {
_showError("登录已过期,请重新登录");
_handleTokenExpired();
} else {
// 业务错误
final message = data['message'] ?? '请求失败';
_showError(message);
handler.reject(DioException(
requestOptions: response.requestOptions,
error: message,
type: DioExceptionType.badResponse,
));
}
} else {
handler.next(response);
}
} else {
handler.next(response);
}
}
@override
void onError(DioException err, ErrorInterceptorHandler handler) {
// 统一处理错误
String errorMessage = '网络请求失败';
print('DioError: ${err.message}');
switch (err.type) {
case DioExceptionType.connectionTimeout:
case DioExceptionType.sendTimeout:
case DioExceptionType.receiveTimeout:
errorMessage = '网络连接超时,请检查网络';
break;
case DioExceptionType.badResponse:
if (err.response?.statusCode == 401) {
errorMessage = '登录已过期,请重新登录';
_handleTokenExpired();
} else if (err.response?.statusCode == 403) {
errorMessage = '没有权限访问该资源';
} else if (err.response?.statusCode == 404) {
errorMessage = '请求的资源不存在';
} else if (err.response?.statusCode == 500) {
errorMessage = '服务器内部错误';
} else {
errorMessage = '请求失败,状态码:${err.response?.statusCode}';
}
break;
case DioExceptionType.cancel:
errorMessage = '请求已取消';
break;
default:
errorMessage = err.message ?? '未知错误';
}
_showError(errorMessage);
handler.reject(err);
}
void _showError(String message) {
// 使用FlutterSmartDialog显示错误信息
SmartDialog.showToast(message, displayTime: const Duration(seconds: 2));
}
void _handleTokenExpired() async {
// 处理token过期逻辑,如清除本地数据、跳转登录页等
// 这里可以使用Get.offAllNamed('/login')等方式跳转
// 先退出 IM 登录
// 退出直播间
if (Get.isRegistered<RoomController>()) {
try {
final roomController = Get.find<RoomController>();
await roomController.leaveChannel();
} catch (e) {
print('退出直播间失败: $e');
}
}
// 取消小窗口
if (Get.isRegistered<OverlayController>()) {
try {
final overlayController = Get.find<OverlayController>();
overlayController.hide(); // 隐藏直播房间小窗
overlayController.hideVideoCall(); // 隐藏视频通话小窗
} catch (e) {
print('取消小窗口失败: $e');
}
}
if(IMManager.instance.isInitialized){
await IMManager.instance.logout();
}
// 清除会话列表和用户信息缓存
if (Get.isRegistered<ConversationController>()) {
final conversationController = Get.find<ConversationController>();
conversationController.clearConversations();
}
// 清除本地存储
GetStorage().remove('userId');
GetStorage().remove('token');
// 清除全局数据
GlobalData().logout();
Get.offAll(() => LoginPage());
}
}