You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Go Router时Flutter热重载重置至初始页面问题求助

Go Router热重载重置页面问题解决方案

问题背景

使用Flutter 3.3.4 + Go Router 5.1.0开发时,热重载会触发路由重置到初始页面,移除MaterialApp.router后热重载恢复正常。相关路由代码如下:

class AppRouter {
  final LoginInfo loginInfo;
  AppRouter(this.loginInfo);

  late final router = GoRouter(
      debugLogDiagnostics: true,
      routerNeglect: true,
      redirect: (context, state) {
        print(':::: ${loginInfo.isLogin}');
        final bool? loggedIn = loginInfo.isLogin;
        final bool loggingIn = state.subloc == '/login';

        if (loggedIn == null) {
          return null;
        }
        if (!loggedIn) {
          return loggingIn ? null : '/login';
        }

        if (loggingIn) {
          return '/';
        }

        return null;
      },
      refreshListenable: loginInfo,
      routes: [
        GoRoute(
          path: '/',
          builder: (context, state) {
            return const BottomNaviBar();
          },
          routes: [
            GoRoute(
              name: 'statusCheck',
              path: 'statusCheck',
              builder: (context, state) {
                return const StatusCheckPage();
              },
            ),
        GoRoute(
          name: 'login',
          path: '/login',
          builder: (context, state) {
            return const LoginPage();
          },
        ),
      ]);
}

解决方法

1. 保持GoRouter实例单例

热重载时如果AppRouter被重新实例化,会生成新的GoRouter对象,导致路由状态丢失。将AppRouter改为单例模式:

class AppRouter {
  final LoginInfo loginInfo;
  static AppRouter? _instance;

  // 工厂构造函数确保单例
  factory AppRouter(LoginInfo loginInfo) {
    _instance ??= AppRouter._internal(loginInfo);
    return _instance!;
  }

  AppRouter._internal(this.loginInfo);

  late final router = GoRouter(
    // 原有配置保留
    debugLogDiagnostics: true,
    routerNeglect: true,
    redirect: (context, state) {
      // 原有重定向逻辑
    },
    refreshListenable: loginInfo,
    routes: [/* 原有路由定义 */]
  );
}

2. 禁用routerNeglect参数

routerNeglect: true会让路由操作不被记录到导航栈,热重载时可能导致状态无法恢复。尝试将其改为false:

late final router = GoRouter(
  debugLogDiagnostics: true,
  routerNeglect: false, // 修改此处
  // 其他配置不变
);

3. 检查LoginInfo的Listenable实现

确保LoginInfo正确实现ChangeNotifier(或Listenable),且实例在热重载时不会被重置:

class LoginInfo extends ChangeNotifier {
  bool? _isLogin;

  bool? get isLogin => _isLogin;

  set isLogin(bool? value) {
    if (_isLogin != value) {
      _isLogin = value;
      notifyListeners();
    }
  }
}

同时确保LoginInfo实例是全局单例,或通过Provider等状态管理工具维护,避免热重载时重新初始化。

4. 升级Go Router版本

Go Router 5.x存在部分热重载相关的已知问题,升级到v6.x稳定版本可修复这类兼容性问题。注意升级后需适配新API,比如路由嵌套方式、redirect逻辑的写法调整。

内容的提问来源于stack exchange,提问作者dragonJin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.16 08:15:38