Add config option reset

This commit is contained in:
problematicconsumer
2023-12-12 18:07:02 +03:30
parent 4c2a412820
commit 5e436e3f13
8 changed files with 84 additions and 24 deletions

View File

@@ -178,6 +178,7 @@
"clearSelection": "Clear selection" "clearSelection": "Clear selection"
}, },
"config": { "config": {
"resetBtn": "Reset options",
"serviceMode": "Service Mode", "serviceMode": "Service Mode",
"serviceModes": { "serviceModes": {
"proxy": "Proxy", "proxy": "Proxy",

View File

@@ -223,7 +223,8 @@
"tlsFragmentSleep": "TLS Fragment Sleep", "tlsFragmentSleep": "TLS Fragment Sleep",
"enableTlsMixedSniCase": "Enable TLS Mixed SNI Case", "enableTlsMixedSniCase": "Enable TLS Mixed SNI Case",
"enableTlsPadding": "Enable TLS Padding", "enableTlsPadding": "Enable TLS Padding",
"tlsPaddingSize": "TLS Padding" "tlsPaddingSize": "TLS Padding",
"resetBtn": "گزینه ها را بازنشانی کنید"
}, },
"geoAssets": { "geoAssets": {
"pageTitle": "فایل‌های مسیریابی", "pageTitle": "فایل‌های مسیریابی",

View File

@@ -223,7 +223,8 @@
"tlsFragmentSleep": "TLS Fragment Sleep", "tlsFragmentSleep": "TLS Fragment Sleep",
"enableTlsMixedSniCase": "Enable TLS Mixed SNI Case", "enableTlsMixedSniCase": "Enable TLS Mixed SNI Case",
"enableTlsPadding": "Enable TLS Padding", "enableTlsPadding": "Enable TLS Padding",
"tlsPaddingSize": "TLS Padding" "tlsPaddingSize": "TLS Padding",
"resetBtn": "Сбросить параметры"
}, },
"geoAssets": { "geoAssets": {
"pageTitle": "Активы маршрутизации", "pageTitle": "Активы маршрутизации",

View File

@@ -223,7 +223,8 @@
"tlsFragmentSleep": "TLS Fragment Sleep", "tlsFragmentSleep": "TLS Fragment Sleep",
"enableTlsMixedSniCase": "Enable TLS Mixed SNI Case", "enableTlsMixedSniCase": "Enable TLS Mixed SNI Case",
"enableTlsPadding": "Enable TLS Padding", "enableTlsPadding": "Enable TLS Padding",
"tlsPaddingSize": "TLS Padding" "tlsPaddingSize": "TLS Padding",
"resetBtn": "Ayarları sıfırla"
}, },
"geoAssets": { "geoAssets": {
"pageTitle": "Varlıkları Yönlendirme", "pageTitle": "Varlıkları Yönlendirme",

View File

@@ -223,7 +223,8 @@
"tlsFragmentSleep": "TLS Fragment Sleep", "tlsFragmentSleep": "TLS Fragment Sleep",
"enableTlsMixedSniCase": "Enable TLS Mixed SNI Case", "enableTlsMixedSniCase": "Enable TLS Mixed SNI Case",
"enableTlsPadding": "Enable TLS Padding", "enableTlsPadding": "Enable TLS Padding",
"tlsPaddingSize": "TLS Padding" "tlsPaddingSize": "TLS Padding",
"resetBtn": "重置选项"
}, },
"geoAssets": { "geoAssets": {
"pageTitle": "路由资源文件", "pageTitle": "路由资源文件",

View File

@@ -10,6 +10,7 @@ import 'package:hiddify/singbox/model/singbox_config_enum.dart';
import 'package:hiddify/singbox/model/singbox_config_option.dart'; import 'package:hiddify/singbox/model/singbox_config_option.dart';
import 'package:hiddify/singbox/model/singbox_rule.dart'; import 'package:hiddify/singbox/model/singbox_rule.dart';
import 'package:hiddify/utils/utils.dart'; import 'package:hiddify/utils/utils.dart';
import 'package:meta/meta.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:shared_preferences/shared_preferences.dart';
abstract interface class ConfigOptionRepository { abstract interface class ConfigOptionRepository {
@@ -19,6 +20,7 @@ abstract interface class ConfigOptionRepository {
TaskEither<ConfigOptionFailure, Unit> updateConfigOption( TaskEither<ConfigOptionFailure, Unit> updateConfigOption(
ConfigOptionPatch patch, ConfigOptionPatch patch,
); );
TaskEither<ConfigOptionFailure, Unit> resetConfigOption();
} }
class ConfigOptionRepositoryImpl class ConfigOptionRepositoryImpl
@@ -151,28 +153,48 @@ class ConfigOptionRepositoryImpl
return exceptionHandler( return exceptionHandler(
() async { () async {
final map = patch.toJson(); final map = patch.toJson();
for (final key in map.keys) { await updateByJson(map);
final value = map[key];
if (value != null) {
loggy.debug("updating [$key] to [$value]");
switch (value) {
case bool _:
await preferences.setBool(key, value);
case String _:
await preferences.setString(key, value);
case int _:
await preferences.setInt(key, value);
case double _:
await preferences.setDouble(key, value);
default:
loggy.warning("unexpected type");
}
}
}
return right(unit); return right(unit);
}, },
ConfigOptionUnexpectedFailure.new, ConfigOptionUnexpectedFailure.new,
); );
} }
@override
TaskEither<ConfigOptionFailure, Unit> resetConfigOption() {
return exceptionHandler(
() async {
final map = ConfigOptionEntity.initial.toJson();
await updateByJson(map);
return right(unit);
},
ConfigOptionUnexpectedFailure.new,
);
}
@visibleForTesting
Future<void> updateByJson(
Map<String, dynamic> options,
) async {
final map = ConfigOptionEntity.initial.toJson();
for (final key in map.keys) {
final value = options[key];
if (value != null) {
loggy.debug("updating [$key] to [$value]");
switch (value) {
case bool _:
await preferences.setBool(key, value);
case String _:
await preferences.setString(key, value);
case int _:
await preferences.setInt(key, value);
case double _:
await preferences.setDouble(key, value);
default:
loggy.warning("unexpected type");
}
}
}
}
} }

View File

@@ -28,4 +28,9 @@ class ConfigOptionNotifier extends _$ConfigOptionNotifier with AppLogger {
.run(); .run();
} }
} }
Future<void> resetOption() async {
await ref.read(configOptionRepositoryProvider).resetConfigOption().run();
ref.invalidateSelf();
}
} }

