Flutter GetX权限列表在侧边栏获取为空问题求助
问题解决步骤
1. 修复MainController的响应式定义
你的perms写法会丢失响应式特性,需改为RxList类型:
// ignore_for_file: non_constant_identifier_names import 'package:get/get.dart'; class MainController extends GetxController { final RxList<dynamic> perms = <dynamic>[].obs; // 改为RxList确保响应式 final String apiUrl = "http://10.0.2.2:8000/api"; final RxString token = "".obs; final RxString userid = "".obs; final RxString name = "".obs; final RxString surname = "".obs; final RxBool isLogged = false.obs; final RxBool isSuccess = false.obs; }
2. 修复AuthController的实例共享问题
你在AuthController中新建了MainController实例,导致和侧边栏获取的不是同一个对象,数据无法共享。需改为获取全局注入的实例:
// ignore_for_file: avoid_print, use_build_context_synchronously import 'dart:convert'; import 'package:get/get.dart'; import 'package:http/http.dart' as http; import 'package:material_tracking/Controllers/main_controller.dart'; import 'package:material_tracking/Services/GetToken.dart'; import 'package:jwt_decoder/jwt_decoder.dart'; class AuthController { // 通过Get.find()获取全局的MainController实例 final MainController _mainController = Get.find<MainController>(); Future loginUser(String email, String password) async { try { final _url = _mainController.apiUrl + '/Auth/Login'; var response = await http.post( Uri.parse(_url), headers: <String, String>{ 'Content-Type': 'application/json; charset=UTF-8', }, body: jsonEncode({"email": email, "password": password}), ); if (response.statusCode == 200) { GetToken result = getTokenFromJson(response.body); Map<String, dynamic> decodedJwtToken = JwtDecoder.decode(result.data.accessToken); if (result.isSuccessful == true) { // 更新响应式变量必须通过.value _mainController.token.value = result.data.accessToken; _mainController.isSuccess.value = result.isSuccessful; // 用assignAll更新RxList,确保触发响应式刷新 _mainController.perms.assignAll(decodedJwtToken["Permission"]); print(_mainController.perms); if (_mainController.isSuccess.value) { // 用GetX路由跳转替代Navigator,保证状态同步 Get.toNamed("/dashboard"); } else { print("Hata"); } } else { print(result.error); } } else { print("Login Error"); } } catch (e) { print("Exception: $e"); } } }
3. 提前注入MainController
在APP启动时注入MainController,确保全局只有一个实例:
void main() { // 提前注入MainController Get.put(MainController()); runApp(const MyApp()); }
4. 修复侧边栏的权限监听逻辑
不要仅在initState中赋值perms,需监听响应式变量变化,或用Obx包裹UI:
import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:get/get.dart'; import 'package:material_tracking/Controllers/main_controller.dart'; class SideBarNavigationDrawer extends StatefulWidget { const SideBarNavigationDrawer({super.key}); @override State<SideBarNavigationDrawer> createState() => _SideBarNavigationDrawerState(); } class _SideBarNavigationDrawerState extends State<SideBarNavigationDrawer> { final MainController mainController = Get.find<MainController>(); @override void initState() { super.initState(); // 监听perms变化,确保数据更新时触发UI刷新 ever(mainController.perms, (value) { if (kDebugMode) { print("更新后的权限:$value"); } }); } @override Widget build(BuildContext context) { // 用Obx包裹依赖权限的UI部分,自动响应数据变化 return Obx(() { return Drawer( child: ListView( children: [ // 示例:根据权限显示对应菜单 if (mainController.perms.contains("view_dashboard")) ListTile(title: const Text("仪表盘"), onTap: () {}), if (mainController.perms.contains("view_settings")) ListTile(title: const Text("设置"), onTap: () {}), ], ), ); }); } }
核心问题总结
- 实例不共享:AuthController中新建MainController导致数据无法传递,必须通过GetX依赖注入获取全局实例。
- 响应式更新错误:直接赋值RxList不会触发UI刷新,需用
assignAll;更新Rx变量必须通过.value。 - 路由跳转不匹配:使用GetX路由方法替代Navigator,保证状态管理一致性。
内容的提问来源于stack exchange,提问作者Atakan Koç
相关产品推荐
相关产品推荐

