Flutter Geolocator在iOS17.5.1模拟器无法获取位置致App Store审核被拒
Flutter iOS模拟器启动页卡顿问题排查与解决
问题场景
我正在开发一款Flutter应用,初始页面为自定义启动页,核心逻辑如下:
- 尝试获取用户位置
- 成功获取则携带位置数据跳转到首页
- 获取失败或无权限时,直接跳转首页(首页参数为可空类型)
使用go_router做路由管理,定位逻辑在启动页的异步init方法中执行。代码在Android设备、真实iPhone SE上运行正常,但在iOS17.5.1的iPad Air模拟器、iPhone13 mini模拟器中,应用一直卡在启动页,导致两次被App Store审核拒绝。
定位相关代码
if (permissionGranted) { try { final location = await Geolocator.getCurrentPosition(); try { // do some API call } catch (e) { print(e); } if (!mounted) return; router.go( '/', extra: LatLng(location.latitude, location.longitude), ); } catch (e) { print('Error obtaining location: $e'); router.go( '/', ); } } else { router.go( '/', ); }
疑问
- Geolocator包在iOS17.5.1模拟器上是否存在已知问题?
- 是否是我对go_router的实现存在问题?
- 是否缺少iOS模拟器特有的配置项?
排查与解决方案
1. Geolocator在iOS17.5.1模拟器的已知问题
是的,Geolocator在iOS17+模拟器上存在定位请求阻塞问题。模拟器默认不会自动返回位置,若未手动设置模拟位置,getCurrentPosition()会一直处于等待状态,不会触发超时或错误,直接导致启动页的异步逻辑卡住,无法执行路由跳转。
2. go_router的实现问题
路由调用逻辑本身无问题,但缺少超时处理是卡顿的核心原因。当定位请求无限挂起时,后续的router.go()永远不会执行。你已添加的!mounted判断是合理的,这部分无需修改。
3. iOS模拟器特有的配置项
需要补充三个关键配置:
- 设置定位超时:给
getCurrentPosition()添加超时参数,避免无限等待 - 完善Info.plist配置:确保已添加
NSLocationWhenInUseUsageDescription或NSLocationAlwaysAndWhenInUseUsageDescription权限描述,且模拟器已允许APP访问定位 - 手动设置模拟位置:在Xcode模拟器中通过
Debug > Location选择一个预设位置(比如Apple),避免定位请求挂起
修复后的代码示例
给定位请求添加超时和精度参数,确保无论成功失败都能触发路由:
if (permissionGranted) { try { // 添加超时设置,避免模拟器卡住 final location = await Geolocator.getCurrentPosition( locationSettings: const LocationSettings( accuracy: LocationAccuracy.medium, timeout: Duration(seconds: 10), // 10秒超时 ), ); try { // do some API call } catch (e) { print(e); } if (!mounted) return; router.go( '/', extra: LatLng(location.latitude, location.longitude), ); } catch (e) { print('Error obtaining location: $e'); if (!mounted) return; router.go('/'); } } else { if (!mounted) return; router.go('/'); }
额外优化建议
- 启动页添加加载动画:即使定位请求在处理,用户能看到加载状态,不会误以为APP卡死
- 权限申请后即时校验:确保权限状态判断准确,避免因状态更新不及时导致的逻辑异常
- Debug模式下跳过真实定位:直接使用预设的测试位置,提升开发测试效率
内容的提问来源于stack exchange,提问作者Safiul islam
相关产品推荐
相关产品推荐

