diff --git a/lib/l10n/app_en.arb b/lib/l10n/app_en.arb index 5c202ab..bbb19bc 100644 --- a/lib/l10n/app_en.arb +++ b/lib/l10n/app_en.arb @@ -462,5 +462,11 @@ "overrideMaximumTtl": "Override maximum TTL", "overrideMaximumTtlDescription": "Set a maximum time-to-live value (seconds) for entries in the DNS cache.", "optimisticCaching": "Optimistic caching", - "optimisticCachingDescription": "Make AdGuard Home respond from the cache even when the entries are expired and also try to refresh them." + "optimisticCachingDescription": "Make AdGuard Home respond from the cache even when the entries are expired and also try to refresh them.", + "loadingDnsConfig": "Loading DNS configuration...", + "dnsConfigNotLoaded": "DNS config could not be loaded.", + "blockingIpv4": "Blocking IPv4", + "blockingIpv4Description": "IP address to be returned for a blocked A request", + "blockingIpv6": "Blocking IPv6", + "blockingIpv6Description": "IP address to be returned for a blocked AAAA request" } \ No newline at end of file diff --git a/lib/l10n/app_es.arb b/lib/l10n/app_es.arb index e590707..5410d90 100644 --- a/lib/l10n/app_es.arb +++ b/lib/l10n/app_es.arb @@ -461,6 +461,12 @@ "overrideMinimumTtlDescription": "Amplía el corto tiempo de vida (segundos) de los valores recibidos del servidor DNS de subida al almacenar en caché las respuestas DNS.", "overrideMaximumTtl": "Anular TTL máximo", "overrideMaximumTtlDescription": "Establece un valor de tiempo de vida (segundos) máximo para las entradas en la caché DNS.", - "optimisticCaching": "Optimistic caching", - "optimisticCachingDescription": "Haz que AdGuard Home responda desde la caché incluso cuando las entradas estén expiradas y también intente actualizarlas." + "optimisticCaching": "Cacheado optimista", + "optimisticCachingDescription": "Haz que AdGuard Home responda desde la caché incluso cuando las entradas estén expiradas y también intente actualizarlas.", + "loadingDnsConfig": "Cargando configuración de DNS...", + "dnsConfigNotLoaded": "No se ha podido cargar la configuración de DNS.", + "blockingIpv4": "Bloqueo de IPv4", + "blockingIpv4Description": "Dirección IP devolverá una petición A bloqueada", + "blockingIpv6": "Bloqueo de IPv6", + "blockingIpv6Description": "Dirección IP devolverá una petición AAAA bloqueada" } \ No newline at end of file diff --git a/lib/models/dns_info.dart b/lib/models/dns_info.dart new file mode 100644 index 0000000..de2e308 --- /dev/null +++ b/lib/models/dns_info.dart @@ -0,0 +1,107 @@ +import 'dart:convert'; + +class DnsInfo { + int loadStatus = 0; + DnsInfoData? data; + + DnsInfo({ + required this.loadStatus, + this.data + }); +} + +DnsInfoData dnsInfoDataFromJson(String str) => DnsInfoData.fromJson(json.decode(str)); + +String dnsInfoDataToJson(DnsInfoData data) => json.encode(data.toJson()); + +class DnsInfoData { + List upstreamDns; + String upstreamDnsFile; + List bootstrapDns; + bool protectionEnabled; + int ratelimit; + String blockingMode; + bool ednsCsEnabled; + bool dnssecEnabled; + bool disableIpv6; + String upstreamMode; + int cacheSize; + int cacheTtlMin; + int cacheTtlMax; + bool cacheOptimistic; + bool resolveClients; + bool usePrivatePtrResolvers; + List localPtrUpstreams; + String blockingIpv4; + String blockingIpv6; + + List defaultLocalPtrUpstreams; + DnsInfoData({ + required this.upstreamDns, + required this.upstreamDnsFile, + required this.bootstrapDns, + required this.protectionEnabled, + required this.ratelimit, + required this.blockingMode, + required this.ednsCsEnabled, + required this.dnssecEnabled, + required this.disableIpv6, + required this.upstreamMode, + required this.cacheSize, + required this.cacheTtlMin, + required this.cacheTtlMax, + required this.cacheOptimistic, + required this.resolveClients, + required this.usePrivatePtrResolvers, + required this.localPtrUpstreams, + required this.blockingIpv4, + required this.blockingIpv6, + required this.defaultLocalPtrUpstreams, + }); + + factory DnsInfoData.fromJson(Map json) => DnsInfoData( + upstreamDns: json["upstream_dns"] != null ? List.from(json["upstream_dns"].map((x) => x)) : [], + upstreamDnsFile: json["upstream_dns_file"], + bootstrapDns: List.from(json["bootstrap_dns"].map((x) => x)), + protectionEnabled: json["protection_enabled"], + ratelimit: json["ratelimit"], + blockingMode: json["blocking_mode"], + ednsCsEnabled: json["edns_cs_enabled"], + dnssecEnabled: json["dnssec_enabled"], + disableIpv6: json["disable_ipv6"], + upstreamMode: json["upstream_mode"], + cacheSize: json["cache_size"], + cacheTtlMin: json["cache_ttl_min"], + cacheTtlMax: json["cache_ttl_max"], + cacheOptimistic: json["cache_optimistic"], + resolveClients: json["resolve_clients"], + usePrivatePtrResolvers: json["use_private_ptr_resolvers"], + localPtrUpstreams: json["local_ptr_upstreams"] != null ? List.from(json["local_ptr_upstreams"].map((x) => x)) : [], + blockingIpv4: json["blocking_ipv4"], + blockingIpv6: json["blocking_ipv6"], + defaultLocalPtrUpstreams: json["default_local_ptr_upstreams"] != null ? List.from(json["default_local_ptr_upstreams"].map((x) => x)) : [], + ); + + Map toJson() => { + "upstream_dns": List.from(upstreamDns.map((x) => x)), + "upstream_dns_file": upstreamDnsFile, + "bootstrap_dns": List.from(bootstrapDns.map((x) => x)), + "protection_enabled": protectionEnabled, + "ratelimit": ratelimit, + "blocking_mode": blockingMode, + "edns_cs_enabled": ednsCsEnabled, + "dnssec_enabled": dnssecEnabled, + "disable_ipv6": disableIpv6, + "upstream_mode": upstreamMode, + "cache_size": cacheSize, + "cache_ttl_min": cacheTtlMin, + "cache_ttl_max": cacheTtlMax, + "cache_optimistic": cacheOptimistic, + "resolve_clients": resolveClients, + "use_private_ptr_resolvers": usePrivatePtrResolvers, + "local_ptr_upstreams": List.from(localPtrUpstreams.map((x) => x)), + "blocking_ipv4": blockingIpv4, + "blocking_ipv6": blockingIpv6, + "default_local_ptr_upstreams": List.from(defaultLocalPtrUpstreams.map((x) => x)), + }; +} diff --git a/lib/providers/servers_provider.dart b/lib/providers/servers_provider.dart index bac7da2..9ec86c0 100644 --- a/lib/providers/servers_provider.dart +++ b/lib/providers/servers_provider.dart @@ -3,6 +3,7 @@ import 'package:sqflite/sqflite.dart'; import 'package:adguard_home_manager/models/filtering.dart'; import 'package:adguard_home_manager/models/dhcp.dart'; +import 'package:adguard_home_manager/models/dns_info.dart'; import 'package:adguard_home_manager/models/rewrite_rules.dart'; import 'package:adguard_home_manager/models/filtering_status.dart'; import 'package:adguard_home_manager/models/clients_allowed_blocked.dart'; @@ -43,6 +44,11 @@ class ServersProvider with ChangeNotifier { data: null ); + final DnsInfo _dnsInfo = DnsInfo( + loadStatus: 0, // 0 = loading, 1 = loaded, 2 = error + data: null + ); + FilteringStatus? _filteringStatus; List get serversList { @@ -81,6 +87,10 @@ class ServersProvider with ChangeNotifier { return _rewriteRules; } + DnsInfo get dnsInfo { + return _dnsInfo; + } + void setDbInstance(Database db) { _dbInstance = db; } @@ -178,6 +188,18 @@ class ServersProvider with ChangeNotifier { notifyListeners(); } } + + void setDnsInfoData(DnsInfoData data) { + _dnsInfo.data = data; + notifyListeners(); + } + + void setDnsInfoLoadStatus(int status, bool notify) { + _dnsInfo.loadStatus = status; + if (notify == true) { + notifyListeners(); + } + } Future createServer(Server server) async { final saved = await saveServerIntoDb(server); diff --git a/lib/screens/settings/dns/bootstrap_dns.dart b/lib/screens/settings/dns/bootstrap_dns.dart index 3ffba3f..f8bbc4b 100644 --- a/lib/screens/settings/dns/bootstrap_dns.dart +++ b/lib/screens/settings/dns/bootstrap_dns.dart @@ -1,17 +1,32 @@ import 'package:flutter/material.dart'; import 'package:flutter_gen/gen_l10n/app_localizations.dart'; +import 'package:adguard_home_manager/providers/servers_provider.dart'; + class BootstrapDnsScreen extends StatefulWidget { - const BootstrapDnsScreen({Key? key}) : super(key: key); + final ServersProvider serversProvider; + + const BootstrapDnsScreen({ + Key? key, + required this.serversProvider, + }) : super(key: key); @override State createState() => _BootstrapDnsScreenState(); } class _BootstrapDnsScreenState extends State { - List bootstrapControllers = [ - TextEditingController() - ]; + List bootstrapControllers = []; + + @override + void initState() { + for (var item in widget.serversProvider.dnsInfo.data!.bootstrapDns) { + final controller = TextEditingController(); + controller.text = item; + bootstrapControllers.add(controller); + } + super.initState(); + } @override Widget build(BuildContext context) { diff --git a/lib/screens/settings/dns/cache_config.dart b/lib/screens/settings/dns/cache_config.dart index 253a96f..13c5b60 100644 --- a/lib/screens/settings/dns/cache_config.dart +++ b/lib/screens/settings/dns/cache_config.dart @@ -3,8 +3,15 @@ import 'package:flutter_gen/gen_l10n/app_localizations.dart'; import 'package:adguard_home_manager/widgets/custom_switch_list_tile.dart'; +import 'package:adguard_home_manager/providers/servers_provider.dart'; + class CacheConfigDnsScreen extends StatefulWidget { - const CacheConfigDnsScreen({Key? key}) : super(key: key); + final ServersProvider serversProvider; + + const CacheConfigDnsScreen({ + Key? key, + required this.serversProvider + }) : super(key: key); @override State createState() => _CacheConfigDnsScreenState(); @@ -22,6 +29,15 @@ class _CacheConfigDnsScreenState extends State { bool optimisticCache = false; + @override + void initState() { + cacheSizeController.text = widget.serversProvider.dnsInfo.data!.cacheSize.toString(); + overrideMinTtlController.text = widget.serversProvider.dnsInfo.data!.cacheTtlMin.toString(); + overrideMaxTtlController.text = widget.serversProvider.dnsInfo.data!.cacheTtlMax.toString(); + optimisticCache = widget.serversProvider.dnsInfo.data!.cacheOptimistic; + super.initState(); + } + @override Widget build(BuildContext context) { @@ -35,7 +51,7 @@ class _CacheConfigDnsScreenState extends State { return Padding( padding: const EdgeInsets.symmetric(horizontal: 20), child: TextFormField( - controller: overrideMinTtlController, + controller: controller, onChanged: onChanged, decoration: InputDecoration( prefixIcon: const Icon(Icons.timer_rounded), diff --git a/lib/screens/settings/dns/dns.dart b/lib/screens/settings/dns/dns.dart index 0446b4c..8916afe 100644 --- a/lib/screens/settings/dns/dns.dart +++ b/lib/screens/settings/dns/dns.dart @@ -1,4 +1,5 @@ import 'package:flutter/material.dart'; +import 'package:provider/provider.dart'; import 'package:flutter_gen/gen_l10n/app_localizations.dart'; import 'package:adguard_home_manager/screens/settings/dns/cache_config.dart'; @@ -7,79 +8,201 @@ import 'package:adguard_home_manager/screens/settings/dns/bootstrap_dns.dart'; import 'package:adguard_home_manager/screens/settings/dns/private_reverse_servers.dart'; import 'package:adguard_home_manager/screens/settings/dns/upstream_dns.dart'; +import 'package:adguard_home_manager/providers/servers_provider.dart'; +import 'package:adguard_home_manager/providers/app_config_provider.dart'; +import 'package:adguard_home_manager/services/http_requests.dart'; + class DnsSettings extends StatelessWidget { const DnsSettings({Key? key}) : super(key: key); @override Widget build(BuildContext context) { + final serversProvider = Provider.of(context); + final appConfigProvider = Provider.of(context); + + return DnsSettingsWidget( + serversProvider: serversProvider, + appConfigProvider: appConfigProvider, + ); + } +} +class DnsSettingsWidget extends StatefulWidget { + final ServersProvider serversProvider; + final AppConfigProvider appConfigProvider; + + const DnsSettingsWidget({ + required this.serversProvider, + required this.appConfigProvider, + Key? key + }) : super(key: key); + + @override + State createState() => _DnsSettingsWidgetState(); +} + +class _DnsSettingsWidgetState extends State { + + void fetchData() async { + widget.serversProvider.setDnsInfoLoadStatus(0, false); + + final result = await getDnsInfo(server: widget.serversProvider.selectedServer!); + + if (mounted) { + if (result['result'] == 'success') { + widget.serversProvider.setDnsInfoData(result['data']); + widget.serversProvider.setDnsInfoLoadStatus(1, true); + } + else { + widget.appConfigProvider.addLog(result['log']); + widget.serversProvider.setDnsInfoLoadStatus(2, true); + } + } + } + + @override + void initState() { + fetchData(); + super.initState(); + } + + @override + Widget build(BuildContext context) { + final serversProvider = Provider.of(context); + + Widget generateBody() { + switch (widget.serversProvider.dnsInfo.loadStatus) { + case 0: + return SizedBox( + width: double.maxFinite, + child: Column( + mainAxisAlignment: MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, + children: [ + const CircularProgressIndicator(), + const SizedBox(height: 30), + Text( + AppLocalizations.of(context)!.loadingDnsConfig, + textAlign: TextAlign.center, + style: const TextStyle( + fontSize: 22, + color: Colors.grey, + ), + ) + ], + ) + ); + + case 1: + return ListView( + children: [ + ListTile( + title: Text( + AppLocalizations.of(context)!.upstreamDns, + style: const TextStyle( + fontSize: 16, + fontWeight: FontWeight.normal + ), + ), + onTap: () => Navigator.push(context, MaterialPageRoute( + builder: (context) => UpstreamDnsScreen( + serversProvider: serversProvider + ) + )), + ), + ListTile( + title: Text( + AppLocalizations.of(context)!.bootstrapDns, + style: const TextStyle( + fontSize: 16, + fontWeight: FontWeight.normal + ), + ), + onTap: () => Navigator.push(context, MaterialPageRoute( + builder: (context) => BootstrapDnsScreen( + serversProvider: serversProvider + ) + )), + ), + ListTile( + title: Text( + AppLocalizations.of(context)!.privateReverseDnsServers, + style: const TextStyle( + fontSize: 16, + fontWeight: FontWeight.normal + ), + ), + onTap: () => Navigator.push(context, MaterialPageRoute( + builder: (context) => PrivateReverseDnsServersScreen( + serversProvider: serversProvider + ) + )), + ), + ListTile( + title: Text( + AppLocalizations.of(context)!.dnsServerSettings, + style: const TextStyle( + fontSize: 16, + fontWeight: FontWeight.normal + ), + ), + onTap: () => Navigator.push(context, MaterialPageRoute( + builder: (context) => DnsServerSettingsScreen( + serversProvider: serversProvider + ) + )), + ), + ListTile( + title: Text( + AppLocalizations.of(context)!.dnsCacheConfig, + style: const TextStyle( + fontSize: 16, + fontWeight: FontWeight.normal + ), + ), + onTap: () => Navigator.push(context, MaterialPageRoute( + builder: (context) => CacheConfigDnsScreen( + serversProvider: serversProvider + ) + )), + ), + ], + ); + + case 2: + return SizedBox( + width: double.maxFinite, + child: Column( + mainAxisAlignment: MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, + children: [ + const Icon( + Icons.error, + color: Colors.red, + size: 50, + ), + const SizedBox(height: 30), + Text( + AppLocalizations.of(context)!.dnsConfigNotLoaded, + textAlign: TextAlign.center, + style: const TextStyle( + fontSize: 22, + color: Colors.grey, + ), + ) + ], + ), + ); + + default: + return const SizedBox(); + } + } + return Scaffold( appBar: AppBar( title: Text(AppLocalizations.of(context)!.dnsSettings), ), - body: ListView( - children: [ - ListTile( - title: Text( - AppLocalizations.of(context)!.upstreamDns, - style: const TextStyle( - fontSize: 16, - fontWeight: FontWeight.normal - ), - ), - onTap: () => Navigator.push(context, MaterialPageRoute( - builder: (context) => const UpstreamDnsScreen() - )), - ), - ListTile( - title: Text( - AppLocalizations.of(context)!.bootstrapDns, - style: const TextStyle( - fontSize: 16, - fontWeight: FontWeight.normal - ), - ), - onTap: () => Navigator.push(context, MaterialPageRoute( - builder: (context) => const BootstrapDnsScreen() - )), - ), - ListTile( - title: Text( - AppLocalizations.of(context)!.privateReverseDnsServers, - style: const TextStyle( - fontSize: 16, - fontWeight: FontWeight.normal - ), - ), - onTap: () => Navigator.push(context, MaterialPageRoute( - builder: (context) => const PrivateReverseDnsServersScreen() - )), - ), - ListTile( - title: Text( - AppLocalizations.of(context)!.dnsServerSettings, - style: const TextStyle( - fontSize: 16, - fontWeight: FontWeight.normal - ), - ), - onTap: () => Navigator.push(context, MaterialPageRoute( - builder: (context) => const DnsServerSettingsScreen() - )), - ), - ListTile( - title: Text( - AppLocalizations.of(context)!.dnsCacheConfig, - style: const TextStyle( - fontSize: 16, - fontWeight: FontWeight.normal - ), - ), - onTap: () => Navigator.push(context, MaterialPageRoute( - builder: (context) => const CacheConfigDnsScreen() - )), - ), - ], - ), + body: generateBody(), ); } } \ No newline at end of file diff --git a/lib/screens/settings/dns/dns_server_settings.dart b/lib/screens/settings/dns/dns_server_settings.dart index 5490948..771a572 100644 --- a/lib/screens/settings/dns/dns_server_settings.dart +++ b/lib/screens/settings/dns/dns_server_settings.dart @@ -5,8 +5,15 @@ import 'package:adguard_home_manager/widgets/custom_radio_list_tile.dart'; import 'package:adguard_home_manager/screens/settings/section_label.dart'; import 'package:adguard_home_manager/widgets/custom_switch_list_tile.dart'; +import 'package:adguard_home_manager/providers/servers_provider.dart'; + class DnsServerSettingsScreen extends StatefulWidget { - const DnsServerSettingsScreen({Key? key}) : super(key: key); + final ServersProvider serversProvider; + + const DnsServerSettingsScreen({ + Key? key, + required this.serversProvider + }) : super(key: key); @override State createState() => _DnsServerSettingsScreenState(); @@ -21,8 +28,36 @@ class _DnsServerSettingsScreenState extends State { String blockingMode = "default"; + final TextEditingController ipv4controller = TextEditingController(); + String? ipv4error; + final TextEditingController ipv6controller = TextEditingController(); + String? ipv6error; + + @override + void initState() { + limitRequestsController.text = widget.serversProvider.dnsInfo.data!.ratelimit.toString(); + enableEdns = widget.serversProvider.dnsInfo.data!.ednsCsEnabled; + enableDnssec = widget.serversProvider.dnsInfo.data!.dnssecEnabled; + disableIpv6Resolving = widget.serversProvider.dnsInfo.data!.disableIpv6; + blockingMode = widget.serversProvider.dnsInfo.data!.blockingMode; + ipv4controller.text = widget.serversProvider.dnsInfo.data!.blockingIpv4; + ipv6controller.text = widget.serversProvider.dnsInfo.data!.blockingIpv6; + super.initState(); + } + @override Widget build(BuildContext context) { + + void updateBlockingMode(String mode) { + if (mode != 'custom_ip') { + ipv4controller.text = ''; + ipv4error = null; + ipv6controller.text = ''; + ipv6error = null; + } + setState(() => blockingMode = mode); + } + return Scaffold( appBar: AppBar( title: Text(AppLocalizations.of(context)!.dnsServerSettings), @@ -81,7 +116,7 @@ class _DnsServerSettingsScreenState extends State { radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: AppLocalizations.of(context)!.defaultMode, subtitle: AppLocalizations.of(context)!.defaultDescription, - onChanged: (value) => setState(() => blockingMode = value), + onChanged: updateBlockingMode, ), CustomRadioListTile( groupValue: blockingMode, @@ -89,7 +124,7 @@ class _DnsServerSettingsScreenState extends State { radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: "REFUSED", subtitle: AppLocalizations.of(context)!.refusedDescription, - onChanged: (value) => setState(() => blockingMode = value), + onChanged: updateBlockingMode, ), CustomRadioListTile( groupValue: blockingMode, @@ -97,7 +132,7 @@ class _DnsServerSettingsScreenState extends State { radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: "NXDOMAIN", subtitle: AppLocalizations.of(context)!.nxdomainDescription, - onChanged: (value) => setState(() => blockingMode = value), + onChanged: updateBlockingMode, ), CustomRadioListTile( groupValue: blockingMode, @@ -105,7 +140,7 @@ class _DnsServerSettingsScreenState extends State { radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: AppLocalizations.of(context)!.nullIp, subtitle: AppLocalizations.of(context)!.nullIpDescription, - onChanged: (value) => setState(() => blockingMode = value), + onChanged: updateBlockingMode, ), CustomRadioListTile( groupValue: blockingMode, @@ -113,8 +148,53 @@ class _DnsServerSettingsScreenState extends State { radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: AppLocalizations.of(context)!.customIp, subtitle: AppLocalizations.of(context)!.customIpDescription, - onChanged: (value) => setState(() => blockingMode = value), + onChanged: updateBlockingMode, ), + const SizedBox(height: 10), + if (blockingMode == 'custom_ip') ...[ + Padding( + padding: const EdgeInsets.symmetric(horizontal: 24), + child: TextFormField( + controller: ipv4controller, + // onChanged: onChanged, + decoration: InputDecoration( + prefixIcon: const Icon(Icons.link_rounded), + border: const OutlineInputBorder( + borderRadius: BorderRadius.all( + Radius.circular(10) + ) + ), + errorText: ipv4error, + helperText: AppLocalizations.of(context)!.blockingIpv4Description, + helperMaxLines: 10, + labelText: AppLocalizations.of(context)!.blockingIpv4, + ), + keyboardType: TextInputType.number, + ), + ), + const SizedBox(height: 30), + Padding( + padding: const EdgeInsets.symmetric(horizontal: 24), + child: TextFormField( + controller: ipv6controller, + // onChanged: onChanged, + decoration: InputDecoration( + prefixIcon: const Icon(Icons.link_rounded), + border: const OutlineInputBorder( + borderRadius: BorderRadius.all( + Radius.circular(10) + ) + ), + errorText: ipv6error, + helperText: AppLocalizations.of(context)!.blockingIpv6Description, + helperMaxLines: 10, + labelText: AppLocalizations.of(context)!.blockingIpv6, + ), + keyboardType: TextInputType.number, + ), + ), + const SizedBox(height: 30) + ] ], ), ); diff --git a/lib/screens/settings/dns/private_reverse_servers.dart b/lib/screens/settings/dns/private_reverse_servers.dart index 83e0488..3c37f35 100644 --- a/lib/screens/settings/dns/private_reverse_servers.dart +++ b/lib/screens/settings/dns/private_reverse_servers.dart @@ -3,17 +3,22 @@ import 'package:flutter_gen/gen_l10n/app_localizations.dart'; import 'package:adguard_home_manager/widgets/custom_switch_list_tile.dart'; +import 'package:adguard_home_manager/providers/servers_provider.dart'; + class PrivateReverseDnsServersScreen extends StatefulWidget { - const PrivateReverseDnsServersScreen({Key? key}) : super(key: key); + final ServersProvider serversProvider; + + const PrivateReverseDnsServersScreen({ + Key? key, + required this.serversProvider, + }) : super(key: key); @override State createState() => _PrivateReverseDnsServersScreenState(); } class _PrivateReverseDnsServersScreenState extends State { - List privateControllers = []; - - List defaultReverseResolvers = ["80.58.61.250", "80.58.61.251"]; + List defaultReverseResolvers = []; bool editReverseResolvers = false; List reverseResolversControllers = [ TextEditingController() @@ -21,6 +26,24 @@ class _PrivateReverseDnsServersScreenState extends State createState() => _UpstreamDnsScreenState(); } class _UpstreamDnsScreenState extends State { - List upstreamControllers = [ - TextEditingController() - ]; + List upstreamControllers = []; String upstreamMode = "load_balancing"; + @override + void initState() { + for (var item in widget.serversProvider.dnsInfo.data!.upstreamDns) { + final controller = TextEditingController(); + controller.text = item; + upstreamControllers.add(controller); + } + upstreamMode = widget.serversProvider.dnsInfo.data!.upstreamMode; + super.initState(); + } + @override Widget build(BuildContext context) { return Scaffold( @@ -88,7 +104,7 @@ class _UpstreamDnsScreenState extends State { SectionLabel(label: AppLocalizations.of(context)!.dnsMode), CustomRadioListTile( groupValue: upstreamMode, - value: "load_balancing", + value: "", radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: AppLocalizations.of(context)!.loadBalancing, subtitle: AppLocalizations.of(context)!.loadBalancingDescription, @@ -96,7 +112,7 @@ class _UpstreamDnsScreenState extends State { ), CustomRadioListTile( groupValue: upstreamMode, - value: "parallel_requests", + value: "parallel", radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: AppLocalizations.of(context)!.parallelRequests, subtitle: AppLocalizations.of(context)!.parallelRequestsDescription, @@ -104,7 +120,7 @@ class _UpstreamDnsScreenState extends State { ), CustomRadioListTile( groupValue: upstreamMode, - value: "fastest_ip_address", + value: "fastest_addr", radioBackgroundColor: Theme.of(context).dialogBackgroundColor, title: AppLocalizations.of(context)!.fastestIpAddress, subtitle: AppLocalizations.of(context)!.fastestIpAddressDescription, diff --git a/lib/services/http_requests.dart b/lib/services/http_requests.dart index 4d2f484..50a0dd2 100644 --- a/lib/services/http_requests.dart +++ b/lib/services/http_requests.dart @@ -5,6 +5,7 @@ import 'dart:convert'; import 'dart:io'; import 'package:adguard_home_manager/models/dhcp.dart'; +import 'package:adguard_home_manager/models/dns_info.dart'; import 'package:adguard_home_manager/models/filtering.dart'; import 'package:adguard_home_manager/models/logs.dart'; import 'package:adguard_home_manager/models/filtering_status.dart'; @@ -1618,4 +1619,39 @@ Future clearLogs({ else { return result; } +} + +Future getDnsInfo({ + required Server server, +}) async { + final result = await apiRequest( + urlPath: '/dns_info', + method: 'get', + server: server, + type: 'get_dns_info' + ); + + if (result['hasResponse'] == true) { + if (result['statusCode'] == 200) { + return { + 'result': 'success' , + 'data': DnsInfoData.fromJson(jsonDecode(result['body'])) + }; + } + else { + return { + 'result': 'error', + 'log': AppLog( + type: 'get_dns_info', + dateTime: DateTime.now(), + message: 'error_code_not_expected', + statusCode: result['statusCode'].toString(), + resBody: result['body'], + ) + }; + } + } + else { + return result; + } } \ No newline at end of file