mirror of
https://github.com/dz0ny/meshcore-sar.git
synced 2026-08-11 16:30:28 +00:00
Fix connection provider auto-add bug
This commit is contained in:
@@ -2058,6 +2058,12 @@ class ConnectionProvider with ChangeNotifier {
|
|||||||
advertLocationPolicy: advertLocationPolicy,
|
advertLocationPolicy: advertLocationPolicy,
|
||||||
multiAcks: multiAcks,
|
multiAcks: multiAcks,
|
||||||
);
|
);
|
||||||
|
_deviceInfo = _deviceInfo.copyWith(
|
||||||
|
telemetryModes: telemetryModes,
|
||||||
|
advertLocPolicy: advertLocationPolicy,
|
||||||
|
multiAcks: multiAcks,
|
||||||
|
);
|
||||||
|
notifyListeners();
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
_error = 'Failed to set other params: $e';
|
_error = 'Failed to set other params: $e';
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
@@ -2098,6 +2104,10 @@ class ConnectionProvider with ChangeNotifier {
|
|||||||
notifyListeners();
|
notifyListeners();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if (_isTransientAutoaddConfigError(e)) {
|
||||||
|
debugPrint('Ignoring transient auto-add config error: $e');
|
||||||
|
return;
|
||||||
|
}
|
||||||
_error = 'Failed to get auto-add config: $e';
|
_error = 'Failed to get auto-add config: $e';
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
}
|
}
|
||||||
@@ -2151,16 +2161,7 @@ class ConnectionProvider with ChangeNotifier {
|
|||||||
// The device query command triggers a SelfInfo response
|
// The device query command triggers a SelfInfo response
|
||||||
await _activeService.refreshDeviceInfo();
|
await _activeService.refreshDeviceInfo();
|
||||||
if (_supportsAutoaddConfig != false) {
|
if (_supportsAutoaddConfig != false) {
|
||||||
try {
|
unawaited(getAutoaddConfig());
|
||||||
await _activeService.getAutoaddConfig();
|
|
||||||
_supportsAutoaddConfig = true;
|
|
||||||
} catch (e) {
|
|
||||||
if (_isUnsupportedAutoaddConfigError(e)) {
|
|
||||||
_supportsAutoaddConfig = false;
|
|
||||||
} else {
|
|
||||||
rethrow;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
await _activeService.getAllowedRepeatFreq();
|
await _activeService.getAllowedRepeatFreq();
|
||||||
@@ -2175,10 +2176,15 @@ class ConnectionProvider with ChangeNotifier {
|
|||||||
|
|
||||||
bool _isUnsupportedAutoaddConfigError(Object error) {
|
bool _isUnsupportedAutoaddConfigError(Object error) {
|
||||||
final message = error.toString().toLowerCase();
|
final message = error.toString().toLowerCase();
|
||||||
return message.contains('illegal argument') ||
|
return message.contains('unsupported command') ||
|
||||||
message.contains('unsupported');
|
message.contains('unsupported');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool _isTransientAutoaddConfigError(Object error) {
|
||||||
|
final message = error.toString().toLowerCase();
|
||||||
|
return message.contains('illegal argument');
|
||||||
|
}
|
||||||
|
|
||||||
/// Request battery and storage information
|
/// Request battery and storage information
|
||||||
///
|
///
|
||||||
/// Queries the companion radio for:
|
/// Queries the companion radio for:
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
import 'dart:async';
|
||||||
import 'dart:typed_data';
|
import 'dart:typed_data';
|
||||||
|
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
@@ -24,6 +25,7 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
static const Duration _bulkDeleteInterItemDelay = Duration(milliseconds: 120);
|
static const Duration _bulkDeleteInterItemDelay = Duration(milliseconds: 120);
|
||||||
static const Duration _bulkDeleteBatchDelay = Duration(milliseconds: 700);
|
static const Duration _bulkDeleteBatchDelay = Duration(milliseconds: 700);
|
||||||
static const Duration _bulkDeleteFinalSyncDelay = Duration(milliseconds: 900);
|
static const Duration _bulkDeleteFinalSyncDelay = Duration(milliseconds: 900);
|
||||||
|
static const int _autoAddFilterModeFlag = 1;
|
||||||
static const List<_RadioPreset> _radioPresets = [
|
static const List<_RadioPreset> _radioPresets = [
|
||||||
_RadioPreset(
|
_RadioPreset(
|
||||||
id: 'australia',
|
id: 'australia',
|
||||||
@@ -176,6 +178,7 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
late TextEditingController _lonController;
|
late TextEditingController _lonController;
|
||||||
late TextEditingController _freqController;
|
late TextEditingController _freqController;
|
||||||
late TextEditingController _txPowerController;
|
late TextEditingController _txPowerController;
|
||||||
|
late final ConnectionProvider _connectionProvider;
|
||||||
|
|
||||||
bool _telemetryEnabled = false;
|
bool _telemetryEnabled = false;
|
||||||
bool _repeatEnabled = false;
|
bool _repeatEnabled = false;
|
||||||
@@ -194,6 +197,8 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
bool _publicInfoSaved = false;
|
bool _publicInfoSaved = false;
|
||||||
bool _radioSettingsSaved = false;
|
bool _radioSettingsSaved = false;
|
||||||
bool _autoDiscoverySettingsSaved = false;
|
bool _autoDiscoverySettingsSaved = false;
|
||||||
|
bool _autoDiscoverySettingsDirty = false;
|
||||||
|
String? _lastAutoDiscoverySignature;
|
||||||
String? _publicInfoError;
|
String? _publicInfoError;
|
||||||
String? _radioSettingsError;
|
String? _radioSettingsError;
|
||||||
String? _autoDiscoverySettingsError;
|
String? _autoDiscoverySettingsError;
|
||||||
@@ -218,7 +223,9 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
super.initState();
|
super.initState();
|
||||||
final deviceInfo = context.read<ConnectionProvider>().deviceInfo;
|
_connectionProvider = context.read<ConnectionProvider>();
|
||||||
|
_connectionProvider.addListener(_handleConnectionProviderChanged);
|
||||||
|
final deviceInfo = _connectionProvider.deviceInfo;
|
||||||
|
|
||||||
_nameController = TextEditingController(
|
_nameController = TextEditingController(
|
||||||
text: deviceInfo.selfName ?? deviceInfo.deviceName ?? '',
|
text: deviceInfo.selfName ?? deviceInfo.deviceName ?? '',
|
||||||
@@ -273,14 +280,8 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
|
|
||||||
// Initialize repeat mode from device info (firmware v9+)
|
// Initialize repeat mode from device info (firmware v9+)
|
||||||
_repeatEnabled = deviceInfo.clientRepeat ?? false;
|
_repeatEnabled = deviceInfo.clientRepeat ?? false;
|
||||||
_autoAddDiscoveredContactsEnabled =
|
_syncAutoDiscoveryState(deviceInfo);
|
||||||
!(deviceInfo.manualAddContacts ?? false);
|
_lastAutoDiscoverySignature = _autoDiscoverySignature(deviceInfo);
|
||||||
_autoAddUsersEnabled = deviceInfo.autoAddUsers ?? true;
|
|
||||||
_autoAddRepeatersEnabled = deviceInfo.autoAddRepeaters ?? true;
|
|
||||||
_autoAddRoomServersEnabled = deviceInfo.autoAddRoomServers ?? true;
|
|
||||||
_autoAddSensorsEnabled = deviceInfo.autoAddSensors ?? true;
|
|
||||||
_overwriteOldestAutoAddEnabled =
|
|
||||||
deviceInfo.autoAddOverwriteOldest ?? false;
|
|
||||||
|
|
||||||
// Fetch allowed repeat frequencies on open if device supports repeat mode
|
// Fetch allowed repeat frequencies on open if device supports repeat mode
|
||||||
if (deviceInfo.clientRepeat != null &&
|
if (deviceInfo.clientRepeat != null &&
|
||||||
@@ -291,13 +292,14 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
WidgetsBinding.instance.addPostFrameCallback((_) {
|
WidgetsBinding.instance.addPostFrameCallback((_) {
|
||||||
context.read<ConnectionProvider>().getBatteryAndStorage();
|
_connectionProvider.getBatteryAndStorage();
|
||||||
context.read<ConnectionProvider>().getAutoaddConfig();
|
unawaited(_connectionProvider.getAutoaddConfig());
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void dispose() {
|
void dispose() {
|
||||||
|
_connectionProvider.removeListener(_handleConnectionProviderChanged);
|
||||||
_nameController.dispose();
|
_nameController.dispose();
|
||||||
_latController.dispose();
|
_latController.dispose();
|
||||||
_lonController.dispose();
|
_lonController.dispose();
|
||||||
@@ -406,6 +408,7 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void _markAutoDiscoverySettingsDirty() {
|
void _markAutoDiscoverySettingsDirty() {
|
||||||
|
_autoDiscoverySettingsDirty = true;
|
||||||
if (_autoDiscoverySettingsSaved || _autoDiscoverySettingsError != null) {
|
if (_autoDiscoverySettingsSaved || _autoDiscoverySettingsError != null) {
|
||||||
setState(() {
|
setState(() {
|
||||||
_autoDiscoverySettingsSaved = false;
|
_autoDiscoverySettingsSaved = false;
|
||||||
@@ -414,6 +417,71 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
String _autoDiscoverySignature(DeviceInfo deviceInfo) {
|
||||||
|
return [
|
||||||
|
deviceInfo.manualAddContacts,
|
||||||
|
deviceInfo.autoAddUsers,
|
||||||
|
deviceInfo.autoAddRepeaters,
|
||||||
|
deviceInfo.autoAddRoomServers,
|
||||||
|
deviceInfo.autoAddSensors,
|
||||||
|
deviceInfo.autoAddOverwriteOldest,
|
||||||
|
].join('|');
|
||||||
|
}
|
||||||
|
|
||||||
|
void _handleConnectionProviderChanged() {
|
||||||
|
if (!mounted || _autoDiscoverySettingsDirty) return;
|
||||||
|
|
||||||
|
final deviceInfo = _connectionProvider.deviceInfo;
|
||||||
|
final nextSignature = _autoDiscoverySignature(deviceInfo);
|
||||||
|
if (nextSignature == _lastAutoDiscoverySignature) return;
|
||||||
|
|
||||||
|
_lastAutoDiscoverySignature = nextSignature;
|
||||||
|
setState(() {
|
||||||
|
_syncAutoDiscoveryState(deviceInfo);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
bool _hasAutoAddTargetsEnabled(DeviceInfo deviceInfo) {
|
||||||
|
return (deviceInfo.autoAddUsers ?? false) ||
|
||||||
|
(deviceInfo.autoAddRepeaters ?? false) ||
|
||||||
|
(deviceInfo.autoAddRoomServers ?? false) ||
|
||||||
|
(deviceInfo.autoAddSensors ?? false);
|
||||||
|
}
|
||||||
|
|
||||||
|
void _syncAutoDiscoveryState(DeviceInfo deviceInfo) {
|
||||||
|
final hasFetchedAutoAddConfig =
|
||||||
|
deviceInfo.autoAddUsers != null ||
|
||||||
|
deviceInfo.autoAddRepeaters != null ||
|
||||||
|
deviceInfo.autoAddRoomServers != null ||
|
||||||
|
deviceInfo.autoAddSensors != null ||
|
||||||
|
deviceInfo.autoAddOverwriteOldest != null;
|
||||||
|
|
||||||
|
_autoAddDiscoveredContactsEnabled = hasFetchedAutoAddConfig
|
||||||
|
? _hasAutoAddTargetsEnabled(deviceInfo)
|
||||||
|
: !(deviceInfo.manualAddContacts ?? false);
|
||||||
|
_autoAddUsersEnabled = deviceInfo.autoAddUsers ?? true;
|
||||||
|
_autoAddRepeatersEnabled = deviceInfo.autoAddRepeaters ?? true;
|
||||||
|
_autoAddRoomServersEnabled = deviceInfo.autoAddRoomServers ?? true;
|
||||||
|
_autoAddSensorsEnabled = deviceInfo.autoAddSensors ?? true;
|
||||||
|
_overwriteOldestAutoAddEnabled = deviceInfo.autoAddOverwriteOldest ?? false;
|
||||||
|
}
|
||||||
|
|
||||||
|
int _telemetryModesForSave(ConnectionProvider connectionProvider) {
|
||||||
|
final deviceInfo = connectionProvider.deviceInfo;
|
||||||
|
final telemetryEnabled =
|
||||||
|
(deviceInfo.advLat != null && deviceInfo.advLat != 0) ||
|
||||||
|
(deviceInfo.advLon != null && deviceInfo.advLon != 0);
|
||||||
|
return deviceInfo.telemetryModes ?? (telemetryEnabled ? 0x0A : 0x00);
|
||||||
|
}
|
||||||
|
|
||||||
|
int _advertLocationPolicyForSave(ConnectionProvider connectionProvider) {
|
||||||
|
final deviceInfo = connectionProvider.deviceInfo;
|
||||||
|
final telemetryEnabled =
|
||||||
|
(deviceInfo.advLat != null && deviceInfo.advLat != 0) ||
|
||||||
|
(deviceInfo.advLon != null && deviceInfo.advLon != 0);
|
||||||
|
return deviceInfo.advertLocPolicy ?? (telemetryEnabled ? 1 : 0);
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> _savePublicInfo() async {
|
Future<void> _savePublicInfo() async {
|
||||||
final connectionProvider = context.read<ConnectionProvider>();
|
final connectionProvider = context.read<ConnectionProvider>();
|
||||||
final validator = ValidationService();
|
final validator = ValidationService();
|
||||||
@@ -425,9 +493,6 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
});
|
});
|
||||||
|
|
||||||
try {
|
try {
|
||||||
final manualAddContacts =
|
|
||||||
(connectionProvider.deviceInfo.manualAddContacts ?? false) ? 1 : 0;
|
|
||||||
|
|
||||||
// Save name
|
// Save name
|
||||||
if (_nameController.text.isNotEmpty) {
|
if (_nameController.text.isNotEmpty) {
|
||||||
await connectionProvider.setAdvertName(_nameController.text);
|
await connectionProvider.setAdvertName(_nameController.text);
|
||||||
@@ -466,7 +531,7 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
// Set telemetry modes to "Allow All" (mode 2 for both base and location)
|
// Set telemetry modes to "Allow All" (mode 2 for both base and location)
|
||||||
final telemetryModes = 0x0A; // binary: 00001010 (base=2, location=2)
|
final telemetryModes = 0x0A; // binary: 00001010 (base=2, location=2)
|
||||||
await connectionProvider.setOtherParams(
|
await connectionProvider.setOtherParams(
|
||||||
manualAddContacts: manualAddContacts,
|
manualAddContacts: _autoAddFilterModeFlag,
|
||||||
telemetryModes: telemetryModes,
|
telemetryModes: telemetryModes,
|
||||||
advertLocationPolicy: 1,
|
advertLocationPolicy: 1,
|
||||||
);
|
);
|
||||||
@@ -477,7 +542,7 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
// Set telemetry modes to "Deny" (mode 0)
|
// Set telemetry modes to "Deny" (mode 0)
|
||||||
final telemetryModes = 0x00;
|
final telemetryModes = 0x00;
|
||||||
await connectionProvider.setOtherParams(
|
await connectionProvider.setOtherParams(
|
||||||
manualAddContacts: manualAddContacts,
|
manualAddContacts: _autoAddFilterModeFlag,
|
||||||
telemetryModes: telemetryModes,
|
telemetryModes: telemetryModes,
|
||||||
advertLocationPolicy: 0,
|
advertLocationPolicy: 0,
|
||||||
);
|
);
|
||||||
@@ -580,6 +645,16 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
|
|
||||||
Future<void> _saveAutoDiscoverySettings() async {
|
Future<void> _saveAutoDiscoverySettings() async {
|
||||||
final connectionProvider = context.read<ConnectionProvider>();
|
final connectionProvider = context.read<ConnectionProvider>();
|
||||||
|
final autoAddUsers =
|
||||||
|
_autoAddDiscoveredContactsEnabled && _autoAddUsersEnabled;
|
||||||
|
final autoAddRepeaters =
|
||||||
|
_autoAddDiscoveredContactsEnabled && _autoAddRepeatersEnabled;
|
||||||
|
final autoAddRoomServers =
|
||||||
|
_autoAddDiscoveredContactsEnabled && _autoAddRoomServersEnabled;
|
||||||
|
final autoAddSensors =
|
||||||
|
_autoAddDiscoveredContactsEnabled && _autoAddSensorsEnabled;
|
||||||
|
final overwriteOldest =
|
||||||
|
_autoAddDiscoveredContactsEnabled && _overwriteOldestAutoAddEnabled;
|
||||||
|
|
||||||
setState(() {
|
setState(() {
|
||||||
_isSavingAutoDiscoverySettings = true;
|
_isSavingAutoDiscoverySettings = true;
|
||||||
@@ -588,25 +663,30 @@ class _DeviceConfigScreenState extends State<DeviceConfigScreen> {
|
|||||||
});
|
});
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
await connectionProvider.setAutoaddConfig(
|
||||||
|
autoAddUsers: autoAddUsers,
|
||||||
|
autoAddRepeaters: autoAddRepeaters,
|
||||||
|
autoAddRoomServers: autoAddRoomServers,
|
||||||
|
autoAddSensors: autoAddSensors,
|
||||||
|
overwriteOldest: overwriteOldest,
|
||||||
|
);
|
||||||
await connectionProvider.setOtherParams(
|
await connectionProvider.setOtherParams(
|
||||||
manualAddContacts: _autoAddDiscoveredContactsEnabled ? 0 : 1,
|
manualAddContacts: _autoAddFilterModeFlag,
|
||||||
telemetryModes: connectionProvider.deviceInfo.telemetryModes ?? 0,
|
telemetryModes: _telemetryModesForSave(connectionProvider),
|
||||||
advertLocationPolicy: connectionProvider.deviceInfo.advertLocPolicy ?? 0,
|
advertLocationPolicy: _advertLocationPolicyForSave(connectionProvider),
|
||||||
multiAcks: connectionProvider.deviceInfo.multiAcks ?? 0,
|
multiAcks: connectionProvider.deviceInfo.multiAcks ?? 0,
|
||||||
);
|
);
|
||||||
await connectionProvider.setAutoaddConfig(
|
await connectionProvider.getAutoaddConfig();
|
||||||
autoAddUsers: _autoAddUsersEnabled,
|
|
||||||
autoAddRepeaters: _autoAddRepeatersEnabled,
|
|
||||||
autoAddRoomServers: _autoAddRoomServersEnabled,
|
|
||||||
autoAddSensors: _autoAddSensorsEnabled,
|
|
||||||
overwriteOldest: _overwriteOldestAutoAddEnabled,
|
|
||||||
);
|
|
||||||
await connectionProvider.refreshDeviceInfo();
|
|
||||||
|
|
||||||
if (mounted) {
|
if (mounted) {
|
||||||
setState(() {
|
setState(() {
|
||||||
|
_syncAutoDiscoveryState(connectionProvider.deviceInfo);
|
||||||
|
_lastAutoDiscoverySignature = _autoDiscoverySignature(
|
||||||
|
connectionProvider.deviceInfo,
|
||||||
|
);
|
||||||
_isSavingAutoDiscoverySettings = false;
|
_isSavingAutoDiscoverySettings = false;
|
||||||
_autoDiscoverySettingsSaved = true;
|
_autoDiscoverySettingsSaved = true;
|
||||||
|
_autoDiscoverySettingsDirty = false;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
|
|||||||
Reference in New Issue
Block a user