View File

@@ -3,6 +3,7 @@ import 'package:flutter/material.dart';
import 'package:flutter/services.dart'; import 'package:flutter/services.dart';
import 'package:gap/gap.dart'; import 'package:gap/gap.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/failures.dart';
import 'package:hiddify/core/model/range.dart'; import 'package:hiddify/core/model/range.dart';
import 'package:hiddify/features/config_option/model/config_option_entity.dart'; import 'package:hiddify/features/config_option/model/config_option_entity.dart';
import 'package:hiddify/features/config_option/model/config_option_patch.dart'; import 'package:hiddify/features/config_option/model/config_option_patch.dart';
@@ -45,6 +46,14 @@ class ConfigOptionsPage extends HookConsumerWidget {
); );
}, },
), ),
PopupMenuItem(
child: Text(t.settings.config.resetBtn),
onTap: () async {
await ref
.read(configOptionNotifierProvider.notifier)
.resetOption();
},
),
]; ];
}, },
), ),
@@ -377,7 +386,26 @@ class ConfigOptionsPage extends HookConsumerWidget {
const Gap(24), const Gap(24),
], ],
), ),
// TODO show appropriate error/loading widgets AsyncError(:final error) => Center(
child: SingleChildScrollView(
child: Column(
children: [
const Icon(Icons.error),
const Gap(2),
Text(t.presentShortError(error)),
const Gap(2),
TextButton(
onPressed: () async {
await ref
.read(configOptionNotifierProvider.notifier)
.resetOption();
},
child: Text(t.settings.config.resetBtn),
),
],
),
),
),
_ => const SizedBox(), _ => const SizedBox(),
}, },
); );