From 60d5c427dedb3a3124a1d6a1f18599ced12ff585 Mon Sep 17 00:00:00 2001 From: ZuoZuo <68836346+Mrz-sakura@users.noreply.github.com> Date: Sat, 11 Apr 2026 13:52:49 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E5=A4=8D=E8=AF=AD=E9=9F=B3=E6=88=BF?= =?UTF-8?q?=E5=88=97=E8=A1=A8=E7=9A=84bug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../config/configs/sc_variant1_config.dart | 10 +-- .../account/sc_login_with_account_page.dart | 15 ++++ .../auth/edit/sc_edit_profile_page.dart | 15 +++- lib/modules/splash/splash_page.dart | 34 ++++---- lib/services/audio/rtc_manager.dart | 79 +++++++++++++++---- lib/services/auth/authentication_manager.dart | 33 ++++++++ .../data_sources/sources/remote/net/api.dart | 14 ++-- .../sources/remote/net/network_client.dart | 21 ++--- 8 files changed, 161 insertions(+), 60 deletions(-) diff --git a/lib/app/config/configs/sc_variant1_config.dart b/lib/app/config/configs/sc_variant1_config.dart index e3f354a..664ebd9 100644 --- a/lib/app/config/configs/sc_variant1_config.dart +++ b/lib/app/config/configs/sc_variant1_config.dart @@ -13,11 +13,11 @@ class SCVariant1Config implements AppConfig { @override String get packageName => 'com.org.yumi'; - @override + @override String get apiHost => const String.fromEnvironment( 'API_HOST', - defaultValue: 'http://10.0.2.2:1100/', - ); // 默认走模拟器宿主机地址,真机可通过 --dart-define=API_HOST 覆盖 + defaultValue: 'https://jvapi.haiyihy.com/', + ); // 默认连线上环境,本地调试可通过 --dart-define=API_HOST 覆盖 @override String get imgHost => 'https://img.atuchat.com/'; // 测试图片服务器,上架前需替换为正式域名 @@ -74,7 +74,7 @@ class SCVariant1Config implements AppConfig { int get primaryColor => 0xffFF5722; // 不同主色(橙色) @override - String get tencentImAppid => '20035299'; + String get tencentImAppid => '20036101'; @override String get agoraRtcAppid => 'ceb9e2620d454bca9725f7a7f11d4019'; @@ -86,7 +86,7 @@ class SCVariant1Config implements AppConfig { String get gameAppChannel => 'yumi'; @override - String get bigBroadcastGroup => '@TGS#2XDMSPK5CR'; + String get bigBroadcastGroup => '@TGS#2RUK4PK5C2'; @override String get imAdmin => 'c2c_yumiadmin'; diff --git a/lib/modules/auth/account/sc_login_with_account_page.dart b/lib/modules/auth/account/sc_login_with_account_page.dart index e9fc920..b76e52a 100644 --- a/lib/modules/auth/account/sc_login_with_account_page.dart +++ b/lib/modules/auth/account/sc_login_with_account_page.dart @@ -16,6 +16,9 @@ import 'package:yumi/shared/tools/sc_loading_manager.dart'; import 'package:yumi/shared/tools/sc_version_utils.dart'; import 'package:yumi/shared/data_sources/sources/repositories/sc_user_repository_impl.dart'; import 'package:yumi/shared/business_logic/models/res/login_res.dart'; +import 'package:provider/provider.dart'; +import 'package:yumi/services/audio/rtc_manager.dart'; +import 'package:yumi/services/audio/rtm_manager.dart'; ///密码账户登录 class SCLoginWithAccountPage extends StatefulWidget { @@ -365,6 +368,18 @@ class SCLoginWithAccountPageState extends State SCVersionUtils.checkReview(), ]); var user = (results[0] as SocialChatLoginRes); + if (!mounted) { + return; + } + await Provider.of( + context, + listen: false, + ).resetLocalRoomState( + fallbackRtmProvider: Provider.of(context, listen: false), + ); + if (!mounted) { + return; + } AccountStorage().setCurrentUser(user); SCLoadingManager.hide(); DataPersistence.setString("Login_Account", account); diff --git a/lib/modules/auth/edit/sc_edit_profile_page.dart b/lib/modules/auth/edit/sc_edit_profile_page.dart index 1c05ee2..3cfcab5 100644 --- a/lib/modules/auth/edit/sc_edit_profile_page.dart +++ b/lib/modules/auth/edit/sc_edit_profile_page.dart @@ -21,6 +21,8 @@ import 'package:yumi/shared/data_sources/sources/local/user_manager.dart'; import 'package:yumi/shared/business_logic/models/res/login_res.dart'; import 'package:yumi/services/general/sc_app_general_manager.dart'; import 'package:yumi/services/auth/user_profile_manager.dart'; +import 'package:yumi/services/audio/rtc_manager.dart'; +import 'package:yumi/services/audio/rtm_manager.dart'; import 'package:yumi/app/constants/sc_global_config.dart'; import '../../../shared/business_logic/usecases/sc_custom_filtering_textinput_formatter.dart'; @@ -466,8 +468,8 @@ class _SCEditProfilePageState extends State { textTheme: CupertinoTextThemeData( // 在这里设置字体颜色、大小等样式 dateTimePickerTextStyle: TextStyle( - color: Colors.white, // 设置字体颜色 - fontSize: 16.sp, // 设置字体大小 + color: Colors.white, // 设置字体颜色 + fontSize: 16.sp, // 设置字体大小 ), ), ), @@ -542,6 +544,15 @@ class _SCEditProfilePageState extends State { idToken, userProvider!.editUser!, ); + if (!mounted) { + return; + } + await Provider.of(context, listen: false).resetLocalRoomState( + fallbackRtmProvider: Provider.of(context, listen: false), + ); + if (!mounted) { + return; + } AccountStorage().setCurrentUser(user); SCLoadingManager.hide(); SCNavigatorUtils.push(context, SCRoutes.home, clearStack: true); diff --git a/lib/modules/splash/splash_page.dart b/lib/modules/splash/splash_page.dart index 31bf213..75c1380 100644 --- a/lib/modules/splash/splash_page.dart +++ b/lib/modules/splash/splash_page.dart @@ -34,21 +34,25 @@ class _SplashPageState extends State { _startTimer(context); } - ///加载启动页配置 - void getStartPage() { - SCConfigRepositoryImp().getStartPage().then((result) { - startPages = result; - if (startPages.length > 1) { - int index = Random().nextInt(startPages.length); - currentStartPage = result[index]; - } else { - currentStartPage = result.first; - } - - status = 1; - setState(() {}); - }); - } + ///加载启动页配置 + void getStartPage() { + SCConfigRepositoryImp().getStartPage().then((result) { + startPages = result; + if (startPages.length > 1) { + int index = Random().nextInt(startPages.length); + currentStartPage = result[index]; + } else if (startPages.isNotEmpty) { + currentStartPage = result.first; + } else { + currentStartPage = null; + } + + status = 1; + if (mounted) { + setState(() {}); + } + }); + } @override void dispose() { diff --git a/lib/services/audio/rtc_manager.dart b/lib/services/audio/rtc_manager.dart index a6c5b09..92f6684 100644 --- a/lib/services/audio/rtc_manager.dart +++ b/lib/services/audio/rtc_manager.dart @@ -21,6 +21,7 @@ import 'package:yumi/shared/tools/sc_lk_dialog_util.dart'; import 'package:yumi/shared/tools/sc_loading_manager.dart'; import 'package:yumi/shared/tools/sc_gift_vap_svga_manager.dart'; import 'package:yumi/shared/data_sources/sources/repositories/sc_user_repository_impl.dart'; +import 'package:yumi/shared/data_sources/sources/local/data_persistence.dart'; import 'package:yumi/shared/business_logic/models/res/join_room_res.dart'; import 'package:yumi/shared/business_logic/models/res/login_res.dart'; import 'package:yumi/shared/business_logic/models/res/mic_res.dart'; @@ -290,7 +291,15 @@ class RealTimeCommunicationManager extends ChangeNotifier { } if (roomId == currenRoom?.roomProfile?.roomProfile?.id) { ///最小化进入房间,或者进入的是同一个房间 - loadRoomInfo(currenRoom?.roomProfile?.roomProfile?.id ?? ""); + final loaded = await loadRoomInfo( + currenRoom?.roomProfile?.roomProfile?.id ?? "", + ); + if (!loaded) { + return; + } + if (!context.mounted) { + return; + } Provider.of( context, listen: false, @@ -321,20 +330,29 @@ class RealTimeCommunicationManager extends ChangeNotifier { if (currenRoom != null) { await exitCurrentVoiceRoomSession(false); } + if (!context.mounted) { + return; + } rtmProvider = Provider.of(context, listen: false); SCLoadingManager.show(context: context); - currenRoom = await SCAccountRepository().entryRoom( - roomId, - pwd: pwd, - redPackId: redPackId, - needOpenRedenvelope: needOpenRedenvelope, - ); - await initializeRoomSession( - needOpenRedenvelope: needOpenRedenvelope, - redPackId: redPackId, - ); - SCLoadingManager.hide(); - notifyListeners(); + try { + currenRoom = await SCAccountRepository().entryRoom( + roomId, + pwd: pwd, + redPackId: redPackId, + needOpenRedenvelope: needOpenRedenvelope, + ); + await initializeRoomSession( + needOpenRedenvelope: needOpenRedenvelope, + redPackId: redPackId, + ); + notifyListeners(); + } catch (e) { + await resetLocalRoomState(fallbackRtmProvider: rtmProvider); + rethrow; + } finally { + SCLoadingManager.hide(); + } } } @@ -551,6 +569,28 @@ class RealTimeCommunicationManager extends ChangeNotifier { } } + Future resetLocalRoomState({RtmProvider? fallbackRtmProvider}) async { + rtmProvider ??= fallbackRtmProvider; + try { + SCHeartbeatUtils.cancelTimer(); + SCHeartbeatUtils.cancelAnchorTimer(); + final groupId = currenRoom?.roomProfile?.roomProfile?.roomAccount ?? ""; + if (groupId.isNotEmpty) { + await rtmProvider?.quitGroup(groupId); + } + await engine?.leaveChannel(); + await Future.delayed(const Duration(milliseconds: 100)); + await engine?.release(); + } catch (e) { + print('rtc清理本地房间状态出错: $e'); + } finally { + engine = null; + rtmProvider?.cleanRoomData(); + _clearData(); + notifyListeners(); + } + } + ///清空列表数据 void _clearData() { roomRocketStatus = null; @@ -568,6 +608,7 @@ class RealTimeCommunicationManager extends ChangeNotifier { currenRoom = null; isMic = true; isMusicPlaying = false; + DataPersistence.setLastTimeRoomId(""); SCGiftVapSvgaManager().clearTasks(); SCRoomUtils.closeAllDialogs(); SCGlobalConfig.isEntryVehicleAnimation = true; @@ -853,8 +894,9 @@ class RealTimeCommunicationManager extends ChangeNotifier { return -1; } - void loadRoomInfo(String roomId) { - SCChatRoomRepository().specific(roomId).then((value) { + Future loadRoomInfo(String roomId) async { + try { + final value = await SCChatRoomRepository().specific(roomId); currenRoom = currenRoom?.copyWith( roomProfile: currenRoom?.roomProfile?.copyWith( roomCounter: value.counter, @@ -879,7 +921,12 @@ class RealTimeCommunicationManager extends ChangeNotifier { } } notifyListeners(); - }); + return true; + } catch (e) { + await resetLocalRoomState(fallbackRtmProvider: rtmProvider); + SCTts.show("Room not exists"); + return false; + } } ///解锁麦位 diff --git a/lib/services/auth/authentication_manager.dart b/lib/services/auth/authentication_manager.dart index 43361a5..0d6aa28 100644 --- a/lib/services/auth/authentication_manager.dart +++ b/lib/services/auth/authentication_manager.dart @@ -12,6 +12,9 @@ import 'package:yumi/shared/data_sources/sources/local/user_manager.dart'; import 'package:yumi/shared/data_sources/sources/repositories/sc_user_repository_impl.dart'; import 'package:yumi/shared/business_logic/models/res/login_res.dart'; import 'package:yumi/ui_kit/components/sc_tts.dart'; +import 'package:provider/provider.dart'; +import 'package:yumi/services/audio/rtc_manager.dart'; +import 'package:yumi/services/audio/rtm_manager.dart'; import '../../shared/data_sources/models/enum/sc_auth_type.dart'; @@ -55,6 +58,21 @@ class SocialChatAuthenticationManager extends ChangeNotifier { SCVersionUtils.checkReview(), ]); var user = (res[0] as SocialChatLoginRes); + if (!context.mounted) { + return; + } + await Provider.of( + context, + listen: false, + ).resetLocalRoomState( + fallbackRtmProvider: Provider.of( + context, + listen: false, + ), + ); + if (!context.mounted) { + return; + } AccountStorage().setCurrentUser(user); SCLoadingManager.hide(); notifyListeners(); @@ -80,6 +98,21 @@ class SocialChatAuthenticationManager extends ChangeNotifier { SCVersionUtils.checkReview(), ]); var user = (res[0] as SocialChatLoginRes); + if (!context.mounted) { + return; + } + await Provider.of( + context, + listen: false, + ).resetLocalRoomState( + fallbackRtmProvider: Provider.of( + context, + listen: false, + ), + ); + if (!context.mounted) { + return; + } AccountStorage().setCurrentUser(user); SCLoadingManager.hide(); notifyListeners(); diff --git a/lib/shared/data_sources/sources/remote/net/api.dart b/lib/shared/data_sources/sources/remote/net/api.dart index 2973764..3734bdb 100644 --- a/lib/shared/data_sources/sources/remote/net/api.dart +++ b/lib/shared/data_sources/sources/remote/net/api.dart @@ -31,13 +31,13 @@ class BaseNetworkClient { } void _confD() { - dio.transformer = BackgroundTransformer()..jsonDecodeCallback = parseJson; - dio.options = BaseOptions( - connectTimeout: const Duration(seconds: 12), - receiveTimeout: const Duration(seconds: 15), - contentType: 'application/json; charset=UTF-8', - ); - } + dio.transformer = BackgroundTransformer()..jsonDecodeCallback = parseJson; + dio.options = BaseOptions( + connectTimeout: const Duration(seconds: 12), + receiveTimeout: const Duration(seconds: 30), + contentType: 'application/json; charset=UTF-8', + ); + } void init() {} diff --git a/lib/shared/data_sources/sources/remote/net/network_client.dart b/lib/shared/data_sources/sources/remote/net/network_client.dart index 5cf9d5a..b9b3a04 100644 --- a/lib/shared/data_sources/sources/remote/net/network_client.dart +++ b/lib/shared/data_sources/sources/remote/net/network_client.dart @@ -272,20 +272,11 @@ const Map _localRouteOverrides = { "/user/vip/ability/update", }; -bool _isLocalGatewayBaseUrl(String baseUrl) { - final uri = Uri.tryParse(baseUrl); - if (uri == null) return false; - return uri.host == "10.0.2.2" || - uri.host == "127.0.0.1" || - uri.host == "localhost"; -} - -String _resolveRequestPath(String baseUrl, String path) { - if (!_isLocalGatewayBaseUrl(baseUrl)) { - return path; - } - return _localRouteOverrides[path] ?? path; -} +String _resolveRequestPath(String baseUrl, String path) { + // Prefer the known plain-text route when we have one. + // This avoids environment-specific AES forwarding mismatches at the gateway. + return _localRouteOverrides[path] ?? path; +} class NetworkClient extends BaseNetworkClient { @override @@ -465,7 +456,7 @@ class ResponseData { /// 超时拦截器 class TimeOutInterceptor extends Interceptor { - static const int globalTimeoutSeconds = 15; + static const int globalTimeoutSeconds = 25; static const String timeoutSecondsKey = "requestTimeoutSeconds"; final Map _timers = {};