Compare commits

...

340 Commits

Author SHA1 Message Date
Ildar Kamalov
e6bd2a101d Merge: + translations: add twosky config file
* commit '568a7a73347862c30830d956a26e2beb31c27857':
  + translations: add twosky config file
2019-08-20 18:07:16 +03:00
Simon Zolin
d2e0940053 Merge: * use dnsproxy v0.18.4
* commit '31af6ae9147fd85d593237ec6715c428d56740ed':
  * use dnsproxy v0.18.4
2019-08-20 18:05:21 +03:00
Simon Zolin
31af6ae914 * use dnsproxy v0.18.4 2019-08-20 17:59:40 +03:00
Ildar Kamalov
568a7a7334 + translations: add twosky config file 2019-08-20 17:19:49 +03:00
Simon Zolin
09a52436fb Merge: - dnsforward: don't use dnsfilter object after it's closed
Close #940

* commit '94552a30d7080c8471f7fca370a5905c6c420272':
  - dnsforward: don't use dnsfilter object after it's closed
2019-08-20 15:36:34 +03:00
Simon Zolin
94552a30d7 - dnsforward: don't use dnsfilter object after it's closed 2019-08-20 15:07:39 +03:00
Andrey Meshkov
87ca9ed9c2 -(dnsforward): fixed sigsegv when protection is disabled
* commit 'c82e93cfc7cf439a5e5bf9b8bc27f5b68b528b53':
  -(dnsforward): fixed sigsegv when protection is disabled
2019-08-20 15:03:17 +03:00
Andrey Meshkov
c82e93cfc7 -(dnsforward): fixed sigsegv when protection is disabled
Also, fixed all golint issues

 Closes: #941
2019-08-20 00:55:32 +03:00
Simon Zolin
91a1eb9e06 Merge: * use dnsproxy v0.18.3
* commit 'c54e2585ac86d045fe21ae61af35e6a4eeda5d91':
  * use dnsproxy v0.18.3
2019-08-19 17:10:03 +03:00
Simon Zolin
c54e2585ac * use dnsproxy v0.18.3 2019-08-19 17:02:19 +03:00
Simon Zolin
5b555f95ff Merge: + dhcp: use --workdir value for "leases.db" file path
Close #935

* commit '8e08cddf647226d5e8e5f41307b60274a3f232e5':
  + dhcp: use --workdir value for "leases.db" file path
2019-08-19 16:55:42 +03:00
Simon Zolin
8e08cddf64 + dhcp: use --workdir value for "leases.db" file path 2019-08-19 14:40:10 +03:00
Simon Zolin
eba7931c2d Merge: Revert: * dnsfilter: use fastcache instead of gcache
* commit 'b37208564bd170f21347db9cfde39614ea4a02c2':
  - fix build: we're using a new gcache module now
  Revert "+ config: add cache size settings"
  Revert "* dnsfilter: use fastcache instead of gcache"
  Revert "fix tests"
2019-08-16 16:13:03 +03:00
Andrey Meshkov
5448000f7b *(global): travis slack notification 2019-08-16 16:08:56 +03:00
Simon Zolin
b37208564b - fix build: we're using a new gcache module now 2019-08-16 15:43:12 +03:00
Simon Zolin
d46ebe1c8b Revert "+ config: add cache size settings"
This reverts commit 81303b5db7.
2019-08-16 15:17:38 +03:00
Simon Zolin
68d5d595b6 Revert "* dnsfilter: use fastcache instead of gcache"
This reverts commit 6f51df7d2e.
2019-08-16 15:17:38 +03:00
Simon Zolin
56c69cdb79 Revert "fix tests"
This reverts commit d9265aa9a8.
2019-08-16 15:11:57 +03:00
Simon Zolin
28cc9dc973 Merge: + travis: slack notifications
* commit '8aef6d8f91bbac5ce47539ef121a73ea75d12042':
  + travis: slack notifications
2019-08-16 13:50:59 +03:00
Simon Zolin
8aef6d8f91 + travis: slack notifications 2019-08-16 13:47:51 +03:00
Simon Zolin
1f0c8c6a3b Merge: * use dnsproxy v0.18.1
Close #847

* commit '0faf144853df3cf5628d917e936aae0c508aa753':
  * use dnsproxy v0.18.1
2019-08-14 19:18:23 +03:00
Simon Zolin
0faf144853 * use dnsproxy v0.18.1 2019-08-14 18:49:27 +03:00
Simon Zolin
57cfd97a6a Merge: * client: update translations
Close #915

* commit '256030f0c1b780dd73618965a0738162b7835780':
  * client: update translations
2019-08-14 12:48:35 +03:00
Simon Zolin
256030f0c1 * client: update translations 2019-08-13 17:36:19 +03:00
Simon Zolin
ea2a523f8c Merge: * config: set default DNS server as IP addresses
Close #926

* commit '9d7285e42c61852ab5106402b0138ef27dbc5b0f':
  * config: set default DNS server as IP addresses
2019-08-13 13:48:12 +03:00
Simon Zolin
b302ccb491 Merge: * filters update: increase update period to 24 hours
Close #929

* commit '8b63811fa98333cae3c33cac5cc3484995d3ea09':
  * filters update: increase update period to 24 hours
2019-08-13 12:33:11 +03:00
Simon Zolin
4407ad3585 Merge: - readme: fix misspelling
Close #924

* commit 'd7ff61ca590cca9d7fd2374934da790b11aabfdb':
  - readme: fix misspelling
2019-08-13 12:32:04 +03:00
Simon Zolin
9d7285e42c * config: set default DNS server as IP addresses
* config: add "1.0.0.1" to default bootstrap addresses
2019-08-13 11:52:06 +03:00
Simon Zolin
d7ff61ca59 - readme: fix misspelling 2019-08-13 10:41:06 +03:00
Simon Zolin
8b63811fa9 * filters update: increase update period to 24 hours 2019-08-13 10:30:28 +03:00
Andrey Meshkov
5c3dfd114c *(global): update dependencies 2019-08-11 20:45:01 +03:00
Simon Zolin
61897db0c5 Merge: * rDNS: refactor: move code to a separate file
* commit 'ccf72b60084b4818e64105b0687eb98434f14cf3':
  * safebrowsing/parental: split some code
  * rDNS: make log messages' level = debug
  * rDNS: refactor: move code to a separate file
2019-08-08 12:14:32 +03:00
Simon Zolin
ccf72b6008 * safebrowsing/parental: split some code
* dnsfilter.CheckHost() doesn't support host="hostname." (with a trailing dot) anymore
2019-08-08 12:11:24 +03:00
Simon Zolin
d659e7ee08 * rDNS: make log messages' level = debug 2019-08-08 12:11:24 +03:00
Simon Zolin
4f08f96607 * rDNS: refactor: move code to a separate file 2019-08-08 12:10:50 +03:00
Simon Zolin
77592c6382 Merge: * use golibs v0.1.4
Close #893

* commit '272115724df8748afc1954538673786cd56f9365':
  * use golibs v0.1.4
2019-08-07 15:12:44 +03:00
Simon Zolin
272115724d * use golibs v0.1.4 2019-08-06 18:55:56 +03:00
Simon Zolin
a59b6b3054 Merge: block access to specific services
Close #819

* commit 'e7001c3bc4a7e1ec53d810cafbc90d7f2a624af5':
  * config upgrade: sequential processing
  * config: upgrade schema version: 3 -> 4
  + client: add prefix to the service icons
  + client: handle blocked services
  + openapi: add /blocked_services/*
  + openapi: clients: add "blocked_services" field
  * refactor
  + /control/blocked_services/* API
  + dnsfilter: use global and per-client BlockedServices array
  + clients: add BlockedServices field
  + config: store/load "blocked_services" per-client setting
  + doc: add "Services Filter" section
2019-08-05 14:13:54 +03:00
Simon Zolin
e7001c3bc4 * config upgrade: sequential processing 2019-08-05 14:12:22 +03:00
Simon Zolin
1b95a85651 * config: upgrade schema version: 3 -> 4 2019-08-05 14:12:22 +03:00
Ildar Kamalov
0c46a70d9a + client: add prefix to the service icons 2019-08-05 14:12:22 +03:00
Ildar Kamalov
92cebd5b31 + client: handle blocked services 2019-08-05 14:12:22 +03:00
Simon Zolin
3c684d1f85 + openapi: add /blocked_services/* 2019-08-05 14:12:22 +03:00
Simon Zolin
87b379b140 + openapi: clients: add "blocked_services" field 2019-08-05 14:12:22 +03:00
Simon Zolin
15d07a40eb * refactor 2019-08-05 14:12:22 +03:00
Simon Zolin
dc2d8cf075 + /control/blocked_services/* API 2019-08-05 14:12:22 +03:00
Simon Zolin
e81a9c7d56 + dnsfilter: use global and per-client BlockedServices array 2019-08-05 14:12:22 +03:00
Simon Zolin
04a477c14a + clients: add BlockedServices field 2019-08-05 14:12:22 +03:00
Simon Zolin
8307a5a494 + config: store/load "blocked_services" per-client setting 2019-08-05 14:12:22 +03:00
Simon Zolin
01f5a13dd2 + doc: add "Services Filter" section 2019-08-05 14:12:22 +03:00
Andrey Meshkov
fdfc8d7683 fix typo2 2019-08-02 14:55:58 +03:00
Andrey Meshkov
b17cbcb38f fix typo 2019-08-02 14:55:00 +03:00
Andrey Meshkov
9389b087be Merge pull request #290 in DNS/adguard-home from feature/github_issue_template to master
* commit '0550a9a460aac7e5cd449513fed0567e558d2891':
  *(documentation): Github issue template
2019-08-02 14:48:25 +03:00
Andrey Meshkov
0550a9a460 *(documentation): Github issue template 2019-08-02 13:33:36 +03:00
Simon Zolin
4ae8c799ee Merge: + DNS: Add Rewrites section
Close #818

* commit 'e95aae5744ffd1de0809c95a8df50ea3f5f1af28':
  + client: handle DNS rewrites
  + openapi: add /rewrite/* methods
  + dnsforward: use Rewrites table
  + control: add /rewrite/* handlers
  + doc: add Rewrites section
  * dnsfilter: refactor: a simple approach to convert Reason to string
2019-07-31 18:55:01 +03:00
Ildar Kamalov
e95aae5744 + client: handle DNS rewrites 2019-07-31 14:29:37 +03:00
Ildar Kamalov
3cca61d599 Merge: + translations: add twosky integration
* commit '3b0f2e5563bfa3411b258b1b9c0b9d74f5598514':
  + translations: add twosky integration
2019-07-31 14:02:01 +03:00
Ildar Kamalov
3b0f2e5563 + translations: add twosky integration 2019-07-31 13:51:58 +03:00
Simon Zolin
70b8cf6ec8 + openapi: add /rewrite/* methods 2019-07-29 14:49:14 +03:00
Simon Zolin
1bb6638db7 + dnsforward: use Rewrites table 2019-07-29 11:48:24 +03:00
Simon Zolin
9857024c5d + control: add /rewrite/* handlers 2019-07-29 11:48:24 +03:00
Simon Zolin
0c2459b51b + doc: add Rewrites section 2019-07-29 11:37:47 +03:00
Simon Zolin
b66e370ffc * dnsfilter: refactor: a simple approach to convert Reason to string 2019-07-29 11:37:10 +03:00
Simon Zolin
a9fbb93f0f Merge: + Add "parental_block_host" and "safebrowsing_block_host" settings
#454

* commit 'fdf7ee2c08d4177d78fcdc20571bc7d2b61320ae':
  * refactor: don't set new configuration while running DNS server
  * refactor
  * dnsforward: parental control server can be an IP address, not just host name
  + dnsforward, config: add "parental_block_host" and "safebrowsing_block_host" settings
2019-07-24 19:35:46 +03:00
Andrey Meshkov
a742181956 Merge: +: git-cz config file
* commit '873108bf081c98eeb22fe00befd81f198aca7879':
  +: git-cz config file
2019-07-24 17:25:53 +03:00
Andrey Meshkov
873108bf08 +: git-cz config file
Added a git-cz config file because otherwise I cannot write proper
commit messages as I forget our rules all the time.
2019-07-24 17:26:21 +03:00
Andrey Meshkov
e9647e2962 Merge: refactor: 💡 optimizing GC
* commit '479675b6ccffbd9505a1edced40472438ea6a737':
  refactor: 💡 optimizing GC
2019-07-24 17:06:04 +03:00
Andrey Meshkov
e09ec5d38e Merge: * dnsfilter: use fastcache instead of gcache
* commit 'd9265aa9a8c21d97206b0e43a03b448f2c33a510':
  fix tests
  * dnsfilter: use fastcache instead of gcache
  + config: add cache size settings
2019-07-24 17:04:24 +03:00
Andrey Meshkov
479675b6cc refactor: 💡 optimizing GC
Setting debug.SetGCPercent makes golang free memory faster. This greatly
improves overall RSS usage. Otherwise, golang prefers not to free memory
at all:)
2019-07-24 17:00:05 +03:00
Simon Zolin
d9265aa9a8 fix tests 2019-07-23 20:01:50 +03:00
Simon Zolin
6f51df7d2e * dnsfilter: use fastcache instead of gcache 2019-07-23 17:14:13 +03:00
Simon Zolin
81303b5db7 + config: add cache size settings 2019-07-23 15:57:44 +03:00
Simon Zolin
fdf7ee2c08 * refactor: don't set new configuration while running DNS server 2019-07-22 12:52:27 +03:00
Simon Zolin
5a3de2a276 * refactor 2019-07-22 12:33:58 +03:00
Simon Zolin
4a05ab0057 * dnsforward: parental control server can be an IP address, not just host name 2019-07-22 12:33:45 +03:00
Simon Zolin
4134a8c30e + dnsforward, config: add "parental_block_host" and "safebrowsing_block_host" settings 2019-07-22 12:16:30 +03:00
Simon Zolin
c2dacd32d1 Merge: * use urlfilter v0.4.1
Close #840

* commit 'bb00a632382823d8c0a0d9f307788711ea50cb5f':
  * use urlfilter v0.4.1
2019-07-19 15:26:52 +03:00
Simon Zolin
bb00a63238 * use urlfilter v0.4.1 2019-07-19 15:20:42 +03:00
Simon Zolin
bd5162ada3 Merge: Refactoring: move global variables; move initialization of periodic tasks
Close #583

* commit 'b8444ff46aff5e45194c6cb61fdf4d3e7aa798fa':
  * minor
  * dnsforward: move initialization of periodic tasks to NewServer()
  * move "dnsctx" to "config"
  * move "dnsServer" to "config"
  * move "dhcpServer" to "config"
  * move "httpServer" to "config"
  * move "httpsServer" to "config"
  * move "pidFileName" to "config"
  * move "versionCheckJSON" to "config"
  * move "client", "transport" to "config"
  * move "controlLock" mutex to "config"
  * clients: move container object to "config"
2019-07-19 15:18:51 +03:00
Simon Zolin
b8444ff46a * minor 2019-07-19 12:18:16 +03:00
Simon Zolin
2bbd262968 * dnsforward: move initialization of periodic tasks to NewServer() 2019-07-19 12:18:16 +03:00
Simon Zolin
6701e9ce06 * move "dnsctx" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
af21a5f17b * move "dnsServer" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
001b4b981f * move "dhcpServer" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
5e309a7b3a * move "httpServer" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
2780ace63e * move "httpsServer" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
f79008d9d0 * move "pidFileName" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
d3ddfc81a6 * move "versionCheckJSON" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
c426ee0108 * move "client", "transport" to "config" 2019-07-19 12:18:16 +03:00
Simon Zolin
2682adca39 * move "controlLock" mutex to "config" 2019-07-17 19:29:45 +03:00
Simon Zolin
d51f43e27a * clients: move container object to "config"
Now the functions use parameter, not a global object.
2019-07-17 19:29:45 +03:00
Simon Zolin
1973901802 Merge: * dhcpd: check if subnet mask is correct
Close #887

* commit '79a5c920a40180b7291d94535e50017d98eb3a63':
  * dhcpd: check if subnet mask is correct
2019-07-17 12:45:45 +03:00
Simon Zolin
79a5c920a4 * dhcpd: check if subnet mask is correct 2019-07-17 11:55:21 +03:00
Simon Zolin
0fb42e5c71 Merge: - filters: fix crash after update
#878

* commit '1c5b6130480b7c8796c9861c94e9635b550582bc':
  - filters: fix crash after update
2019-07-16 15:35:54 +03:00
Simon Zolin
1c5b613048 - filters: fix crash after update 2019-07-16 15:29:36 +03:00
Simon Zolin
55a4536997 Merge: - filters: start DNS server after filters are updated
Close #886

* commit '1b45dc45fc4e610689afc4e618e45ed946f02646':
  - filters: start DNS server after filters are updated
2019-07-16 14:41:23 +03:00
Simon Zolin
1b45dc45fc - filters: start DNS server after filters are updated 2019-07-16 14:32:58 +03:00
Simon Zolin
87ccd192c3 Merge: - filters: windows: fix update procedure
Close #878

* commit '2c91de73af78a032c076dbad6dcdb85e22e82536':
  * minor
  - filters: start DNS server after filter has been removed
  - filters: windows: fix update procedure
2019-07-16 13:58:54 +03:00
Simon Zolin
2c91de73af * minor 2019-07-16 12:55:55 +03:00
Simon Zolin
94f3bf44d7 - filters: start DNS server after filter has been removed 2019-07-16 12:55:47 +03:00
Simon Zolin
27006f58c5 - filters: windows: fix update procedure
We couldn't write filter files on Windows due to
 "file is being used" error.
2019-07-16 12:55:18 +03:00
Simon Zolin
4326a2c945 Merge: - /filtering/remove_url: windows: remove filter file only after DNS server has been stopped
Close #878

* commit '375e410aa310c24ec0e95ee48ebd40675d5df1e7':
  - /filtering/remove_url: windows: remove filter file only after DNS server has been stopped
2019-07-15 18:36:08 +03:00
Simon Zolin
375e410aa3 - /filtering/remove_url: windows: remove filter file only after DNS server has been stopped
Otherwise, os.Remove() will return with an error "file is being used".
2019-07-15 18:23:58 +03:00
Simon Zolin
cc8633ed7d Merge: - dnsfilter: fix crash when global setting 'SafeSearch' is off
Close #880

* commit 'a79643f23e4bb45a912a71b4a973a027431a8720':
  + dnsfilter-test: override global safe-browsing setting with a per-client setting
  - dnsfilter: fix crash when global setting 'SafeSearch' is off
2019-07-15 18:22:58 +03:00
Simon Zolin
a79643f23e + dnsfilter-test: override global safe-browsing setting with a per-client setting 2019-07-15 14:03:22 +03:00
Simon Zolin
c81c79aad7 Merge: - don't load filter rules if filter is disabled
Close #879

* commit 'e2b518339fe6c14bb29008ad1638244e2f0fb3f8':
  - don't load filter rules if filter is disabled
2019-07-15 13:17:44 +03:00
Simon Zolin
e2b518339f - don't load filter rules if filter is disabled 2019-07-15 12:49:48 +03:00
Simon Zolin
57c510631e - dnsfilter: fix crash when global setting 'SafeSearch' is off
but per-client setting is on
2019-07-15 12:10:43 +03:00
Andrey Meshkov
d4bbc45a39 Added beta link for FreeBSD 2019-07-12 16:22:13 +03:00
Andrey Meshkov
9eb6da05ad Bump version to 0.97.0 and fix #798 2019-07-12 15:57:20 +03:00
Simon Zolin
3f796a5d05 Merge: - fix tests
* commit '0a1d7fd70732c306f39c777cbe60bb8bf1ab9da5':
  - fix tests
2019-07-09 11:35:49 +03:00
Simon Zolin
0a1d7fd707 - fix tests 2019-07-09 11:35:39 +03:00
Ildar Kamalov
26db906e54 Merge: + client: add link to the DNS filterting rules article
Closes #721

* commit '3a5f9a7ad35aa7f0f0dc5eac5dfcb9b9a3276fc0':
  + client: add link to the DNS filterting rules article
2019-07-08 18:05:02 +03:00
Ildar Kamalov
3a5f9a7ad3 + client: add link to the DNS filterting rules article 2019-07-08 17:36:32 +03:00
Ildar Kamalov
bcbfa43ea2 Merge: * client: remove /clients and /stats_top request from global requests
* commit '2520a62e2430dac1d9bf689c567b95d419a78339':
  * client: remove /clients and /stats_top request from global requests
2019-07-08 13:47:37 +03:00
Ildar Kamalov
2520a62e24 * client: remove /clients and /stats_top request from global requests 2019-07-08 12:49:03 +03:00
Simon Zolin
fce551dcaf Merge: - client: fix version line break
#815

* commit 'cf4616cbee3f835ed4db0875f1183c5dcac347f5':
  - client: fix version line break
2019-07-05 18:37:46 +03:00
Ildar Kamalov
cf4616cbee - client: fix version line break 2019-07-05 18:37:57 +03:00
Simon Zolin
f0c9ffcbeb Merge: - client: fix update now button and notification
#815

* commit '71c1157ef56fa456698e828b3d4ff992d62199ff':
  * client: remove version truncate for desktop
  - client: fix update now button and notification
2019-07-05 18:26:53 +03:00
Ildar Kamalov
71c1157ef5 * client: remove version truncate for desktop 2019-07-05 18:27:15 +03:00
Ildar Kamalov
2fe9819150 - client: fix update now button and notification 2019-07-05 18:21:46 +03:00
Simon Zolin
4af635e58a Merge: - dnsfilter: fix post-install error "filter file not found"
* commit 'b0cfd7228eaae0719f40d37f766c541c06bfb1b0':
  - dnsfilter: fix post-install error "filter file not found"
2019-07-05 17:53:43 +03:00
Simon Zolin
b0cfd7228e - dnsfilter: fix post-install error "filter file not found"
Right after installation we don't have the filter files downloaded.
While they are being downloaded, we replace them with an empty filter.
2019-07-05 17:35:40 +03:00
Simon Zolin
e03efbcdd1 Merge: + release.sh: add freebsd/amd64 distrib
Close #873

* commit '124d73bd3202efbed1e0774d79576f4e7a160fd9':
  + release.sh: add freebsd/amd64 distrib
2019-07-05 15:50:37 +03:00
Simon Zolin
2897bb983f Merge: Print DOH/DOT addresses if it's configured
Close #761

* commit '387783cf91acb8a78b9c9b22f5373187e4dfc16b':
  * client: remove /dns-query from string on client
  * client: fix description
  - client: fix page lang issue with Portuguese
  * client: show DNS-over-HTTPS and DNS-over-TLS addresses
  + client: add DNS privacy tab to setup guide
  + /status: "dns_addresses": add "tls://" or "https://" prefix
  * /status: "dns_addresses": add port if not 53
2019-07-05 15:49:55 +03:00
Ildar Kamalov
387783cf91 * client: remove /dns-query from string on client 2019-07-05 15:47:21 +03:00
Ildar Kamalov
d4bd53a824 * client: fix description 2019-07-05 15:47:21 +03:00
Ildar Kamalov
f1a6912092 - client: fix page lang issue with Portuguese 2019-07-05 15:47:21 +03:00
Ildar Kamalov
531ee20988 * client: show DNS-over-HTTPS and DNS-over-TLS addresses 2019-07-05 15:47:21 +03:00
Ildar Kamalov
5c7c9964b8 + client: add DNS privacy tab to setup guide 2019-07-05 15:47:21 +03:00
Simon Zolin
425f3c87d0 + /status: "dns_addresses": add "tls://" or "https://" prefix 2019-07-05 15:47:21 +03:00
Simon Zolin
ad7c5cb9dc * /status: "dns_addresses": add port if not 53 2019-07-05 15:47:21 +03:00
Simon Zolin
124d73bd32 + release.sh: add freebsd/amd64 distrib 2019-07-05 14:42:32 +03:00
Simon Zolin
1445940473 Merge: * use urlfilter v0.4.0
Close #866

* commit '134d9275bba7de7d1550412310bc275c52bb340e':
  * use urlfilter v0.4.0
2019-07-05 12:33:30 +03:00
Simon Zolin
df30248870 Merge: - freebsd: fix build
Close #870

* commit '98ff11e1c781a373768f01c54f6c7c29d8096d32':
  - freebsd: fix build
2019-07-04 15:12:38 +03:00
Simon Zolin
b419a1e3d8 Merge: * dns: fail on starting DNS server if upstream servers configuration is incorrect
* commit 'e2675e9a3bb54263d991ed4e9260d5acfedd63da':
  - client: fix link to dhcp settings page
  * dns: fail on starting DNS server if upstream servers configuration is incorrect
2019-07-04 14:57:35 +03:00
Simon Zolin
98ff11e1c7 - freebsd: fix build
Go's "syscall" package file for FreeBSD (incorrectly?) uses int64
 types in syscall.Rlimit struct.
2019-07-04 14:26:34 +03:00
Simon Zolin
134d9275bb * use urlfilter v0.4.0
Now we pass filtering rules to urlfilter as filer file names,
 rather than the list of rule strings.
(Note: user rules are still passed as the list of rule strings).

As a result, we don't store the contents of filter files in memory.
2019-07-04 14:10:01 +03:00
Ildar Kamalov
e2675e9a3b - client: fix link to dhcp settings page 2019-07-03 17:59:26 +03:00
Simon Zolin
dc43ad9910 * dns: fail on starting DNS server if upstream servers configuration is incorrect 2019-07-03 17:59:19 +03:00
Simon Zolin
ceac4cbdd5 Merge: - service stop: fix race
Close #799

* commit '131aa4c93ccd6e2603e8025dfd4d3693aa9dd561':
  - service stop: fix race
2019-07-02 14:45:21 +03:00
Simon Zolin
131aa4c93c - service stop: fix race
Service Stop handler sends SIGINT to the main thread,
 which begins the stops the app.
2019-07-02 12:56:23 +03:00
Ildar Kamalov
5abf0b5a53 Merge: - client: request tls status on app load
Closes #851

* commit '640620288892afad7b84cc3b25d96bab10cdb5d6':
  - client: fix version alignment
  - client: request tls status on app load
2019-07-02 09:40:49 +03:00
Ildar Kamalov
5cddde53c3 Merge: * client: allow ip address in filter
Closes #832

* commit 'e616d843bfbef044372c4968559f02b71f5d8210':
  * client: allow ip address in filter
2019-07-02 09:39:33 +03:00
Simon Zolin
1c9abd6107 Merge: + dhcpd, clients, dnsfilter: add more tests
#788

* commit '25da23497a19118a22b97d64749fa70337544116':
  + dnsfilter: more tests
  + dhcpd, clients: add more tests
2019-07-01 19:26:27 +03:00
Simon Zolin
8e3f05e538 Merge: * dnsfilter: fix tests: pass config object to NewForTest()
* commit '64f66cfb5d71e34d59977925fd9453a21fe2cd1a':
  * dnsfilter: fix tests: pass config object to NewForTest()
2019-07-01 19:24:53 +03:00
Simon Zolin
64f66cfb5d * dnsfilter: fix tests: pass config object to NewForTest() 2019-07-01 19:24:52 +03:00
Ildar Kamalov
e616d843bf * client: allow ip address in filter 2019-07-01 15:52:24 +03:00
Ildar Kamalov
6406202888 - client: fix version alignment 2019-07-01 15:07:29 +03:00
Ildar Kamalov
b3c2b3a21b - client: request tls status on app load 2019-07-01 15:04:07 +03:00
Simon Zolin
b45e8e80fb Merge: * auto-update: use backup directory format without version: "agh-backup"
Close #801

* commit '885b660808a848277f080c78dc7e6107afdbabb7':
  * auto-update: refactor test;  test getUpdateInfo()
  * auto-update: use backup directory format without version: "agh-backup"
2019-06-27 18:04:37 +03:00
Simon Zolin
885b660808 * auto-update: refactor test; test getUpdateInfo() 2019-06-27 15:23:48 +03:00
Simon Zolin
bdc9a0b906 * auto-update: use backup directory format without version: "agh-backup" 2019-06-27 15:23:16 +03:00
Simon Zolin
c631a6832f Merge: + clients: parse 'arp -a' output; periodically update info
Close #826

* commit 'db7efc24d381f6c8d88e14f485475e812ff5fb7b':
  + clients: parse 'arp -a' output;  periodically update info
2019-06-27 11:59:19 +03:00
Simon Zolin
db7efc24d3 + clients: parse 'arp -a' output; periodically update info
* prioritize a client source: etc/hosts > ARP > rDNS
2019-06-27 11:39:53 +03:00
Simon Zolin
b4b11406cf Merge: * /control/version.json: add "recheck_now" parameter
Close #815

* commit 'd2258cb66de32092f145f2803a7be3d7869970f2':
  * openapi.yaml: update /version.json
  + client: add button for check updates
  * /control/version.json: add "recheck_now" parameter
2019-06-27 11:23:29 +03:00
Simon Zolin
eb8c531ae1 Merge: * dnsfilter: use a single global context object
Close #807

* commit '42b76ada9d42f01aace4c6f47cb32f3d77d53a0b':
  rename dnsfContext -> dnsFilterContext
  * dnsfilter: use a single global context object
2019-06-27 11:22:57 +03:00
Simon Zolin
d1987e711d Merge: - dhcp: store lease data in database on each change rather than once on app stop
Close #852

* commit '0b3ba8224255247fa751a9922f83154e71a26c02':
  - dhcp: store lease data in database on each change rather than once on app stop
  - dhcp: fix race introduced by static lease add/remove from UI thread
2019-06-27 10:56:32 +03:00
Simon Zolin
e50b4fd185 Merge: - rDNS: don't try to resolve loopback IP addresses
Close #838

* commit '6a1edc45be51a16bc1e8b63bb1661a6e4196fe5a':
  - rDNS: don't try to resolve loopback IP addresses
2019-06-27 10:55:25 +03:00
Simon Zolin
d2258cb66d * openapi.yaml: update /version.json 2019-06-27 10:53:03 +03:00
Simon Zolin
42b76ada9d rename dnsfContext -> dnsFilterContext 2019-06-27 10:48:12 +03:00
Simon Zolin
25da23497a + dnsfilter: more tests 2019-06-26 18:13:09 +03:00
Simon Zolin
efaaeb58eb + dhcpd, clients: add more tests 2019-06-26 17:53:05 +03:00
Simon Zolin
0b3ba82242 - dhcp: store lease data in database on each change rather than once on app stop 2019-06-26 14:02:41 +03:00
Simon Zolin
eff23f3b62 - dhcp: fix race introduced by static lease add/remove from UI thread 2019-06-26 14:01:59 +03:00
Ildar Kamalov
0e9df33a40 + client: add button for check updates 2019-06-25 17:56:50 +03:00
Simon Zolin
6a1edc45be - rDNS: don't try to resolve loopback IP addresses 2019-06-25 16:14:52 +03:00
Simon Zolin
5d60bb05ab * /control/version.json: add "recheck_now" parameter 2019-06-25 16:06:55 +03:00
Simon Zolin
2307f55715 * dnsfilter: use a single global context object 2019-06-24 19:00:03 +03:00
Andrey Meshkov
f1e6a30931 Fix version/channel linking 2019-06-20 14:36:26 +03:00
Andrey Meshkov
4ddae72faf Fix Makefile -- VersionString and updateChannel 2019-06-20 14:18:29 +03:00
Andrey Meshkov
082354204b Fix #831
This commit fixes panic when customDialContext fails to resolve the host's address.
2019-06-18 16:18:13 +03:00
Simon Zolin
6187871e3b Merge: * move ./*.go files into ./home/ directory
* commit 'dc682763ff61874eb6043eaac5fa0eba17f7ddec':
  * move ./*.go files into ./home/ directory
2019-06-10 12:07:57 +03:00
Simon Zolin
dc682763ff * move ./*.go files into ./home/ directory 2019-06-10 11:51:53 +03:00
Andrey Meshkov
9fe34818e3 Fix #770 - dnsproxy v0.15.0
* commit '9a77bb3a0acddf88f32991e13891270deea5725c':
  go mod tidy
  * dnsproxy v0.15.0
2019-06-07 20:13:59 +03:00
Andrey Meshkov
9a77bb3a0a go mod tidy 2019-06-07 20:10:07 +03:00
Simon Zolin
86890a8609 * dnsproxy v0.15.0 2019-06-07 19:59:11 +03:00
Simon Zolin
1fd0f78612 Merge: - clients: fix race introduced by commit 07db927; update tech doc
Close #727

* commit '1fcb69d3a913dec9b53f148acab45b1f621faa24':
  - clients: fix race introduced by commit 07db927; update tech doc
2019-06-07 19:11:28 +03:00
Simon Zolin
1fcb69d3a9 - clients: fix race introduced by commit 07db927; update tech doc 2019-06-07 11:37:55 +03:00
Andrey Meshkov
07db927246 Fix #727 - use default parental sensitivity when it's not set 2019-06-06 22:42:17 +03:00
Andrey Meshkov
f9807e4011 Fix #806 2019-06-06 21:06:19 +03:00
Andrey Meshkov
5647bc1fc9 Fix #727 - apply client settings properly 2019-06-06 21:04:17 +03:00
Andrey Meshkov
0f7235f217 fix string id 2019-06-06 17:48:46 +03:00
Andrey Meshkov
db67fb6c6a rename client settings 2019-06-06 17:45:24 +03:00
Simon Zolin
087d2f68c2 Merge: - client: fix versions check
Close #428

* commit '02fa39226c442a23e9cba9816382f55c2b276589':
  * client: pull locales
  - client: fix versions check
2019-06-06 17:27:38 +03:00
Ildar Kamalov
02fa39226c * client: pull locales 2019-06-06 17:25:50 +03:00
Andrey Meshkov
edfa104710 add urlfilter to the list of software 2019-06-06 16:18:12 +03:00
Andrey Meshkov
7a124213e5 Merge branch 'master' of ssh://bit.adguard.com:7999/dns/adguard-dns 2019-06-06 16:00:42 +03:00
Andrey Meshkov
0a2a7ca630 Fix #566 -- added comparison table 2019-06-06 16:00:35 +03:00
Ildar Kamalov
1f164c7005 - client: fix versions check 2019-06-06 15:54:19 +03:00
Simon Zolin
44f224d69e Merge: Auto-update: improve algorithm, fix bugs
Close #428

* commit '22469bb83bcf902804191d4896c2224e5d5b9f75':
  * control_update_test.go: "+build ignore"
  - client: check version on update before page reload
  * auto-update: remove the update directory after successful update
  + auto-update: copy supporting files (README, etc.)
  * release.sh: add AdGuardHome/ directory to .tar.gz output file
  * auto-update: zipFileUnpack() returns list of unpacked files
  * auto-update: use native code to unpack .tar.gz
  * auto-update: use 'selfupdate_min_version' from version.json
  - control: outgoing HTTP requests didn't work if target IP is IPv6
2019-06-06 14:05:43 +03:00
Simon Zolin
22469bb83b * control_update_test.go: "+build ignore" 2019-06-06 12:20:26 +03:00
Ildar Kamalov
10a0873bc8 - client: check version on update before page reload 2019-06-06 11:41:53 +03:00
Simon Zolin
a165410c9f * auto-update: remove the update directory after successful update 2019-06-06 11:41:53 +03:00
Simon Zolin
ec5e2be31f + auto-update: copy supporting files (README, etc.) 2019-06-06 11:41:53 +03:00
Simon Zolin
6d3099acd3 * release.sh: add AdGuardHome/ directory to .tar.gz output file 2019-06-06 11:41:53 +03:00
Simon Zolin
66c670c6ff * auto-update: zipFileUnpack() returns list of unpacked files 2019-06-06 11:41:14 +03:00
Simon Zolin
c2a31f9503 * auto-update: use native code to unpack .tar.gz 2019-06-06 11:41:14 +03:00
Simon Zolin
466f553bbe * auto-update: use 'selfupdate_min_version' from version.json 2019-06-06 11:41:14 +03:00
Simon Zolin
ddb1bc0fee - control: outgoing HTTP requests didn't work if target IP is IPv6 2019-06-06 11:41:14 +03:00
Andrey Meshkov
a36630e5a8 Merge: Fix #773 - preparing the new update channel
* commit '395833056097fa44c1221da33319cd64e4a5ca62':
  Fix #773 - preparing the new update channel
2019-06-06 11:23:55 +03:00
Andrey Meshkov
3958330560 Fix #773 - preparing the new update channel 2019-06-06 03:00:15 +03:00
Ildar Kamalov
86ba6d4332 Merge pull request in DNS/adguard-dns from fix/793 to master
Closes #793

* commit 'b2364e465f7c7b19ad455b07864ddaf2848e6664':
  * client: reload list on opening Clients settings
2019-06-05 16:06:54 +03:00
Ildar Kamalov
b2364e465f * client: reload list on opening Clients settings 2019-06-05 15:49:01 +03:00
Andrey Meshkov
a3b8d4d923 Fix #706 -- rDNS for DOH/DOT clients 2019-06-04 20:38:53 +03:00
Andrey Meshkov
3454bf9243 Merge branch 'master' of ssh://bit.adguard.com:7999/dns/adguard-dns 2019-06-04 19:58:17 +03:00
Andrey Meshkov
64a4443d0c Fix #706 - logging for resolveRDNS 2019-06-04 19:58:13 +03:00
Simon Zolin
d24b78db0e Merge: + dns: resolve hosts via rDNS for the top clients after the server has been started
Close #706

* commit 'f7150e6a19bfc5643fef4106bd068f6ba099f8e2':
  + dns: resolve hosts via rDNS for the top clients after the server has been started
2019-06-04 18:59:14 +03:00
Simon Zolin
f7150e6a19 + dns: resolve hosts via rDNS for the top clients after the server has been started 2019-06-04 18:12:45 +03:00
Andrey Meshkov
85046abb15 Merge branch 'master' of ssh://bit.adguard.com:7999/dns/adguard-dns 2019-06-04 16:30:59 +03:00
Andrey Meshkov
454e26db7f Update ports in docker files 2019-06-04 16:30:55 +03:00
Andrey Meshkov
b74438bf83 Merge pull request 235, Fix #778
* commit '7d40d3bfeaa2bea83ca50b41550b16907e447a47':
  + docker: use --no-check-update
2019-06-04 16:28:17 +03:00
Simon Zolin
7d40d3bfea + docker: use --no-check-update 2019-06-04 16:06:00 +03:00
Simon Zolin
6261fb79ab Merge: fix docker build
Close #789

* commit '27bffef9400615f502f4799fb318254b585fad99':
  Fix #789
2019-06-04 11:34:16 +03:00
Eugene Zbiranik
27bffef940 Fix #789 2019-06-04 11:03:13 +03:00
Simon Zolin
450e2ac549 Merge: * minor API changes
Close #785

* commit '7f5ac19b592c2a63e52a5e5319e9e8eb687c7410':
  * client: use JSON for filtering/remove_url
  * /remove_url: use JSON input data format
  - openapi: correct format
  - openapi: fix /add_url
2019-06-03 19:39:40 +03:00
Simon Zolin
6ac466e430 Merge: + client: split settings page into several pages
Close #726

* commit 'f7d88f6976ae8328bc47c0df4686ae6a38ed7bb0':
  * client: check initial access settings
  * client: remove unused addErrorToast method
  * client: move access settings to DNS settings page
  + client: split settings page into several pages
2019-06-03 19:38:21 +03:00
Ildar Kamalov
f7d88f6976 * client: check initial access settings 2019-06-03 16:39:02 +03:00
Ildar Kamalov
7f5ac19b59 * client: use JSON for filtering/remove_url 2019-06-03 16:33:15 +03:00
Ildar Kamalov
54f6710b8f * client: remove unused addErrorToast method 2019-06-03 16:18:49 +03:00
Ildar Kamalov
757bb7285a * client: move access settings to DNS settings page 2019-06-03 16:08:50 +03:00
Ildar Kamalov
af041bcbd7 Merge pull request in DNS/adguard-dns from fix/702 to master
* commit 'df9864ec00fe9b4c7f4912a6122d1308f06fa844':
  * client: replace favicon.ico with favicon.png
2019-06-03 15:47:42 +03:00
Ildar Kamalov
cf53653cfa + client: split settings page into several pages 2019-06-03 15:44:29 +03:00
Simon Zolin
1d09ff0562 Merge: + dnsforward: add access settings for blocking DNS requests
Close #728

* commit 'e4532a27cd2a6f92aaf724fddbffa00fcecb064c':
  - openapi: correct format
  + client: handle access settings
  * go.mod: update dnsproxy
  + control: /access/list, /access/set handlers
  + dnsforward: add access settings for blocking DNS requests
2019-06-03 15:04:52 +03:00
Simon Zolin
c93cb43db8 * /remove_url: use JSON input data format 2019-06-03 12:05:08 +03:00
Simon Zolin
276d87a218 - openapi: correct format 2019-06-03 12:05:08 +03:00
Simon Zolin
fcf609ac1e - openapi: fix /add_url 2019-06-03 12:05:08 +03:00
Simon Zolin
e4532a27cd - openapi: correct format 2019-06-03 11:21:57 +03:00
Simon Zolin
302a11a6a3 Merge: - fix tests and linter issues
* commit 'b8d9ca942c23b37133dbb894d42a8b3f310a86a1':
  - app: fix crash on starting DNS server after installation
  - fix tests and linter issues
2019-05-31 18:49:07 +03:00
Simon Zolin
b8d9ca942c - app: fix crash on starting DNS server after installation 2019-05-31 16:39:18 +03:00
Ildar Kamalov
df9864ec00 * client: replace favicon.ico with favicon.png 2019-05-31 16:36:48 +03:00
Simon Zolin
3baa6919dc - fix tests and linter issues 2019-05-31 12:27:13 +03:00
Ildar Kamalov
02db488b30 + client: handle access settings 2019-05-30 18:45:56 +03:00
Simon Zolin
821ad3edd9 * go.mod: update dnsproxy 2019-05-30 18:22:29 +03:00
Simon Zolin
d18c222b1a + control: /access/list, /access/set handlers 2019-05-30 18:21:56 +03:00
Simon Zolin
36ffcf7d22 + dnsforward: add access settings for blocking DNS requests
Block by client IP or target domain name.
2019-05-30 18:21:36 +03:00
Simon Zolin
147344afa3 Merge: - dns: fix crash (rDNS)
* commit '1abd9da27d7ced46a92e2b0cb85224a1d7d9025b':
  - dns: fix crash (rDNS)
2019-05-29 12:50:04 +03:00
Simon Zolin
1abd9da27d - dns: fix crash (rDNS) 2019-05-28 19:51:49 +03:00
Simon Zolin
d9e70f5244 Merge: + DHCP: Support statically configured leases
Close #687

* commit 'b1fbd7c40c640eef575e6c2babc7eab26a525cf8':
  * openapi: add new dhcp methods
  * client: fix page scrolling on adding/deleting leases
  + client: handle static leases form
  + client: add table to show static leases
  + doc: DHCP static leases
  * dhcpd: refactor: use separate objects for ServerConfig and RWMutex
  + dhcp: /dhcp/status: return static leases
  * dhcpd: minor improvements
  * control: refactor: move DHCP lease -> json convertor to a separate function
  + dhcp: /dhcp/add_static_lease, /dhcp/remove_static_lease: control static lease table
  + helpers: parseIPv4()
  * control: use new DHCP functions: CheckConfig, Init, Start
  * control,dhcp: use dhcpServerConfigJSON struct
  + dhcpd: CheckConfig()
  * dhcpd: move code from Start() to Init()
2019-05-28 19:34:42 +03:00
Simon Zolin
a1ceb83da0 Merge: + clients: find DNS client's hostname by IP using rDNS
Close #706

* commit 'a12f01793ff97e0ea53bc6f751bee758d1df6bb2':
  + clients: find DNS client's hostname by IP using rDNS
2019-05-28 19:33:30 +03:00
Simon Zolin
a12f01793f + clients: find DNS client's hostname by IP using rDNS 2019-05-28 19:07:57 +03:00
Simon Zolin
b1fbd7c40c * openapi: add new dhcp methods 2019-05-28 19:01:24 +03:00
Ildar Kamalov
2976726f99 * client: fix page scrolling on adding/deleting leases 2019-05-28 19:01:24 +03:00
Ildar Kamalov
6f2503a09f + client: handle static leases form 2019-05-28 19:01:24 +03:00
Ildar Kamalov
a8384c004e + client: add table to show static leases 2019-05-28 19:01:24 +03:00
Simon Zolin
49b91b4fc9 + doc: DHCP static leases 2019-05-28 19:01:24 +03:00
Simon Zolin
fa47fa3f9c * dhcpd: refactor: use separate objects for ServerConfig and RWMutex 2019-05-28 19:01:24 +03:00
Simon Zolin
763b986955 + dhcp: /dhcp/status: return static leases 2019-05-28 18:59:15 +03:00
Simon Zolin
342699d933 * dhcpd: minor improvements 2019-05-28 18:59:15 +03:00
Simon Zolin
fd593f5282 * control: refactor: move DHCP lease -> json convertor to a separate function 2019-05-28 18:59:15 +03:00
Simon Zolin
725aeeb910 + dhcp: /dhcp/add_static_lease, /dhcp/remove_static_lease: control static lease table 2019-05-28 18:59:15 +03:00
Simon Zolin
564a41d598 + helpers: parseIPv4() 2019-05-28 18:59:15 +03:00
Simon Zolin
c3204664c3 * control: use new DHCP functions: CheckConfig, Init, Start 2019-05-28 18:59:15 +03:00
Simon Zolin
626c1ae753 * control,dhcp: use dhcpServerConfigJSON struct 2019-05-28 18:59:15 +03:00
Simon Zolin
cc366495d3 + dhcpd: CheckConfig() 2019-05-28 18:59:15 +03:00
Simon Zolin
0d405c0af8 * dhcpd: move code from Start() to Init() 2019-05-28 18:59:15 +03:00
Simon Zolin
c038e4cf14 Merge: + Per-client settings
Close #727

* commit 'a83bc5eeeb4107f2157443b7b40636036fe2a7cc':
  * client: add source column
  * client: remove redundant table formatting for runtime clients table
  * client: show MAC address as default
  + client: add runtime clients table
  * client: add icons for table buttons
  * client: remove unused api method
  * client: confirm before deleting
  * client: remove table column min-width
  * client: fix no data text
  * client: fix sort helper
  + client: handle per-client settings
  - openapi.yaml: fix HTTP methods
  + openapi.yaml: add /clients handlers
  + dnsfilter: use callback function for applying per-client settings
  + dhcp: FindIPbyMAC()
  + dns: use per-client filtering settings
  + clients: config: save/restore clients info array
  + clients API
  + doc: clients
2019-05-28 18:52:51 +03:00
Ildar Kamalov
a83bc5eeeb * client: add source column 2019-05-28 18:44:27 +03:00
Ildar Kamalov
702db84e39 * client: remove redundant table formatting for runtime clients table 2019-05-28 18:44:27 +03:00
Ildar Kamalov
9cc824d852 * client: show MAC address as default 2019-05-28 18:44:27 +03:00
Ildar Kamalov
8a8c7329f7 + client: add runtime clients table 2019-05-28 18:44:27 +03:00
Ildar Kamalov
cbef338592 * client: add icons for table buttons 2019-05-28 18:44:27 +03:00
Ildar Kamalov
bd2c4269db * client: remove unused api method 2019-05-28 18:44:27 +03:00
Ildar Kamalov
f40141bbbc * client: confirm before deleting 2019-05-28 18:44:27 +03:00
Ildar Kamalov
c7b5830336 * client: remove table column min-width 2019-05-28 18:44:27 +03:00
Ildar Kamalov
bb34381a0d * client: fix no data text 2019-05-28 18:44:27 +03:00
Ildar Kamalov
68a4cc597f * client: fix sort helper 2019-05-28 18:44:27 +03:00
Ildar Kamalov
22d3c38df2 + client: handle per-client settings 2019-05-28 18:44:27 +03:00
Simon Zolin
22c7efd2d1 - openapi.yaml: fix HTTP methods 2019-05-28 18:44:27 +03:00
Simon Zolin
eb159e6997 + openapi.yaml: add /clients handlers 2019-05-28 18:44:27 +03:00
Simon Zolin
8bf76c331d + dnsfilter: use callback function for applying per-client settings 2019-05-28 18:44:27 +03:00
Simon Zolin
4bb7b654ab + dhcp: FindIPbyMAC() 2019-05-28 18:44:27 +03:00
Simon Zolin
3f89335ed2 + dns: use per-client filtering settings 2019-05-28 18:44:27 +03:00
Simon Zolin
8f7aff93d7 + clients: config: save/restore clients info array 2019-05-28 18:44:27 +03:00
Simon Zolin
5fb7e44e79 + clients API
* /clients handler: new format
+ /clients/add handler
+ /clients/delete handler
+ /clients/update handler
2019-05-28 18:44:27 +03:00
Simon Zolin
6a7b1aba8b + doc: clients 2019-05-28 18:44:27 +03:00
Simon Zolin
218f51092c Merge: + app: disable new version check and auto-update by command line switch
Close #778

* commit '9f75146eaba9d9a3ce085c884d7f18a2c628dc50':
  * client: check for empty versions response
  * docker: use --no-check-update
  * openapi: update /version.json description
  + app: disable new version check and auto-update by command line switch
2019-05-28 18:18:40 +03:00
Ildar Kamalov
9f75146eab * client: check for empty versions response 2019-05-28 15:22:48 +03:00
Simon Zolin
6ab8aa4da1 * docker: use --no-check-update 2019-05-28 11:42:50 +03:00
Simon Zolin
386886cec2 Merge: * control: 🚑 Corrects typo in parental control API error message
Close #781

* commit '517ebc0251d6bfe43b7b4d31c7c4e7e91ea928fa':
  🚑 Corrects typo in parental control API error message
2019-05-28 11:42:12 +03:00
Simon Zolin
5b29cae133 * openapi: update /version.json description 2019-05-28 11:41:36 +03:00
Simon Zolin
4df8868787 Merge: * dnsfilter: parental/safebrowsing: add setting to switch between HTTP and HTTPS #646
* commit 'f23507a5546229d8ce8f69d56667cd5212f026d3':
  * dnsfilter: parental/safebrowsing: add setting to switch between HTTP and HTTPS
2019-05-28 11:31:51 +03:00
Franck Nijhof
517ebc0251 🚑 Corrects typo in parental control API error message 2019-05-27 22:51:51 +02:00
Simon Zolin
f25639f1fc + app: disable new version check and auto-update by command line switch 2019-05-27 18:48:33 +03:00
Simon Zolin
f23507a554 * dnsfilter: parental/safebrowsing: add setting to switch between HTTP and HTTPS 2019-05-27 18:11:05 +03:00
Simon Zolin
b9df476c5d Merge: dnsforward: support IPv6
Close #735

* commit 'e2579c72bdcafed41d5be1250fb38aeda0a8184e':
  * dnsfilter: fix tests
  + dnsforward: support IPv6 (AAAA response)
  * dnsfilter: return the correct IP address (host rules)
2019-05-27 12:35:31 +03:00
Simon Zolin
e2579c72bd * dnsfilter: fix tests 2019-05-24 18:08:08 +03:00
Simon Zolin
ac8f703407 + dnsforward: support IPv6 (AAAA response)
If question type is AAAA:
 Before this patch we responded with NXDOMAIN.
 Now we send an empty response if host rule is IPv4;
 or we send an AAAA answer if host rule is IPv6.

+ block ipv6 if rule is "0.0.0.0 blockdomain"
2019-05-24 18:08:08 +03:00
Simon Zolin
9ad4bba9ab * dnsfilter: return the correct IP address (host rules) 2019-05-24 18:08:08 +03:00
Simon Zolin
452c930dd0 Merge: * dnsfilter: use 'https' for safe-browsing and parental control
Close #646

* commit '00e1b6ca089705e7fdb4764133058e04111e36df':
  * dnsfilter: use 'https' for safe-browsing and parental control
2019-05-24 18:03:00 +03:00
Simon Zolin
fdd0f594fb Merge: - control: allow requests to "/favicon.ico" while we are in install mode
Close #766

* commit 'dece393d6acfa21f588505e494eb1225adc8376a':
  - control: allow requests to "/favicon.ico" while we are in install mode
2019-05-24 18:02:07 +03:00
Simon Zolin
00e1b6ca08 * dnsfilter: use 'https' for safe-browsing and parental control 2019-05-23 17:26:50 +03:00
Simon Zolin
dece393d6a - control: allow requests to "/favicon.ico" while we are in install mode 2019-05-23 16:28:20 +03:00
Simon Zolin
aa2d942783 Merge: Update by command from UI
Close #428

* commit '70e329956776cc381fdb28805375d5b2f0e22dbf':
  * openapi: update
  * client: add link to the update error
  * client: add update timeout
  * client: add error message if update failed
  + client: handle update
  * go linter
  * control: /version.json: use new JSON format
  + set config.runningAsService
  * app: --help: more pretty help info
  + app: add --check-config command-line argument
  * app: optimize config file reading
  + /control/update handler
  * control: don't use custom resolver for tests
  + doc: Update algorithm
  - control: fix race in /control/version.json handler
2019-05-20 13:38:23 +03:00
Simon Zolin
e3ee7a0c3e Merge: dnsfilter: use urlfilter package #714
* commit '096a95998749b673bc9be638bc9c8f6f0d13be41':
  * dnsforward: use new dnsfilter interface
  * dnsfilter: adapt tests to new interface
  * dnsfilter: use urlfilter package
  * dnsfilter: remove code for filtering rules
  * dns: rename dnsfilter.Filter.Rule -> dnsfilter.Filter.Data
  * dnsforward: use separate ServerConfig object
  * use urlfilter
2019-05-20 11:00:45 +03:00
Simon Zolin
70e3299567 * openapi: update 2019-05-20 10:57:07 +03:00
Ildar Kamalov
967517316f * client: add link to the update error 2019-05-17 18:33:34 +03:00
Ildar Kamalov
24f582d36d * client: add update timeout 2019-05-17 18:33:34 +03:00
Ildar Kamalov
9cffe865ec * client: add error message if update failed 2019-05-17 18:33:34 +03:00
Ildar Kamalov
cb3f7f2834 + client: handle update 2019-05-17 18:33:34 +03:00
Simon Zolin
096a959987 * dnsforward: use new dnsfilter interface 2019-05-17 18:22:57 +03:00
Simon Zolin
5ec747b30b * dnsfilter: adapt tests to new interface 2019-05-17 18:22:57 +03:00
Simon Zolin
829415da5b * dnsfilter: use urlfilter package
+ new config setting 'filtering_temp_filename'

* remove AddRules(), modify New()
2019-05-17 18:22:57 +03:00
Simon Zolin
3396d68019 * dnsfilter: remove code for filtering rules 2019-05-17 18:22:57 +03:00
Simon Zolin
bd68bf2e25 * dns: rename dnsfilter.Filter.Rule -> dnsfilter.Filter.Data 2019-05-17 18:22:57 +03:00
Simon Zolin
9644f79a03 * dnsforward: use separate ServerConfig object 2019-05-17 18:22:57 +03:00
Simon Zolin
36e273dfd5 * use urlfilter 2019-05-17 18:22:57 +03:00
Simon Zolin
068072bc5a * go linter 2019-05-17 15:39:56 +03:00
Simon Zolin
b72ca4d127 * control: /version.json: use new JSON format 2019-05-17 15:37:38 +03:00
Simon Zolin
28440fc3ac + set config.runningAsService 2019-05-17 15:37:38 +03:00
Simon Zolin
6d14ec18ac * app: --help: more pretty help info 2019-05-17 15:37:38 +03:00
Simon Zolin
5fd35254a8 + app: add --check-config command-line argument 2019-05-17 15:37:38 +03:00
Simon Zolin
3ee8051e97 * app: optimize config file reading
* read config file just once (even when upgrading)
* don't call os.Stat()
2019-05-17 15:37:38 +03:00
Simon Zolin
2dd6ea5161 + /control/update handler 2019-05-17 15:37:38 +03:00
Simon Zolin
788e91a51e * control: don't use custom resolver for tests 2019-05-17 15:34:55 +03:00
Simon Zolin
d4fcef8d04 + doc: Update algorithm 2019-05-17 15:34:55 +03:00
Simon Zolin
392c7b6ee1 - control: fix race in /control/version.json handler 2019-05-17 10:20:41 +03:00
Simon Zolin
7bb40bca0f Merge: dns query log: robust file flushing mechanism #708
* commit 'd5f6dd1a46446ebb440811691a6ee8ce2443320d':
  - dns query log: robust file flushing mechanism
  * improve logging
2019-05-15 14:08:01 +03:00
Simon Zolin
f20cb65189 Merge: + dnsfilter: cache IP addresses of safebrowsing and parental control servers
Close #745

* commit 'd918e5b418de232d95ba1e3d642dca00664f0304':
  use maxDialCacheSize constant
  rename functions and container
  + dnsfilter: cache IP addresses of safebrowsing and parental control servers
2019-05-15 14:01:01 +03:00
Simon Zolin
d5f6dd1a46 - dns query log: robust file flushing mechanism
Before this patch we could exit the process without waiting for
 file writing task to complete.
As a result a file could become corrupted or a large chunk of data
 could be missing.

Now the main thread either waits until file writing task completes
 or it writes log buffer to file itself.
2019-05-15 13:12:03 +03:00
Simon Zolin
0f28a989e9 * improve logging 2019-05-15 13:12:03 +03:00
Simon Zolin
d918e5b418 use maxDialCacheSize constant 2019-05-15 12:03:20 +03:00
Simon Zolin
3a0f608402 Merge: dnsforward, config: add unspecified IP blocking option
Close #742, #743

* commit 'cd2dd00da300c24a88a51082ee9622a332a5b72b':
  * dnsforward_test: add test for null filter
  * dnsforward, config: add unspecified IP blocking option
2019-05-15 11:58:40 +03:00
Alexander Turcic
cd2dd00da3 * dnsforward_test: add test for null filter 2019-05-14 16:53:09 +03:00
Alexander Turcic
07ffcbec3d * dnsforward, config: add unspecified IP blocking option
* dnsforward: prioritize host files over null filter

* dnsforward, config: adjust setting variable to blocking_mode

* dnsforward: use net.IPv4zero for null IP
2019-05-14 16:53:06 +03:00
Simon Zolin
b3461d37ca rename functions and container 2019-05-13 14:47:55 +03:00
Simon Zolin
2178546e7b Merge: docker: Run as non-root user
Close #720

* commit '68f9ec70fb0f8ff2a73bf382bc15257c367b7967':
  Optimize Docker image layers; comment out runtime user; add sample docker-compose.yml
  Run as non-root user
2019-05-13 14:42:50 +03:00
Simon Zolin
24ae61de3e + dnsfilter: cache IP addresses of safebrowsing and parental control servers 2019-05-13 14:16:07 +03:00
Simon Zolin
68f9ec70fb Merge branch 'docker-improvements' of git://github.com/javabean/AdGuardHome into javabean-docker-improvements 2019-05-13 11:12:21 +03:00
Cédrik LIME
17aa46c4d2 Optimize Docker image layers; comment out runtime user; add sample docker-compose.yml 2019-05-08 21:17:14 +02:00
Ildar Kamalov
a45f0c519e Merge pull request #209 in DNS/adguard-dns from feature/734 to master
* commit '6ac9509d64e82e48bc22ccd23ac3a25776d05565':
  + client: Add a link to the list of known DNS providers to Upstream DNS settings
2019-05-06 09:35:51 +03:00
Ildar Kamalov
2cb2b3585f Merge pull request #208 in DNS/adguard-dns from fix/729 to master
* commit 'd24f208f98c08155282eb3061fd28e2e149e296b':
  - client: fixed values for settings validation
2019-05-06 09:35:42 +03:00
Ildar Kamalov
d24f208f98 - client: fixed values for settings validation
Closes #729
2019-04-28 11:43:15 +03:00
Ildar Kamalov
6ac9509d64 + client: Add a link to the list of known DNS providers to Upstream DNS settings
Closes #734
2019-04-28 11:18:56 +03:00
Simon Zolin
7d2df26335 Merge: Bump version to v0.95-hotfix
* commit 'ae403fb13752df1fcdf33839d0747e44722382db':
  Bump version to v0.95-hotfix
2019-04-24 14:39:52 +03:00
Simon Zolin
ae403fb137 Bump version to v0.95-hotfix 2019-04-24 14:38:00 +03:00
Simon Zolin
e1bb89c393 Merge: dnsfilter: prevent recursion when both parental control and safebrowsing are enabled
Close #732

* commit 'c4e67690f4fcceb055cbea73610b5974855db96f':
  * dnsfilter: don't use global variable for custom resolver function
  - dnsfilter: prevent recursion when both parental control and safebrowsing are enabled
2019-04-24 12:52:16 +03:00
Simon Zolin
c4e67690f4 * dnsfilter: don't use global variable for custom resolver function 2019-04-24 12:49:12 +03:00
Simon Zolin
f6023b395e - dnsfilter: prevent recursion when both parental control and safebrowsing are enabled 2019-04-24 12:38:05 +03:00
Cédrik LIME
58868b75af Run as non-root user 2019-04-17 20:48:56 +02:00
177 changed files with 12428 additions and 5015 deletions

47
.github/ISSUE_TEMPLATE/Bug_report.md vendored Normal file
View File

@@ -0,0 +1,47 @@
---
name: Bug report
about: Create a bug report to help us improve AdGuard Home
---
<!-- As an open-source project with a dedicated but small maintainer team, it can sometimes take a long time for issues to be addressed so please be patient and we will get back to you as soon as we can.
-->
### Prerequisites
Please answer the following questions for yourself before submitting an issue. **YOU MAY DELETE THE PREREQUISITES SECTION.**
- [ ] I am running the latest version
- [ ] I checked the documentation and found no answer
- [ ] I checked to make sure that this issue has not already been filed
### Issue Details
<!--- Please include all relevant details about the environment you experienced the bug in -->
* **Version of AdGuard Home server:**
* <!-- (e.g. v1.0) -->
* **How did you setup DNS configuration:**
* <!-- (System/Router/IoT) -->
* **If it's a router or IoT, please write device model:**
* <!-- (e.g. Raspberry Pi 3 Model B) -->
* **Operating system and version:**
* <!-- (e.g. Ubuntu 18.04.1) -->
### Expected Behavior
<!-- A clear and concise description of what you expected to happen. -->
### Actual Behavior
<!-- A clear and concise description of what actually happened. -->
### Screenshots
<!-- If applicable, add screenshots to help explain your problem. -->
<details><summary>Screenshot:</summary>
<!--- drag and drop, upload or paste your screenshot to this area-->
</details>
### Additional Information
<!-- Add any other context about the problem here. -->

View File

@@ -0,0 +1,28 @@
---
name: Feature request
about: Suggest an idea for AdGuard Home
---
<!-- As an open-source project with a dedicated but small maintainer team, it can sometimes take a long time for issues to be addressed so please be patient and we will get back to you as soon as we can.
-->
### Prerequisites
Please answer the following questions for yourself before submitting an issue. **YOU MAY DELETE THE PREREQUISITES SECTION.**
- [ ] I am running the latest version
- [ ] I checked the documentation and found no answer
- [ ] I checked to make sure that this issue has not already been filed
### Problem Description
<!-- Is your feature request related to a problem? Please add a clear and concise description of what the problem is. -->
### Proposed Solution
<!-- Describe the solution you'd like in a clear and concise manner -->
### Alternatives Considered
<!-- A clear and concise description of any alternative solutions or features you've considered. -->
### Additional Information
<!-- Add any other context about the problem here. -->

19
.github/stale.yml vendored Normal file
View File

@@ -0,0 +1,19 @@
# Number of days of inactivity before an issue becomes stale
daysUntilStale: 60
# Number of days of inactivity before a stale issue is closed
daysUntilClose: 7
# Issues with these labels will never be considered stale
exemptLabels:
- 'bug'
- 'enhancement'
- 'feature request'
- 'localization'
# Label to use when marking an issue as stale
staleLabel: 'wontfix'
# Comment to post when marking an issue as stale. Set to `false` to disable
markComment: >
This issue has been automatically marked as stale because it has not had
recent activity. It will be closed if no further activity occurs. Thank you
for your contributions.
# Comment to post when closing a stale issue. Set to `false` to disable
closeComment: false

2
.gitignore vendored
View File

@@ -11,8 +11,6 @@
/client/node_modules/
/querylog.json
/querylog.json.1
/scripts/translations/node_modules
/scripts/translations/oneskyapp.json
/a_main-packr.go
# Test output

View File

@@ -13,6 +13,7 @@ run:
skip-files:
- ".*generated.*"
- dnsfilter/rule_to_regexp.go
- ".*_test.go"
# all available settings of specific linters

View File

@@ -33,6 +33,9 @@ script:
after_success:
- bash <(curl -s https://codecov.io/bash)
notifications:
slack: performix:yXTihlSzsLFSZiqbXMNzvTSX
matrix:
include:
# Release build configuration

20
.twosky.json Normal file
View File

@@ -0,0 +1,20 @@
[
{
"project_id": "home",
"base_locale": "en",
"localizable_files": "client/src/__locales/en.json",
"languages": {
"en": "English",
"es": "Español",
"fr": "Français",
"pt-br": "Portuguese (BR)",
"sv": "Svenska",
"vi": "Tiếng Việt",
"bg": "Български",
"ru": "Русский",
"ja": "日本語",
"zh-tw": "正體中文",
"zh-cn": "简体中文"
}
}
]

View File

@@ -9,10 +9,31 @@ Contents:
* "Check configuration" command
* Disable DNSStubListener
* "Apply configuration" command
* Updating
* Get version command
* Update command
* Device Names and Per-client Settings
* Per-client settings
* Get list of clients
* Add client
* Update client
* Delete client
* Enable DHCP server
* "Show DHCP status" command
* "Check DHCP" command
* "Enable DHCP" command
* Static IP check/set
* Add a static lease
* DNS access settings
* List access settings
* Set access settings
* Rewrites
* API: List rewrite entries
* API: Add a rewrite entry
* API: Remove a rewrite entry
* Services Filter
* API: Get blocked services list
* API: Set blocked services list
## First startup
@@ -187,6 +208,107 @@ On error, server responds with code 400 or 500. In this case UI should show err
ERROR MESSAGE
## Updating
Algorithm of an update by command:
* UI requests the latest version information from Server
* Server requests information from Internet; stores the data in cache for several hours; sends data to UI
* If UI sees that a new version is available, it shows notification message and "Update Now" button
* When user clicks on "Update Now" button, UI sends Update command to Server
* UI shows "Please wait, AGH is being updated..." message
* Server performs an update:
* Use working directory from `--work-dir` if necessary
* Download new package for the current OS and CPU
* Unpack the package to a temporary directory `update-vXXX`
* Copy the current configuration file to the directory we unpacked new AGH to
* Check configuration compatibility by executing `./AGH --check-config`. If this command fails, we won't be able to update.
* Create `backup-vXXX` directory and copy the current configuration file there
* Copy supporting files (README, LICENSE, etc.) to backup directory
* Copy supporting files from the update directory to the current directory
* Move the current binary file to backup directory
* Note: if power fails here, AGH won't be able to start at system boot. Administrator has to fix it manually
* Move new binary file to the current directory
* Send response to UI
* Stop all tasks, including DNS server, DHCP server, HTTP server
* If AGH is running as a service, use service control functionality to restart
* If AGH is not running as a service, use the current process arguments to start a new process
* Exit process
* UI resends Get Status command until Server responds to it with the new version. This means that Server is successfully restarted after update.
* UI reloads itself
### Get version command
On receiving this request server downloads version.json data from github and stores it in cache for several hours.
Example of version.json data:
{
"version": "v0.95-hotfix",
"announcement": "AdGuard Home v0.95-hotfix is now available!",
"announcement_url": "",
"download_windows_amd64": "",
"download_windows_386": "",
"download_darwin_amd64": "",
"download_linux_amd64": "",
"download_linux_386": "",
"download_linux_arm": "",
"download_linux_arm64": "",
"download_linux_mips": "",
"download_linux_mipsle": "",
"selfupdate_min_version": "v0.0"
}
Server can only auto-update if the current version is equal or higher than `selfupdate_min_version`.
Request:
POST /control/version.json
{
"recheck_now": true | false // if false, server will check for a new version data only once in several hours
}
Response:
200 OK
{
"new_version": "v0.95",
"announcement": "AdGuard Home v0.95 is now available!",
"announcement_url": "http://...",
"can_autoupdate": true
}
If `can_autoupdate` is true, then the server can automatically upgrade to a new version.
Response with empty body:
200 OK
It means that update check is disabled by user. UI should do nothing.
### Update command
Perform an update procedure to the latest available version
Request:
POST /control/update
Response:
200 OK
Error response:
500
UI shows error message "Auto-update has failed"
## Enable DHCP server
Algorithm:
@@ -201,6 +323,38 @@ Algorithm:
* UI shows the status
### "Show DHCP status" command
Request:
GET /control/dhcp/status
Response:
200 OK
{
"config":{
"enabled":false,
"interface_name":"...",
"gateway_ip":"...",
"subnet_mask":"...",
"range_start":"...",
"range_end":"...",
"lease_duration":60,
"icmp_timeout_msec":0
},
"leases":[
{"ip":"...","mac":"...","hostname":"...","expires":"..."}
...
],
"static_leases":[
{"ip":"...","mac":"...","hostname":"..."}
...
]
}
### "Check DHCP" command
Request:
@@ -325,3 +479,324 @@ Step 2.
If we would set a different IP address, we'd need to replace the IP address for the current network configuration. But currently this step isn't necessary.
ip addr replace dev eth0 192.168.0.1/24
### Add a static lease
Request:
POST /control/dhcp/add_static_lease
{
"mac":"...",
"ip":"...",
"hostname":"..."
}
Response:
200 OK
### Remove a static lease
Request:
POST /control/dhcp/remove_static_lease
{
"mac":"...",
"ip":"...",
"hostname":"..."
}
Response:
200 OK
## Device Names and Per-client Settings
When a client requests information from DNS server, he's identified by IP address.
Administrator can set a name for a client with a known IP and also override global settings for this client. The name is used to improve readability of DNS logs: client's name is shown in UI next to its IP address. The names are loaded from 3 sources:
* automatically from "/etc/hosts" file. It's a list of `IP<->Name` entries which is loaded once on AGH startup from "/etc/hosts" file.
* automatically using rDNS. It's a list of `IP<->Name` entries which is added in runtime using rDNS mechanism when a client first makes a DNS request.
* manually configured via UI. It's a list of client's names and their settings which is loaded from configuration file and stored on disk.
### Per-client settings
UI provides means to manage the list of known clients (List/Add/Update/Delete) and their settings. These settings are stored in configuration file as an array of objects.
Notes:
* `name`, `ip` and `mac` values are unique.
* `ip` & `mac` values can't be set both at the same time.
* If `mac` is set and DHCP server is enabled, IP is taken from DHCP lease table.
* If `use_global_settings` is true, then DNS responses for this client are processed and filtered using global settings.
* If `use_global_settings` is false, then the client-specific settings are used to override (enable or disable) global settings.
* If `use_global_blocked_services` is false, then the client-specific settings are used to override (enable or disable) global Blocked Services settings.
### Get list of clients
Request:
GET /control/clients
Response:
200 OK
{
clients: [
{
name: "client1"
ip: "..."
mac: "..."
use_global_settings: true
filtering_enabled: false
parental_enabled: false
safebrowsing_enabled: false
safesearch_enabled: false
use_global_blocked_services: true
blocked_services: [ "name1", ... ]
}
]
auto_clients: [
{
name: "host"
ip: "..."
source: "etc/hosts" || "rDNS"
}
]
}
### Add client
Request:
POST /control/clients/add
{
name: "client1"
ip: "..."
mac: "..."
use_global_settings: true
filtering_enabled: false
parental_enabled: false
safebrowsing_enabled: false
safesearch_enabled: false
use_global_blocked_services: true
blocked_services: [ "name1", ... ]
}
Response:
200 OK
Error response (Client already exists):
400
### Update client
Request:
POST /control/clients/update
{
name: "client1"
data: {
name: "client1"
ip: "..."
mac: "..."
use_global_settings: true
filtering_enabled: false
parental_enabled: false
safebrowsing_enabled: false
safesearch_enabled: false
use_global_blocked_services: true
blocked_services: [ "name1", ... ]
}
}
Response:
200 OK
Error response (Client not found):
400
### Delete client
Request:
POST /control/clients/delete
{
name: "client1"
}
Response:
200 OK
Error response (Client not found):
400
## DNS access settings
There are low-level settings that can block undesired DNS requests. "Blocking" means not responding to request.
There are 3 types of access settings:
* allowed_clients: Only these clients are allowed to make DNS requests.
* disallowed_clients: These clients are not allowed to make DNS requests.
* blocked_hosts: These hosts are not allowed to be resolved by a DNS request.
### List access settings
Request:
GET /control/access/list
Response:
200 OK
{
allowed_clients: ["127.0.0.1", ...]
disallowed_clients: ["127.0.0.1", ...]
blocked_hosts: ["host.com", ...]
}
### Set access settings
Request:
POST /control/access/set
{
allowed_clients: ["127.0.0.1", ...]
disallowed_clients: ["127.0.0.1", ...]
blocked_hosts: ["host.com", ...]
}
Response:
200 OK
## Rewrites
This section allows the administrator to easily configure custom DNS response for a specific domain name.
A, AAAA and CNAME records are supported.
### API: List rewrite entries
Request:
GET /control/rewrite/list
Response:
200 OK
[
{
domain: "..."
answer: "..."
}
...
]
### API: Add a rewrite entry
Request:
POST /control/rewrite/add
{
domain: "..."
answer: "..." // "1.2.3.4" (A) || "::1" (AAAA) || "hostname" (CNAME)
}
Response:
200 OK
### API: Remove a rewrite entry
Request:
POST /control/rewrite/delete
{
domain: "..."
answer: "..."
}
Response:
200 OK
## Services Filter
Allows to quickly block popular sites globally or for specific client only.
UI manages these settings via global or per-client API.
UI and server have the same list of the services supported and this list must always be in synchronization.
UI code also contains icons for each service: `client/src/components/ui/Icons.js`.
How it works:
* UI presents the list of services which user may want to block
* Admin clicks on the checkboxes in front of the services to block and presses Save
* UI sends `Set blocked services list` or `Update client` message
* Server updates the internal configuration
* When a user sends a DNS request for a host which is blocked by these settings, he won't receive its IP address
* Query log will show that this request was blocked by "Blocked services"
Internally, all supported services are stored as a map:
service name -> list of rules
### API: Get blocked services list
Request:
GET /control/blocked_services/list
Response:
200 OK
[ "name1", ... ]
### API: Set blocked services list
Request:
POST /control/blocked_services/set
[ "name1", ... ]
Response:
200 OK

View File

@@ -11,14 +11,22 @@ FROM alpine:latest
LABEL maintainer="AdGuard Team <devteam@adguard.com>"
# Update CA certs
RUN apk --no-cache --update add ca-certificates && \
rm -rf /var/cache/apk/* && mkdir -p /opt/adguardhome
RUN apk --no-cache --update add ca-certificates libcap && \
rm -rf /var/cache/apk/* && \
mkdir -p /opt/adguardhome/conf /opt/adguardhome/work && \
chown -R nobody: /opt/adguardhome
COPY --from=build /src/AdGuardHome/AdGuardHome /opt/adguardhome/AdGuardHome
COPY --from=build --chown=nobody:nogroup /src/AdGuardHome/AdGuardHome /opt/adguardhome/AdGuardHome
EXPOSE 53/tcp 53/udp 67/tcp 67/udp 68/tcp 68/udp 80/tcp 443/tcp 853/tcp 853/udp 3000/tcp
RUN setcap 'cap_net_bind_service=+eip' /opt/adguardhome/AdGuardHome
EXPOSE 53/tcp 53/udp 67/udp 68/udp 80/tcp 443/tcp 853/tcp 3000/tcp
VOLUME ["/opt/adguardhome/conf", "/opt/adguardhome/work"]
WORKDIR /opt/adguardhome/work
#USER nobody
ENTRYPOINT ["/opt/adguardhome/AdGuardHome"]
CMD ["-c", "/opt/adguardhome/conf/AdGuardHome.yaml", "-w", "/opt/adguardhome/work"]
CMD ["-c", "/opt/adguardhome/conf/AdGuardHome.yaml", "-w", "/opt/adguardhome/work", "--no-check-update"]

View File

@@ -2,15 +2,22 @@ FROM alpine:latest
LABEL maintainer="AdGuard Team <devteam@adguard.com>"
# Update CA certs
RUN apk --no-cache --update add ca-certificates && \
rm -rf /var/cache/apk/* && mkdir -p /opt/adguardhome
RUN apk --no-cache --update add ca-certificates libcap && \
rm -rf /var/cache/apk/* && \
mkdir -p /opt/adguardhome/conf /opt/adguardhome/work && \
chown -R nobody: /opt/adguardhome
COPY --chown=nobody:nogroup ./AdGuardHome /opt/adguardhome/AdGuardHome
COPY ./AdGuardHome /opt/adguardhome/AdGuardHome
RUN setcap 'cap_net_bind_service=+eip' /opt/adguardhome/AdGuardHome
EXPOSE 53/tcp 53/udp 67/tcp 67/udp 68/tcp 68/udp 80/tcp 443/tcp 853/tcp 853/udp 3000/tcp
EXPOSE 53/tcp 53/udp 67/udp 68/udp 80/tcp 443/tcp 853/tcp 3000/tcp
VOLUME ["/opt/adguardhome/conf", "/opt/adguardhome/work"]
WORKDIR /opt/adguardhome/work
#USER nobody
ENTRYPOINT ["/opt/adguardhome/AdGuardHome"]
CMD ["-h", "0.0.0.0", "-c", "/opt/adguardhome/conf/AdGuardHome.yaml", "-w", "/opt/adguardhome/work"]
CMD ["-h", "0.0.0.0", "-c", "/opt/adguardhome/conf/AdGuardHome.yaml", "-w", "/opt/adguardhome/work", "--no-check-update"]

View File

@@ -4,6 +4,7 @@ NATIVE_GOARCH = $(shell unset GOARCH; go env GOARCH)
GOPATH := $(shell go env GOPATH)
JSFILES = $(shell find client -path client/node_modules -prune -o -type f -name '*.js')
STATIC = build/static/index.html
CHANNEL ?= release
TARGET=AdGuardHome
@@ -19,10 +20,10 @@ client/node_modules: client/package.json client/package-lock.json
$(STATIC): $(JSFILES) client/node_modules
npm --prefix client run build-prod
$(TARGET): $(STATIC) *.go dhcpd/*.go dnsfilter/*.go dnsforward/*.go
$(TARGET): $(STATIC) *.go home/*.go dhcpd/*.go dnsfilter/*.go dnsforward/*.go
GOOS=$(NATIVE_GOOS) GOARCH=$(NATIVE_GOARCH) GO111MODULE=off go get -v github.com/gobuffalo/packr/...
PATH=$(GOPATH)/bin:$(PATH) packr -z
CGO_ENABLED=0 go build -ldflags="-s -w -X main.VersionString=$(GIT_VERSION)" -asmflags="-trimpath=$(PWD)" -gcflags="-trimpath=$(PWD)"
CGO_ENABLED=0 go build -ldflags="-s -w -X main.version=$(GIT_VERSION) -X main.channel=$(CHANNEL)" -asmflags="-trimpath=$(PWD)" -gcflags="-trimpath=$(PWD)"
PATH=$(GOPATH)/bin:$(PATH) packr clean
clean:

133
README.md
View File

@@ -44,9 +44,15 @@ AdGuard Home is a network-wide software for blocking ads & tracking. After you s
It operates as a DNS server that re-routes tracking domains to a "black hole," thus preventing your devices from connecting to those servers. It's based on software we use for our public [AdGuard DNS](https://adguard.com/en/adguard-dns/overview.html) servers -- both share a lot of common code.
* [Getting Started](#getting-started)
* [Comparing AdGuard Home to other solutions](#comparison)
* [How is this different from public AdGuard DNS servers?](#comparison-adguard-dns)
* [How does AdGuard Home compare to Pi-Hole](#comparison-pi-hole)
* [How does AdGuard Home compare to traditional ad blockers](#comparison-adblock)
* [How to build from source](#how-to-build)
* [Contributing](#contributing)
* [Reporting issues](#reporting-issues)
* [Test unstable versions](#test-unstable-versions)
* [Reporting issues](#reporting-issues)
* [Help with translations](#translate)
* [Acknowledgments](#acknowledgments)
<a id="getting-started"></a>
@@ -63,6 +69,57 @@ Alternatively, you can use our [official Docker image](https://hub.docker.com/r/
* [How to install and run AdGuard Home on Raspberry Pi](https://github.com/AdguardTeam/AdGuardHome/wiki/Raspberry-Pi)
* [How to install and run AdGuard Home on a Virtual Private Server](https://github.com/AdguardTeam/AdGuardHome/wiki/VPS)
### API
If you want to integrate with AdGuard Home, you can use our [REST API](https://github.com/AdguardTeam/AdGuardHome/tree/master/openapi).
Alternatively, you can use this [python client](https://pypi.org/project/adguardhome/), which is used to build the [AdGuard Home Hass.io Add-on](https://community.home-assistant.io/t/community-hass-io-add-on-adguard-home).
<a id="comparison"></a>
## Comparing AdGuard Home to other solutions
<a id="comparison-adguard-dns"></a>
### How is this different from public AdGuard DNS servers?
Running your own AdGuard Home server allows you to do much more than using a public DNS server. It's a completely different level. See for yourself:
* Choose what exactly will the server block or not block.
* Monitor your network activity.
* Add your own custom filtering rules.
* **Most importantly, this is your own server, and you are the only one who's in control.**
<a id="comparison-pi-hole"></a>
### How does AdGuard Home compare to Pi-Hole
At this point, AdGuard Home has a lot in common with Pi-Hole. Both block ads and trackers using "DNS sinkholing" method, and both allow customizing what's blocked.
> We're not going to stop here. DNS sinkholing is not a bad starting point, but this is just the beginning.
AdGuard Home provides a lot of features out-of-the-box with no need to install and configure additional software. We want it to be simple to the point when even casual users can set it up with minimal effort.
> Disclaimer: some of the listed features can be added to Pi-Hole by installing additional software or by manually using SSH terminal and reconfiguring one of the utilities Pi-Hole consists of. However, in our opinion, this cannot be legitimately counted as a Pi-Hole's feature.
| Feature | AdGuard&nbsp;Home | Pi-Hole |
|-------------------------------------------------------------------------|--------------|--------------------------------------------------------|
| Blocking ads and trackers | ✅ | ✅ |
| Customizing blocklists | ✅ | ✅ |
| Built-in DHCP server | ✅ | ✅ |
| HTTPS for the Admin interface | ✅ | Kind of, but you'll need to manually configure lighthttpd |
| Encrypted DNS upstream servers (DNS-over-HTTPS, DNS-over-TLS, DNSCrypt) | ✅ | ❌ (requires additional software) |
| Cross-platform | ✅ | ❌ (not natively, only via Docker) |
| Running as a DNS-over-HTTPS or DNS-over-TLS server | ✅ | ❌ (requires additional software) |
| Blocking phishing and malware domains | ✅ | ❌ |
| Parental control (blocking adult domains) | ✅ | ❌ |
| Force Safe search on search engines | ✅ | ❌ |
| Per-client (device) configuration | ✅ | ❌ |
| Access settings (choose who can use AGH DNS) | ✅ | ❌ |
<a id="comparison-adblock"></a>
### How does AdGuard Home compare to traditional ad blockers
It depends.
"DNS sinkholing" is capable of blocking a big percentage of ads, but it lacks flexibility and power of traditional ad blockers. You can get a good impression about the difference between these methods by reading [this article](https://adguard.com/en/blog/adguard-vs-adaway-dns66/). It compares AdGuard for Android (a traditional ad blocker) to hosts-level ad blockers (which are almost identical to DNS-based blockers in their capabilities). However, this level of protection is enough for some users.
<a id="how-to-build"></a>
## How to build from source
@@ -89,49 +146,52 @@ cd AdGuardHome
make
```
#### (For devs) Upload translations
```
node upload.js
```
#### (For devs) Download translations
```
node download.js
```
<a id="contributing"></a>
## Contributing
You are welcome to fork this repository, make your changes and submit a pull request — https://github.com/AdguardTeam/AdGuardHome/pulls
### How to update translations
<a id="test-unstable-versions"></a>
### Test unstable versions
There are two options how you can install an unstable version.
You can either install a beta version of AdGuard Home which we update periodically,
or you can use the Docker image from the `edge` tag, which is synced with the repo master branch.
* [Docker Hub](https://hub.docker.com/r/adguard/adguardhome)
* Beta builds
* [Rapsberry Pi (32-bit ARM)](https://static.adguard.com/adguardhome/beta/AdGuardHome_linux_arm.tar.gz)
* [MacOS](https://static.adguard.com/adguardhome/beta/AdGuardHome_MacOS.zip)
* [Windows 64-bit](https://static.adguard.com/adguardhome/beta/AdGuardHome_Windows_amd64.zip)
* [Windows 32-bit](https://static.adguard.com/adguardhome/beta/AdGuardHome_Windows_386.zip)
* [Linux 64-bit](https://static.adguard.com/adguardhome/beta/AdGuardHome_linux_amd64.tar.gz)
* [Linux 32-bit](https://static.adguard.com/adguardhome/beta/AdGuardHome_linux_386.tar.gz)
* [FreeBSD 64-bit](https://static.adguard.com/adguardhome/beta/AdGuardHome_freebsd_amd64.tar.gz)
* [64-bit ARM](https://static.adguard.com/adguardhome/beta/AdGuardHome_linux_arm64.tar.gz)
* [MIPS](https://static.adguard.com/adguardhome/beta/AdGuardHome_linux_mips.tar.gz)
* [MIPSLE](https://static.adguard.com/adguardhome/beta/AdGuardHome_linux_mipsle.tar.gz)
<a id="reporting-issues"></a>
### Report issues
If you run into any problem or have a suggestion, head to [this page](https://github.com/AdguardTeam/AdGuardHome/issues) and click on the `New issue` button.
<a id="translate"></a>
### Help with translations
If you want to help with AdGuard Home translations, please learn more about translating AdGuard products here: https://kb.adguard.com/en/general/adguard-translations
Here is a direct link to AdGuard Home project: http://translate.adguard.com/collaboration/project?id=153384
Before updating translations you need to install dependencies:
```
cd scripts/translations
npm install
```
Create file `oneskyapp.json` in `scripts/translations` folder.
Example of `oneskyapp.json`
```
{
"url": "https://platform.api.onesky.io/1/projects/",
"projectId": <PROJECT ID>,
"apiKey": <API KEY>,
"secretKey": <SECRET KEY>
}
```
#### Upload translations
```
node upload.js
```
#### Download translations
```
node download.js
```
<a id="reporting-issues"></a>
## Reporting issues
If you run into any problem or have a suggestion, head to [this page](https://github.com/AdguardTeam/AdGuardHome/issues) and click on the `New issue` button.
Here is a link to AdGuard Home project: https://crowdin.com/project/adguard-applications
<a id="acknowledgments"></a>
## Acknowledgments
@@ -145,6 +205,7 @@ This software wouldn't have been possible without:
* [go-yaml](https://github.com/go-yaml/yaml)
* [service](https://godoc.org/github.com/kardianos/service)
* [dnsproxy](https://github.com/AdguardTeam/dnsproxy)
* [urlfilter](https://github.com/AdguardTeam/urlfilter)
* [Node.js](https://nodejs.org/) and it's libraries:
* [React.js](https://reactjs.org)
* [Tabler](https://github.com/tabler/tabler)

43
changelog.config.js Normal file
View File

@@ -0,0 +1,43 @@
module.exports = {
"disableEmoji": true,
"list": [
"+",
"*",
"-",
],
"maxMessageLength": 64,
"minMessageLength": 3,
"questions": [
"type",
"scope",
"subject",
"body",
"issues"
],
"scopes": [
"",
"global",
"dnsfilter",
"home",
"dnsforward",
"dhcpd",
"documentation"
],
"types": {
"+": {
"description": "A new feature",
"emoji": "",
"value": "+"
},
"*": {
"description": "A code change that neither fixes a bug or adds a feature",
"emoji": "",
"value": "*"
},
"-": {
"description": "A bug fix",
"emoji": "",
"value": "-"
}
}
};

86
client/package-lock.json generated vendored
View File

@@ -945,12 +945,27 @@
}
},
"axios": {
"version": "0.18.0",
"resolved": "http://registry.npmjs.org/axios/-/axios-0.18.0.tgz",
"integrity": "sha1-MtU+SFHv3AoRmTts0AB4nXDAUQI=",
"version": "0.19.0",
"resolved": "https://registry.npmjs.org/axios/-/axios-0.19.0.tgz",
"integrity": "sha512-1uvKqKQta3KBxIz14F2v06AEHZ/dIoeKfbTRkK1E5oqjDnuEerLmYTgJB5AiQZHJcljpg1TuRzdjDR06qNk0DQ==",
"requires": {
"follow-redirects": "^1.3.0",
"is-buffer": "^1.1.5"
"follow-redirects": "1.5.10",
"is-buffer": "^2.0.2"
},
"dependencies": {
"follow-redirects": {
"version": "1.5.10",
"resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.5.10.tgz",
"integrity": "sha512-0V5l4Cizzvqt5D44aTXbFZz+FtyXV1vrDN6qrelxtfYQKW0KO0W2T/hkE8xvGa/540LkZlkaUjO4ailYTFtHVQ==",
"requires": {
"debug": "=3.1.0"
}
},
"is-buffer": {
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.3.tgz",
"integrity": "sha512-U15Q7MXTuZlrbymiz95PJpZxu8IlipAp4dtS3wOdgPXx3mqBnslrWU14kxfHB+Py/+2PVKSr37dMAgM2A4uArw=="
}
}
},
"axobject-query": {
@@ -5124,6 +5139,7 @@
"version": "1.5.7",
"resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.5.7.tgz",
"integrity": "sha512-NONJVIFiX7Z8k2WxfqBjtwqMifx7X42ORLFrOZ2LTKGj71G3C0kfdyTqGqr8fx5zSX6Foo/D95dgGWbPUiwnew==",
"dev": true,
"requires": {
"debug": "^3.1.0"
}
@@ -6933,7 +6949,8 @@
"is-buffer": {
"version": "1.1.6",
"resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz",
"integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w=="
"integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==",
"dev": true
},
"is-builtin-module": {
"version": "1.0.0",
@@ -7386,9 +7403,9 @@
}
},
"lodash": {
"version": "4.17.11",
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz",
"integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg=="
"version": "4.17.15",
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz",
"integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A=="
},
"lodash-es": {
"version": "4.17.10",
@@ -7767,9 +7784,9 @@
}
},
"mixin-deep": {
"version": "1.3.1",
"resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz",
"integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==",
"version": "1.3.2",
"resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.2.tgz",
"integrity": "sha512-WRoDn//mXBiJ1H40rqa3vH0toePwSsGb45iInWlTySa+Uu4k3tYUSxa2v1KqAiLtvlrSzaExqS1gtk96A9zvEA==",
"dev": true,
"requires": {
"for-in": "^1.0.2",
@@ -10191,6 +10208,14 @@
}
}
},
"react-router-hash-link": {
"version": "1.2.2",
"resolved": "https://registry.npmjs.org/react-router-hash-link/-/react-router-hash-link-1.2.2.tgz",
"integrity": "sha512-LBthLVHdqPeKDVt3+cFRhy15Z7veikOvdKRZRfyBR2vjqIE7rxn+tKLjb6DOmLm6JpoQVemVDnxQ35RVnEHdQA==",
"requires": {
"prop-types": "^15.6.0"
}
},
"react-table": {
"version": "6.8.6",
"resolved": "https://registry.npmjs.org/react-table/-/react-table-6.8.6.tgz",
@@ -10848,9 +10873,9 @@
"dev": true
},
"set-value": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz",
"integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==",
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.1.tgz",
"integrity": "sha512-JxHc1weCN68wRY0fhCoXpyK55m/XPHafOmK4UWD7m2CI14GMcFypt4w/0+NV5f/ZMby2F6S2wwA7fgynh9gWSw==",
"dev": true,
"requires": {
"extend-shallow": "^2.0.1",
@@ -12478,38 +12503,15 @@
}
},
"union-value": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz",
"integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=",
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.1.tgz",
"integrity": "sha512-tJfXmxMeWYnczCVs7XAEvIV7ieppALdyepWMkHkwciRpZraG/xwT+s2JN8+pr1+8jCRf80FFzvr+MpQeeoF4Xg==",
"dev": true,
"requires": {
"arr-union": "^3.1.0",
"get-value": "^2.0.6",
"is-extendable": "^0.1.1",
"set-value": "^0.4.3"
},
"dependencies": {
"extend-shallow": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
"integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
"dev": true,
"requires": {
"is-extendable": "^0.1.0"
}
},
"set-value": {
"version": "0.4.3",
"resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz",
"integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=",
"dev": true,
"requires": {
"extend-shallow": "^2.0.1",
"is-extendable": "^0.1.1",
"is-plain-object": "^2.0.1",
"to-object-path": "^0.3.0"
}
}
"set-value": "^2.0.1"
}
},
"uniq": {

5
client/package.json vendored
View File

@@ -10,13 +10,13 @@
},
"dependencies": {
"@nivo/line": "^0.49.1",
"axios": "^0.18.0",
"axios": "^0.19.0",
"classnames": "^2.2.6",
"date-fns": "^1.29.0",
"file-saver": "^1.3.8",
"i18next": "^12.0.0",
"i18next-browser-languagedetector": "^2.2.3",
"lodash": "^4.17.11",
"lodash": "^4.17.15",
"nanoid": "^1.2.3",
"prop-types": "^15.6.1",
"react": "^16.4.0",
@@ -27,6 +27,7 @@
"react-redux": "^5.0.7",
"react-redux-loading-bar": "^4.0.7",
"react-router-dom": "^4.2.2",
"react-router-hash-link": "^1.2.2",
"react-table": "^6.8.6",
"react-transition-group": "^2.4.0",
"redux": "^4.0.0",

Binary file not shown.

Before

Width:  |  Height:  |  Size: 15 KiB

BIN
client/public/favicon.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

View File

@@ -5,7 +5,7 @@
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<meta name="theme-color" content="#000000">
<meta name="google" content="notranslate">
<link rel="shortcut icon" href="favicon.ico">
<link rel="icon" type="image/png" href="favicon.png" sizes="48x48">
<title>AdGuard Home</title>
</head>
<body>

View File

@@ -5,7 +5,7 @@
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<meta name="theme-color" content="#000000">
<meta name="google" content="notranslate">
<link rel="shortcut icon" href="favicon.ico">
<link rel="icon" type="image/png" href="favicon.png" sizes="48x48">
<title>Setup AdGuard Home</title>
</head>
<body>

View File

@@ -1,250 +1,249 @@
{
"url_added_successfully": "\u0423\u0441\u043f\u0435\u0448\u043d\u043e \u0434\u043e\u0431\u0430\u0432\u0435\u043d URL",
"check_dhcp_servers": "\u041f\u0440\u043e\u0432\u0435\u0440\u043a\u0430 \u0437\u0430 \u0430\u043a\u0442\u0438\u0432\u0435\u043d DHCP \u0441\u044a\u0440\u0432\u044a\u0440",
"save_config": "\u0417\u0430\u043f\u0438\u0448\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438\u0442\u0435",
"enabled_dhcp": "DHCP \u0435 \u0440\u0430\u0437\u0440\u0435\u0448\u0435\u043d",
"disabled_dhcp": "DHCP \u0435 \u0437\u0430\u0431\u0440\u0430\u043d\u0435\u043d",
"dhcp_title": "DHCP \u0441\u044a\u0440\u0432\u044a\u0440 (\u0442\u0435\u0441\u0442\u043e\u0432\u0438!)",
"dhcp_description": "\u0410\u043a\u043e \u0440\u0443\u0442\u0435\u0440\u0430 \u0432\u0438 \u043d\u0435 \u0440\u0430\u0437\u0434\u0430\u0432\u0430 DHCP \u0430\u0434\u0440\u0435\u0441\u0438, \u043c\u043e\u0436\u0435 \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 \u0432\u0433\u0440\u0430\u0434\u0435\u043d\u0438\u044f \u0432 AdGuard DHCP \u0441\u044a\u0440\u0432\u044a\u0440.",
"dhcp_enable": "\u0420\u0437\u0440\u0435\u0448\u0438 DHCP \u0441\u044a\u0440\u0432\u044a\u0440\u0430",
"dhcp_disable": "\u0417\u0430\u0431\u0440\u0430\u043d\u0438 DHCP \u0441\u044a\u0440\u0432\u044a\u0440\u0430",
"dhcp_not_found": "\u0412\u0430\u0448\u0430\u0442\u0430 \u043c\u0440\u0435\u0436\u0430 \u043d\u044f\u043c\u0430 \u0430\u043a\u0442\u0438\u0432\u0435\u043d DHCP \u0441\u044a\u0440\u0432\u044a\u0440. \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0435 \u043f\u043e\u043b\u0437\u0432\u0430\u043d\u0435\u0442\u043e \u043d\u0430 \u0432\u0433\u0440\u0430\u0434\u0435\u043d\u0438\u044f DHCP \u0441\u044a\u0440\u0432\u044a\u0440.",
"dhcp_found": "\u0412\u0430\u0448\u0430\u0442\u0430 \u043c\u0440\u0435\u0436\u0430 \u0432\u0435\u0447\u0435 \u0438\u043c\u0430 \u0430\u043a\u0442\u0438\u0432\u0435\u043d DHCP \u0441\u044a\u0440\u0432\u044a\u0440. \u041d\u0435 \u0435 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u043f\u043e\u043b\u0437\u0432\u0430\u043d\u0435\u0442\u043e \u043d\u0430 \u0432\u0442\u043e\u0440\u0438!",
"dhcp_leases": "DHCP \u0440\u0430\u0437\u0434\u0430\u0434\u0435\u043d\u0438 \u0430\u0434\u0440\u0435\u0441\u0438",
"dhcp_leases_not_found": "\u041d\u044f\u043c\u0430 \u043d\u0430\u043c\u0435\u0440\u0435\u043d\u0438 \u0430\u043a\u0442\u0438\u0432\u043d\u0438 DHCP \u0430\u0434\u0440\u0435\u0441\u0438",
"dhcp_config_saved": "\u0417\u0430\u043f\u0438\u0448\u0438 \u043a\u043e\u043d\u0444\u0438\u0433\u0443\u0440\u0430\u0446\u0438\u044f\u0442\u0430 \u043d\u0430 DHCP \u0441\u044a\u0440\u0432\u044a\u0440\u0430",
"form_error_required": "\u0417\u0430\u0434\u044a\u043b\u0436\u0438\u0442\u0435\u043b\u043d\u043e \u043f\u043e\u043b\u0435",
"form_error_ip_format": "\u041d\u0435\u0432\u0430\u043b\u0438\u0434\u0435\u043d IPv4 \u0430\u0434\u0440\u0435\u0441",
"form_error_positive": "\u041f\u0440\u043e\u0432\u0435\u0440\u0435\u0442\u0435 \u0434\u0430\u043b\u0438 \u0435 \u043f\u043e\u043b\u043e\u0436\u0438\u0442\u0435\u043b\u043d\u043e \u0447\u0438\u0441\u043b\u043e",
"dhcp_form_gateway_input": "IP \u0448\u043b\u044e\u0437",
"dhcp_form_subnet_input": "\u041c\u0440\u0435\u0436\u043e\u0432\u0430 \u043c\u0430\u0441\u043a\u0430",
"dhcp_form_range_title": "\u0413\u0440\u0443\u043f\u0430 \u043e\u0442 IP \u0430\u0434\u0440\u0435\u0441\u0438",
"dhcp_form_range_start": "\u041f\u044a\u0440\u0432\u0438 \u0430\u0434\u0440\u0435\u0441",
"dhcp_form_range_end": "\u041f\u043e\u0441\u043b\u0435\u0434\u0435\u043d \u0430\u0434\u0440\u0435\u0441",
"dhcp_form_lease_title": "\u041e\u0442\u0434\u0430\u0434\u0435\u043d\u0438 \u0430\u0434\u0440\u0435\u0441\u0438 (\u0441\u0435\u043a\u0443\u043d\u0434\u0438)",
"dhcp_form_lease_input": "\u041e\u0442\u0447\u0435\u0442 \u0437\u0430 \u0440\u0430\u0437\u0434\u0430\u0434\u0435\u043d\u0438 \u0430\u0434\u0440\u0435\u0441\u0438",
"dhcp_interface_select": "\u0418\u0437\u0431\u0435\u0440\u0435\u0442\u0435 \u043c\u0440\u0435\u0436\u043e\u0432 \u0430\u0434\u0430\u043f\u0442\u0435\u0440 \u0437\u0430 DHCP",
"dhcp_hardware_address": "\u0425\u0430\u0440\u0434\u0443\u0435\u0440\u043d\u0438 \u0430\u0434\u0440\u0435\u0441\u0438 (MAC)",
"dhcp_ip_addresses": "IP \u0430\u0434\u0440\u0435\u0441\u0438",
"dhcp_table_hostname": "\u0418\u043c\u0435 \u043d\u0430 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u043e",
"dhcp_table_expires": "\u0418\u0441\u0442\u043e\u0440\u0438\u044f",
"dhcp_warning": "\u0410\u043a\u043e \u0438\u0441\u043a\u0430\u0442\u0435 \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 \u0432\u0433\u0440\u0430\u0434\u0435\u043d\u0438\u044f DHCP \u0441\u044a\u0440\u0432\u044a\u0440, \u0442\u0440\u044f\u0431\u0432\u0430 \u0434\u0430 \u043d\u044f\u043c\u0430 \u0434\u0440\u0443\u0433 \u0430\u043a\u0442\u0438\u0432\u0435\u043d DHCP \u0432 \u043c\u0440\u0435\u0436\u0430\u0442\u0430 \u0412\u0438!",
"back": "\u041d\u0430\u0437\u0430\u0434",
"dashboard": "\u0422\u0430\u0431\u043b\u043e",
"settings": "\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438",
"filters": "\u0424\u0438\u043b\u0442\u0440\u0438",
"query_log": "\u0418\u0441\u0442\u043e\u0440\u0438\u044f \u043d\u0430 \u0437\u0430\u044f\u0432\u043a\u0438\u0442\u0435",
"faq": "\u0427\u0417\u0412",
"version": "\u0432\u0435\u0440\u0441\u0438\u044f",
"address": "\u0430\u0434\u0440\u0435\u0441",
"on": "\u0412\u041a\u041b\u042e\u0427\u0415\u041d\u041e",
"off": "\u0418\u0417\u041a\u041b\u042e\u0427\u0415\u041d\u041e",
"copyright": "\u0410\u0432\u0442\u043e\u0440\u0441\u043a\u043e \u043f\u0440\u0430\u0432\u043e",
"homepage": "\u0414\u043e\u043c\u0430\u0448\u043d\u0430 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430",
"report_an_issue": "\u0421\u044a\u043e\u0431\u0449\u0438 \u0437\u0430 \u043f\u0440\u043e\u0431\u043b\u0435\u043c",
"enable_protection": "\u0420\u0430\u0437\u0440\u0435\u0448\u0438 \u0437\u0430\u0449\u0438\u0442\u0430",
"enabled_protection": "\u0417\u0430\u0449\u0438\u0442\u0430\u0442\u0430 \u0435 \u0440\u0430\u0437\u0440\u0435\u0448\u0435\u043d\u0430",
"disable_protection": "\u0417\u0430\u0431\u0440\u0430\u043d\u0438 \u0437\u0430\u0449\u0438\u0442\u0430",
"disabled_protection": "\u0417\u0430\u0449\u0438\u0442\u0430\u0442\u0430 \u0435 \u0437\u0430\u0431\u0440\u0430\u043d\u0435\u043d\u0430",
"refresh_statics": "\u041e\u0431\u043d\u043e\u0432\u0438 \u0441\u0442\u0430\u0442\u0438\u0441\u0442\u0438\u043a\u0430\u0442\u0430",
"dns_query": "DNS \u0437\u0430\u043f\u0438\u0442\u0432\u0430\u043d\u0438\u044f",
"blocked_by": "\u0411\u043b\u043e\u043a\u0438\u0440\u0430\u043d\u0438 \u043e\u0442",
"stats_malware_phishing": "\u0432\u0438\u0440\u0443\u0441\u0438\/\u0430\u0442\u0430\u043a\u0438",
"stats_adult": "\u0441\u0430\u0439\u0442\u043e\u0432\u0435 \u0437\u0430 \u0432\u044a\u0437\u0440\u0430\u0441\u0442\u043d\u0438",
"stats_query_domain": "\u041d\u0430\u0439-\u043e\u0442\u0432\u0430\u0440\u044f\u043d\u0438 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0438",
"for_last_24_hours": "\u0437\u0430 \u043f\u043e\u0441\u043b\u0435\u0434\u043d\u0438\u0442\u0435 24 \u0447\u0430\u0441\u0430",
"no_domains_found": "\u041d\u044f\u043c\u0430 \u043d\u0430\u043c\u0435\u0440\u0435\u043d\u0438 \u0440\u0435\u0437\u0443\u043b\u0442\u0430\u0442\u0438",
"requests_count": "\u0421\u0443\u043c\u0430 \u043d\u0430 \u0437\u0430\u044f\u0432\u043a\u0438\u0442\u0435",
"top_blocked_domains": "\u041d\u0430\u0439-\u0431\u043b\u043e\u043a\u0438\u0440\u0430\u043d\u0438 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0438",
"top_clients": "\u041d\u0430\u0439-\u0430\u043a\u0442\u0438\u0432\u043d\u0438 IP \u0430\u0434\u0440\u0435\u0441\u0438",
"no_clients_found": "\u041d\u044f\u043ca \u043d\u0430\u043c\u0435\u0440\u0435\u043d\u0438 \u0430\u0434\u0440\u0435\u0441\u0438",
"general_statistics": "\u041e\u0431\u0449\u0430 \u0441\u0442\u0430\u0442\u0438\u0441\u0438\u043a\u0430",
"number_of_dns_query_24_hours": "\u0421\u0443\u043c\u0430 \u043d\u0430 DNS \u0437\u0430\u044f\u0432\u043a\u0438 \u0437\u0430 \u043f\u043e\u0441\u043b\u0435\u0434\u043d\u0438\u0442\u0435 24 \u0447\u0430\u0441\u0430",
"number_of_dns_query_blocked_24_hours": "\u0421\u0443\u043c\u0430 \u043d\u0430 \u0431\u043b\u043e\u043a\u0438\u0440\u0430\u043d\u0438 DNS \u0437\u0430\u044f\u0432\u043a\u0438 \u043e\u0442 \u0444\u0438\u043b\u0442\u0440\u0438\u0442\u0435 \u0437\u0430 \u0440\u0435\u043a\u043b\u0430\u043c\u0430 \u0438 \u043c\u0435\u0441\u0442\u043d\u0438",
"number_of_dns_query_blocked_24_hours_by_sec": "\u0421\u0443\u043c\u0430 \u043d\u0430 \u0431\u043b\u043e\u043a\u0438\u0440\u0430\u043d\u0438 DNS \u0437\u0430\u044f\u0432\u043a\u0438 \u043e\u0442 AdGuard \u0441\u0432\u044a\u0440\u0437\u0430\u043d\u0438 \u0441\u044a\u0441 \u0441\u0438\u0433\u0443\u0440\u043d\u043e\u0441\u0442\u0442\u0430",
"number_of_dns_query_blocked_24_hours_adult": "\u0421\u0443\u043c\u0430 \u043d\u0430 \u0431\u043b\u043e\u043a\u0438\u0440\u0430\u043d\u0438 \u0441\u0430\u0439\u0442\u043e\u0432\u0435 \u0437\u0430 \u0432\u044a\u0437\u0440\u0430\u0441\u0442\u043d\u0438",
"enforced_save_search": "\u0410\u043a\u0442\u0438\u0432\u0438\u0440\u0430\u043d\u043e \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0422\u044a\u0440\u0441\u0435\u043d\u0435",
"number_of_dns_query_to_safe_search": "\u0421\u0443\u043c\u0430 \u043d\u0430 DNS \u0437\u0430\u044f\u0432\u043a\u0438 \u043f\u0440\u0438 \u043a\u043e\u0439\u0442\u043e \u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u043e \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0422\u044a\u0440\u0441\u0435\u043d\u0435",
"average_processing_time": "\u0421\u0440\u0435\u0434\u043d\u043e \u0432\u0440\u0435\u043c\u0435 \u0437\u0430 \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0430",
"average_processing_time_hint": "\u0421\u0440\u0435\u0434\u043d\u043e \u0432\u0440\u0435\u043c\u0435 \u0437\u0430 \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0430 \u043d\u0430 DNS \u0437\u0430\u044f\u0432\u043a\u0438 \u0432 \u043c\u0438\u043b\u0438\u0441\u0435\u043a\u0443\u043d\u0434\u0438",
"block_domain_use_filters_and_hosts": "\u0411\u043b\u043e\u043a\u0438\u0440\u0430\u043d\u0438 \u0434\u043e\u043c\u0435\u0439\u043d\u0438 - \u043e\u0431\u0449\u0438 \u0438 \u043c\u0435\u0441\u0442\u043d\u0438 \u0444\u0438\u043b\u0442\u0440\u0438",
"filters_block_toggle_hint": "\u041c\u043e\u0436\u0435 \u0434\u0430 \u0437\u0430\u0434\u0430\u0434\u0435\u0442\u0435 \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438 \u0432 <a href='#filters'>\u0424\u0438\u043b\u0442\u0440\u0438<\/a>.",
"use_adguard_browsing_sec": "\u0418\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0439\u0442\u0435 AdGuard \u043c\u043e\u0434\u0443\u043b \u0437\u0430 \u0441\u0438\u0433\u0443\u0440\u043d\u043e\u0441\u0442\u0442\u0430",
"use_adguard_browsing_sec_hint": "\u041c\u043e\u0434\u0443\u043b \u0421\u0438\u0433\u0443\u0440\u043d\u043e\u0441\u0442 \u0432 AdGuard Home \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0432\u0430 \u0432\u0441\u044f\u043a\u0430 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430 \u043a\u043e\u044f\u0442\u043e \u043e\u0442\u0432\u0430\u0440\u044f\u0442\u0435 \u0434\u0430\u043b\u0438 \u0435 \u0432 \u0447\u0435\u0440\u043d\u0438\u0442\u0435 \u0441\u043f\u0438\u0441\u044a\u0446\u0438 \u0437\u0430\u0441\u0442\u0440\u0430\u0448\u0430\u0432\u0430\u0449\u0438 \u0432\u0430\u0448\u0430\u0442\u0430 \u0441\u0438\u0433\u0443\u0440\u043d\u043e\u0441\u0442. \u0418\u0437\u043f\u043e\u043b\u0437\u0432\u0430 \u0441\u0435 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u0435\u043d \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043a\u043e\u0439\u0442\u043e \u0437\u0430\u0449\u0438\u0442\u0430\u0432\u0430 \u0432\u0430\u0448\u0430\u0442\u0430 \u0430\u043d\u043e\u043d\u0438\u043c\u043d\u043e\u0441\u0442 \u0438 \u0438\u0437\u043f\u0440\u0430\u0449\u0430 \u0441\u0430\u043c\u043e SHA256 \u0441\u0443\u043c\u0430 \u0431\u0430\u0437\u0438\u0440\u0430\u043d\u0430 \u043d\u0430 \u0447\u0430\u0441\u0442 \u043e\u0442 \u0434\u043e\u043c\u0435\u0439\u043d\u0430 \u043a\u043e\u0439\u0442\u043e \u043f\u043e\u0441\u0435\u0449\u0430\u0432\u0430\u0442\u0435.",
"use_adguard_parental": "\u0412\u043a\u043b\u044e\u0447\u0438 AdGuard \u0420\u043e\u0434\u0438\u0442\u0435\u043b\u0441\u043a\u0438 \u041d\u0430\u0434\u0437\u043e\u0440",
"use_adguard_parental_hint": "\u041c\u043e\u0434\u0443\u043b XXX \u0432 AdGuard Home \u0449\u0435 \u043f\u0440\u043e\u0432\u0435\u0440\u0438 \u0434\u0430\u043b\u0438 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430\u0442\u0430 \u0438\u043c\u0430 \u043c\u0430\u0442\u0435\u0440\u0438\u0430\u043b\u0438 \u0437\u0430 \u0432\u044a\u0437\u0432\u044a\u0441\u0442\u043d\u0438. \u0418\u0437\u043f\u043e\u043b\u0437\u0432\u0430 \u0441\u0435 \u0441\u044a\u0449\u0438\u044f API \u0437\u0430 \u0430\u043d\u043e\u043d\u0438\u043c\u043d\u043e\u0441\u0442 \u043a\u0430\u0442\u043e \u043f\u0440\u0438 \u043c\u043e\u0434\u0443\u043b\u0430 \u0437\u0430 \u0421\u0438\u0433\u0443\u0440\u043d\u043e\u0441\u0442.",
"enforce_safe_search": "\u0412\u043a\u043b\u044e\u0447\u0438 \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0422\u044a\u0440\u0441\u0435\u043d\u0435",
"enforce_save_search_hint": "AdGuard Home \u043f\u0440\u0438\u043b\u0430\u0433\u0430 \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0422\u044a\u0440\u0441\u0435\u043d\u0435 \u0432 \u0441\u043b\u0435\u0434\u043d\u0438\u0442\u0435 \u0442\u044a\u0440\u0441\u0430\u0447\u043a\u0438 \u0438 \u0441\u0430\u0439\u0442\u043e\u0432\u0435: Google, Youtube, Bing, \u0438 Yandex.",
"no_servers_specified": "\u041d\u044f\u043c\u0430 \u0438\u0437\u0431\u0440\u0430\u043d\u0438 \u0443\u0441\u043b\u0443\u0433\u0438",
"no_settings": "\u041d\u044f\u043c\u0430 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438",
"general_settings": "\u041e\u0431\u0449\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438",
"upstream_dns": "\u0413\u043b\u0430\u0432\u0435\u043d DNS \u0441\u044a\u0440\u0432\u044a\u0440",
"upstream_dns_hint": "\u0410\u043a\u043e \u043e\u0441\u0442\u0430\u0432\u0438\u0442\u0435 \u043f\u0440\u0430\u0437\u043d\u043e, AdGuard Home \u0449\u0435 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430 <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> \u0437\u0430 \u0433\u043b\u0430\u0432\u0435\u043d. \u0418\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0439 tls:\/\/ \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043a\u0430 \u0437\u0430 DNS \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0449\u0438 TLS \u0432\u0440\u044a\u0437\u043a\u0430.",
"test_upstream_btn": "\u0422\u0435\u0441\u0442\u0432\u0430\u0439 \u0433\u043b\u0430\u0432\u043d\u0438\u044f DNS",
"apply_btn": "\u041f\u0440\u0438\u043b\u043e\u0436\u0438",
"disabled_filtering_toast": "\u0417\u0430\u0431\u0440\u0430\u043d\u0438 \u0444\u0438\u043b\u0442\u0440\u0438\u0440\u0430\u043d\u0435\u0442\u043e",
"enabled_filtering_toast": "\u0420\u0430\u0437\u0440\u0435\u0448\u0438 \u0444\u0438\u0442\u0440\u0438\u0440\u0430\u043d\u0435\u0442\u043e",
"disabled_safe_browsing_toast": "\u0417\u0430\u0431\u0440\u0430\u043d\u0438 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e-\u0441\u044a\u0440\u0444\u0438\u0440\u0430\u043d\u0435",
"enabled_safe_browsing_toast": "\u0420\u0437\u0440\u0435\u0448\u0438 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e-\u0441\u044a\u0440\u0444\u0438\u0440\u0430\u043d\u0435",
"disabled_parental_toast": "\u0417\u0430\u0431\u0440\u0430\u043d\u0438 \u0420\u043e\u0434\u0438\u0442\u0435\u043b\u0441\u043a\u0438 \u041d\u0430\u0434\u0437\u043e\u0440",
"enabled_parental_toast": "\u0420\u0430\u0437\u0440\u0435\u0448\u0438 \u0420\u043e\u0434\u0438\u0442\u0435\u043b\u0441\u043a\u0438 \u041d\u0430\u0434\u0437\u043e\u0440",
"disabled_safe_search_toast": "\u0417\u0430\u0431\u0440\u0430\u043d\u0438 \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0422\u044a\u0440\u0441\u0435\u043d\u0435",
"enabled_save_search_toast": "\u0420\u0430\u0437\u0440\u0435\u0448\u0438 \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0422\u044a\u0440\u0441\u0435\u043d\u0435",
"enabled_table_header": "\u0420\u0430\u0437\u0440\u0435\u0448\u0438",
"name_table_header": "\u0418\u043c\u0435",
"filter_url_table_header": "URL \u0444\u0438\u043b\u0442\u044a\u0440",
"rules_count_table_header": "\u041f\u0440\u0430\u0432\u0438\u043b\u0430 \u043e\u0431\u0449\u043e",
"last_time_updated_table_header": "\u041f\u043e\u0441\u043b\u0435\u0434\u043d\u043e \u043e\u0431\u043d\u043e\u0432\u0435\u043d",
"actions_table_header": "\u0414\u0435\u0439\u0441\u0442\u0432\u0438\u044f",
"delete_table_action": "\u0418\u0437\u0442\u0440\u0438\u0439",
"filters_and_hosts": "\u0427\u0435\u0440\u043d\u0438 \u0441\u043f\u0438\u0441\u044a\u0446\u0438 \u0441 \u043e\u0431\u0449\u0438 \u0438 \u043c\u0435\u0441\u0442\u043d\u0438 \u0444\u0438\u043b\u0442\u0440\u0438",
"filters_and_hosts_hint": "AdGuard Home \u0440\u0430\u0437\u0431\u0438\u0440\u0430 adblock \u0438 host \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0441.",
"no_filters_added": "\u041d\u044f\u043c\u0430 \u0434\u043e\u0431\u0430\u0432\u0435\u043d\u0438 \u0444\u0438\u043b\u0442\u0440\u0438",
"add_filter_btn": "\u0414\u043e\u0431\u0430\u0432\u0438 \u0444\u0438\u043b\u0442\u044a\u0440",
"cancel_btn": "\u041e\u0442\u043a\u0430\u0436\u0438",
"enter_name_hint": "\u0412\u044a\u0432\u0435\u0434\u0438 \u0438\u043c\u0435",
"enter_url_hint": "\u0412\u044a\u0432\u0435\u0434\u0438 URL",
"check_updates_btn": "\u041f\u0440\u043e\u0432\u0435\u0440\u0438 \u0437\u0430 \u0430\u043a\u0442\u0443\u0430\u043b\u0438\u0437\u0430\u0446\u0438\u044f",
"new_filter_btn": "\u0412\u044a\u0432\u0435\u0434\u0438 \u043d\u043e\u0432 \u0444\u0438\u043b\u0442\u044a\u0440",
"enter_valid_filter_url": "\u041c\u043e\u043b\u044f \u0432\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u0432\u0430\u043b\u0438\u0434\u0435\u043d URL \u0437\u0430 \u0444\u0438\u043b\u0442\u044a\u0440\u0430 \u0438\u043b\u0438 \u043f\u0440\u043e\u0432\u0435\u0440\u0435\u0442\u0435 host \u043f\u0440\u0430\u0432\u043e\u043f\u0438\u0441\u0430.",
"custom_filter_rules": "\u041c\u0435\u0441\u0442\u043d\u0438 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0437\u0430 \u0444\u0438\u043b\u0442\u0440\u0438\u0440\u0430\u043d\u0435",
"custom_filter_rules_hint": "\u0412\u044a\u0432\u0435\u0436\u0434\u0430\u0439\u0442\u0435 \u0432\u0441\u044f\u043a\u043e \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u043d\u0430 \u043d\u043e\u0432 \u0440\u0435\u0434. \u041c\u043e\u0436\u0435 \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 adblock \u0438\u043b\u0438 hosts \u0444\u0430\u0439\u043b\u043e\u0432 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0441.",
"examples_title": "\u041f\u0440\u0438\u043c\u0435\u0440\u0438",
"example_meaning_filter_block": "\u0411\u043b\u043e\u043a\u0438\u0440\u0430\u0439 \u0434\u043e\u0441\u0442\u044a\u043f \u0434\u043e \u0434\u043e\u043c\u0435\u0439\u043d example.org \u0438 \u0432\u0441\u0438\u0447\u043a\u0438 \u043f\u043e\u0434 \u0434\u043e\u043c\u0435\u0439\u043d\u0438.",
"example_meaning_filter_whitelist": "\u0420\u0430\u0437\u0440\u0435\u0448\u0438 \u0434\u043e\u0441\u0442\u044a\u043f \u0434\u043e \u0434\u043e\u043c\u0435\u0439\u043d example.org \u0438 \u0432\u0441\u0438\u0447\u043a\u0438\u0442\u0435 \u043c\u0443 \u043f\u043e\u0434 \u0434\u043e\u043c\u0435\u0439\u043d\u0438.",
"example_meaning_host_block": "AdGuard Home \u0449\u0435 \u043e\u0442\u0433\u043e\u0432\u043e\u0440\u0438 \u0441 127.0.0.1 = \u043f\u0440\u0430\u0437\u0435\u043d \u0430\u0434\u0440\u0435\u0441 \u0437\u0430 \u0434\u043e\u043c\u0435\u0439\u043d example.org (\u043d\u043e \u043d\u0435 \u0438 \u0437\u0430 \u043f\u043e\u0434 \u0434\u043e\u043c\u0435\u0439\u043d\u0438).",
"example_comment": "! \u0422\u043e\u0432\u0430 \u0435 \u043a\u043e\u043c\u0435\u043d\u0442\u0430\u0440",
"example_comment_meaning": "\u043f\u0440\u0438\u043c\u0435\u0440 \u0437\u0430 \u043a\u043e\u043c\u0435\u043d\u0442\u0430\u0440",
"example_comment_hash": "# \u0422\u043e\u0432\u0430 \u0435 \u0441\u044a\u0449\u043e \u043a\u043e\u043c\u0435\u043d\u0442\u0430\u0440",
"example_regex_meaning": "\u0411\u043b\u043e\u043a\u0438\u0440\u0430\u0439 \u0434\u043e\u0441\u0442\u044a\u043f \u0434\u043e \u0434\u043e\u043c\u0435\u0439\u043d\u0438 \u043a\u043e\u0439\u0442\u043e \u0441\u044a\u0432\u043f\u0430\u0434\u0430\u0442 \u0441\u044a\u0441 \u0441\u043b\u0435\u0434\u043d\u043e\u0442\u043e",
"example_upstream_regular": "\u043a\u043b\u0430\u0441\u0438\u0447\u0435\u0441\u043a\u0438 DNS (UDP \u043f\u0440\u043e\u0442\u043e\u043a\u043e\u043b)",
"example_upstream_dot": "\u043a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d <0>DNS-\u0432\u044a\u0440\u0445\u0443-TLS<\/0>",
"example_upstream_doh": "\u043a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d <0>DNS-\u0432\u044a\u0440\u0445\u0443-HTTPS<\/0>",
"example_upstream_sdns": "\u043c\u043e\u0436\u0435 \u0434\u0430 \u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 <0>DNS \u041f\u043e\u0434\u043f\u0438\u0441\u0432\u0430\u043d\u0435<\/0> \u0437\u0430 <1>DNSCrypt<\/1> \u0438\u043b\u0438 <2>DNS-\u0432\u044a\u0440\u0445\u0443-HTTPS<\/2> \u0441\u044a\u0440\u0432\u044a\u0440\u0438",
"example_upstream_tcp": "\u043a\u043b\u0430\u0441\u0438\u0447\u0435\u0441\u043a\u0438 DNS (TCP \u043f\u0440\u043e\u0442\u043e\u043a\u043e\u043b)",
"all_filters_up_to_date_toast": "\u0412\u0441\u0438\u0447\u043a\u0438 \u0444\u0438\u043b\u0442\u0438 \u0441\u0430 \u0430\u043a\u0442\u0443\u0430\u043b\u0438\u0437\u0438\u0440\u0430\u043d\u0438",
"updated_upstream_dns_toast": "\u0413\u043b\u043e\u0431\u0430\u043b\u043d\u0438\u0442\u0435 DNS \u0441\u044a\u0440\u0432\u044a\u0440\u0438 \u0441\u0430 \u043e\u0431\u043d\u043e\u0432\u0435\u043d\u0438",
"dns_test_ok_toast": "\u0412\u044a\u0432\u0435\u0434\u0435\u043d\u0438\u0442\u0435 DNS \u0441\u044a\u0440\u0432\u044a\u0440\u0438 \u0440\u0430\u0431\u043e\u0442\u044f\u0442 \u043a\u043e\u0440\u0435\u043a\u0442\u043d\u043e",
"dns_test_not_ok_toast": "\u0421\u044a\u0440\u0432\u044a\u0440 \"{{key}}\": \u043d\u0435 \u0440\u0430\u0431\u043e\u0442\u0438, \u043c\u043e\u043b\u044f \u043f\u0440\u043e\u0432\u0435\u0440\u0435\u0442\u0435 \u0434\u0430\u043b\u0438 \u0435 \u0432\u044a\u0432\u0435\u0434\u0435\u043d \u043a\u043e\u0440\u0435\u043a\u0442\u043d\u043e",
"unblock_btn": "\u041e\u0442\u0431\u043b\u043e\u043a\u0438\u0440\u0430\u0439",
"block_btn": "\u0411\u043b\u043e\u043a\u0438\u0440\u0430\u0439",
"time_table_header": "\u0412\u0440\u0435\u043c\u0435",
"domain_name_table_header": "\u0418\u043c\u0435 \u043d\u0430 \u0434\u043e\u043c\u0435\u0439\u043d",
"type_table_header": "\u0422\u0438\u043f",
"response_table_header": "\u041e\u0442\u0433\u043e\u0432\u043e\u0440",
"client_table_header": "\u041a\u043b\u0438\u0435\u043d\u0442",
"empty_response_status": "\u041f\u0440\u0430\u0437\u0435\u043d",
"show_all_filter_type": "\u041f\u043e\u043a\u0430\u0436\u0438 \u0432\u0441\u0438\u0447\u043a\u0438",
"show_filtered_type": "\u041f\u043e\u043a\u0430\u0436\u0438 \u0444\u0438\u043b\u0442\u0440\u0438\u0440\u0430\u043d\u0438",
"no_logs_found": "\u041d\u044f\u043c\u0430 \u0438\u0441\u0442\u043e\u0440\u0438\u044f",
"disabled_log_btn": "\u0417\u0430\u0431\u0440\u0430\u043d\u0438 \u0438\u0441\u0442\u043e\u0440\u0438\u044f\u0442\u0430",
"download_log_file_btn": "\u0421\u043c\u044a\u043a\u043d\u0438 \u0438\u0441\u0442\u043e\u0440\u0438\u044f\u0442\u0430",
"refresh_btn": "\u041e\u0431\u043d\u043e\u0432\u0438",
"enabled_log_btn": "\u0420\u0430\u0437\u0440\u0435\u0448\u0438 \u0438\u0441\u0442\u043e\u0440\u0438\u044f\u0442\u0430",
"last_dns_queries": "\u041f\u043e\u0441\u043b\u0435\u0434\u043d\u0438\u0442\u0435 5000 DNS \u0437\u0430\u044f\u0432\u043a\u0438",
"previous_btn": "\u041f\u0440\u0435\u0434\u0445\u043e\u0434\u0435\u043d",
"next_btn": "\u0421\u043b\u0435\u0434\u0432\u0430\u0449",
"loading_table_status": "\u0417\u0430\u0440\u0435\u0436\u0434\u0430\u043d\u0435...",
"page_table_footer_text": "\u0421\u0442\u0440\u0430\u043d\u0438\u0446\u0430",
"of_table_footer_text": "\u043e\u0442",
"rows_table_footer_text": "\u0440\u0435\u0434\u043e\u0432\u0435",
"updated_custom_filtering_toast": "\u041e\u0431\u043d\u043e\u0432\u0435\u043d\u0438 \u043c\u0435\u0441\u0442\u043d\u0438 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0437\u0430 \u0444\u0438\u043b\u0442\u0440\u0438\u0440\u0430\u043d\u0435",
"rule_removed_from_custom_filtering_toast": "\u041f\u0440\u0435\u043c\u0430\u0445\u043d\u0430\u0442\u043e \u043e\u0442 \u043c\u0435\u0441\u0442\u043d\u0438 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0437\u0430 \u0444\u0438\u043b\u0442\u0440\u0438\u0440\u0430\u043d\u0435",
"rule_added_to_custom_filtering_toast": "\u0414\u043e\u0431\u0430\u0432\u0435\u043d\u043e \u0434\u043e \u043c\u0435\u0441\u0442\u043d\u0438 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0437\u0430 \u0444\u0438\u043b\u0442\u0440\u0438\u0440\u0430\u043d\u0435",
"query_log_disabled_toast": "\u0418\u0441\u0442\u043e\u0440\u0438\u044f\u0442\u0430 \u0435 \u0437\u0430\u0431\u0440\u0430\u043d\u0435\u043d\u0430",
"query_log_enabled_toast": "\u0418\u0441\u0442\u043e\u0440\u0438\u044f\u0442\u0430 \u0435 \u0440\u0430\u0437\u0440\u0435\u0448\u0435\u043d\u0430",
"source_label": "\u0418\u0437\u0442\u043e\u0447\u043d\u0438\u043a",
"found_in_known_domain_db": "\u041d\u0430\u043c\u0435\u0440\u0435\u043d \u0432 \u0441\u043f\u0438\u0441\u044a\u0446\u0438\u0442\u0435 \u0441 \u0434\u043e\u043c\u0435\u0439\u043d\u0438.",
"category_label": "\u041a\u0430\u0442\u0435\u0433\u043e\u0440\u0438\u044f",
"rule_label": "\u041f\u0440\u0430\u0432\u0438\u043b\u043e",
"filter_label": "\u0424\u0438\u043b\u0442\u044a\u0440",
"unknown_filter": "\u041d\u0435\u043f\u043e\u0437\u043d\u0430\u0442 \u0444\u0438\u043b\u0442\u044a\u0440 {{filterId}}",
"install_welcome_title": "\u0414\u043e\u0431\u0440\u0435 \u0434\u043e\u0448\u043b\u0438 \u0432 AdGuard Home!",
"install_welcome_desc": "AdGuard Home e \u043c\u0440\u0435\u0436\u043e\u0432\u043e \u0440\u0435\u0448\u0435\u043d\u0438\u0435 \u0437\u0430 \u0431\u043b\u043e\u043a\u0438\u0440\u0430\u043d\u0435 \u043d\u0430 \u0440\u0435\u043a\u043b\u0430\u043c\u0438 \u0438 \u0442\u0440\u0430\u043a\u0435\u0440\u0438 \u043d\u0430 DNS \u043d\u0438\u0432\u043e. \u0421\u044a\u0437\u0434\u0430\u0434\u0435\u043d\u043e \u0435 \u0437\u0430 \u0434\u0430 \u0432\u0438 \u0434\u0430\u0434\u0435 \u043f\u044a\u043b\u0435\u043d \u043a\u043e\u043d\u0442\u0440\u043e\u043b \u043d\u0430\u0434 \u043c\u0440\u0435\u0436\u0430\u0442\u0430 \u0438 \u0432\u0441\u0438\u0447\u043a\u0438\u0442\u0435 \u0432\u0438 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430, \u0431\u0435\u0437 \u0434\u0430 \u0435 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e \u0434\u043e\u043f\u044a\u043b\u043d\u0438\u0442\u0435\u043b\u043d\u043e \u0438\u043d\u0441\u0442\u0430\u043b\u0438\u0440\u0430\u043d\u0435 \u043d\u0430 \u0434\u0440\u0443\u0433 \u0441\u043e\u0444\u0442\u0443\u0435\u0440.",
"install_settings_title": "\u0410\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f",
"install_settings_listen": "\u0410\u043a\u0442\u0438\u0432\u043d\u0438 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441\u0438",
"install_settings_port": "\u041f\u043e\u0440\u0442",
"install_settings_interface_link": "\u0412\u0430\u0448\u0430\u0442\u0430 AdGuard Home \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430 \u0437\u0430 \u0430\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f \u0449\u0435 \u0435 \u0434\u043e\u0441\u0442\u044a\u043f\u043d\u0430 \u043d\u0430 \u0442\u043e\u0437\u0438 \u0430\u0434\u0440\u0435\u0441:",
"form_error_port": "\u041c\u043e\u043b\u044f \u0432\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u0432\u0430\u043b\u0438\u0434\u0435\u043d \u043f\u043e\u0440\u0442",
"install_settings_dns": "DNS \u0441\u044a\u0440\u0432\u044a\u0440",
"install_settings_dns_desc": "\u0417\u0430 \u0434\u0430 \u0440\u0430\u0431\u043e\u0442\u0438, \u0449\u0435 \u0442\u0440\u044f\u0431\u0432\u0430 \u0434\u0430 \u043d\u0430\u0441\u0442\u0440\u043e\u0438\u0442\u0435 \u0432\u0430\u0448\u0438\u044f\u0442 \u0440\u0443\u0442\u0435\u0440 \u0438\u043b\u0438 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430 \u0434\u0430 \u043f\u043e\u043b\u0437\u0432\u0430\u0442 DNS \u0441\u044a\u0440\u0432\u044a\u0440 \u0441 \u0430\u0434\u0440\u0435\u0441:",
"install_settings_all_interfaces": "\u0412\u0441\u0438\u0447\u043a\u0438 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441\u0438",
"install_auth_title": "\u0423\u0434\u043e\u0441\u0442\u043e\u0432\u0435\u0440\u044f\u0432\u0430\u043d\u0435",
"install_auth_desc": "\u041c\u043d\u043e\u0433\u043e \u0435 \u0432\u0430\u0436\u043d\u043e \u0434\u0430 \u0437\u0430\u0434\u0430\u0434\u0435\u0442\u0435 \u0438\u043c\u0435 \u0438 \u043f\u0430\u0440\u043e\u043b\u0430 \u0437\u0430 \u0434\u043e\u0441\u0442\u044a\u043f \u0434\u043e \u0432\u0430\u0448\u0438\u044f \u043f\u0430\u043d\u0435\u043b \u0437\u0430 \u0430\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f \u043d\u0430 AdGuard Home. \u041f\u0440\u0435\u043f\u043e\u0440\u044a\u0447\u0432\u0430\u043c\u0435 \u0432\u0438 \u0434\u0430 \u0437\u0430\u0434\u0430\u0434\u0435\u0442\u0435 \u0438\u043c\u0435 \u0438 \u043f\u0430\u0440\u043e\u043b\u0430 \u043d\u0435\u0437\u0430\u0432\u0438\u0441\u0438\u043c\u043e \u0447\u0435 \u0433\u043e \u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 \u0441\u0430\u043c\u043e \u0432 \u043a\u044a\u0449\u0438.",
"install_auth_username": "\u041f\u043e\u0442\u0440\u0435\u0431\u0438\u0442\u0435\u043b",
"install_auth_password": "\u041f\u0430\u0440\u043e\u043b\u0430",
"install_auth_confirm": "\u041f\u043e\u0442\u0432\u044a\u0440\u0434\u0435\u0442\u0435 \u043f\u0430\u0440\u043e\u043b\u0430\u0442\u0430",
"install_auth_username_enter": "\u0412\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u043f\u043e\u0442\u0440\u0435\u0431\u0438\u0442\u0435\u043b",
"install_auth_password_enter": "\u0412\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u043f\u0430\u0440\u043e\u043b\u0430",
"install_step": "\u0421\u0442\u044a\u043f\u043a\u0430",
"install_devices_title": "\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u0442\u0435 \u0432\u0430\u0448\u0435\u0442\u043e \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u043e",
"install_devices_desc": "\u0414\u0430 \u0437\u0430\u043f\u043e\u0447\u043d\u0435\u0442\u0435 \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 AdGuard Home, \u0435 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e \u0434\u0430 \u043d\u0430\u0441\u0442\u0440\u043e\u0438\u0442\u0435 \u0432\u0430\u0448\u0438\u0442\u0435 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430.",
"install_submit_title": "\u041f\u043e\u0437\u0434\u0440\u0430\u0432\u043b\u0435\u043d\u0438\u044f!",
"install_submit_desc": "\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0430\u0442\u0430 \u0435 \u0437\u0430\u0432\u044a\u0440\u0448\u0435\u043d\u0430, \u043c\u043e\u0436\u0435 \u0434\u0430 \u0437\u0430\u043f\u043e\u0447\u043d\u0435\u0442\u0435 \u0434\u0430 \u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 AdGuard Home.",
"install_devices_router": "\u0420\u0443\u0442\u0435\u0440",
"install_devices_router_desc": "\u0410\u043a\u043e \u043d\u0430\u0441\u0442\u0440\u043e\u0438\u0442\u0435 \u0432\u0430\u0448\u0438\u044f\u0442 \u0440\u0443\u0442\u0435\u0440 \u043d\u044f\u043c\u0430 \u043d\u0443\u0436\u0434\u0430 \u0440\u044a\u0447\u043d\u043e \u0434\u0430 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u0432\u0430\u0442\u0435 \u0432\u0441\u044f\u043a\u043e \u0435\u0434\u043d\u043e \u043e\u0442 \u0443\u0441\u0442\u0440\u0439\u0441\u0442\u0432\u0430\u0442\u0430 \u0432 \u043c\u0440\u0435\u0436\u0430\u0442\u0430.",
"install_devices_address": "AdGuard Home DNS \u0441\u044a\u0440\u0432\u044a\u0440\u044a\u0442 \u0435 \u043d\u0430 \u0441\u043b\u0435\u0434\u043d\u0438\u044f \u0430\u0434\u0440\u0435\u0441",
"install_devices_router_list_1": "\u041e\u0442\u0432\u043e\u0440\u0435\u0442\u0435 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430\u0442\u0430 \u0437\u0430 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438 \u043d\u0430 \u0432\u0430\u0448\u0438\u044f \u0440\u0443\u0442\u0435\u0440. \u041e\u0431\u0438\u043a\u043d\u043e\u0432\u0435\u043d\u043e \u0442\u044f \u0441\u0435 \u043d\u0430\u043c\u0438\u0440\u0430 \u043d\u0430 URL (\u0442\u0443\u043a http:\/\/192.168.0.1\/ \u0438\u043b\u0438 \u0442\u0443\u043a http:\/\/192.168.1.1\/). \u0417\u0430 \u0434\u043e\u0441\u0442\u044a\u043f \u043c\u043e\u0436\u0435 \u0434\u0430 \u0432\u0438 \u0442\u0440\u044f\u0431\u0432\u0430 \u043f\u0430\u0440\u043e\u043b\u0430. \u0410\u043a\u043e \u0441\u0442\u0435 \u0437\u0430\u0431\u0440\u0430\u0432\u0438\u043b\u0438 \u043f\u0430\u0440\u043e\u043b\u0430\u0442\u0430 \u043c\u043e\u0436\u0435 \u0434\u0430 \u044f \u0440\u0435\u0441\u0435\u0442\u043d\u0435\u0442\u0435 \u043a\u0430\u0442\u043e \u043d\u0430\u0442\u0438\u0441\u043d\u0435\u0442\u0430 \u0441\u043a\u0440\u0438\u0442\u0438\u044f \u0440\u0435\u0441\u0435\u0442 \u0431\u0443\u0442\u043e\u043d - \u0432\u043d\u0438\u043c\u0430\u043d\u0438\u0435 \u0442\u043e\u0432\u0430 \u0449\u0435 \u0440\u0435\u0441\u0435\u0442\u043d\u0435 \u0432\u0441\u0438\u0447\u043a\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438 \u043d\u0430 \u0440\u0443\u0442\u0435\u0440\u0430 \u0434\u043e \u0444\u0430\u0431\u0440\u0438\u0447\u043d\u0438! \u041d\u044f\u043a\u043e\u0439 \u0440\u0443\u0442\u0435\u0440\u0438 \u043c\u043e\u0433\u0430\u0442 \u0434\u0430 \u0431\u044a\u0434\u0430\u0442\u0435 \u0430\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0438\u0440\u0430\u043d\u0438 \u043e\u0442 \u0441\u043e\u0444\u0442\u0443\u0435\u0440 \u0438\u043b\u0438 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0435, \u043a\u043e\u0439\u0442\u043e \u0431\u0438 \u0442\u0440\u044f\u0431\u0432\u0430\u043b\u043e \u0434\u0430 \u0435 \u0432\u0435\u0447\u0435 \u0438\u043d\u0441\u0442\u0430\u043b\u0438\u0440\u0430\u043d \u043d\u0430 \u043a\u043e\u043c\u043f\u044e\u0442\u044a\u0440\u0430\/\u0442\u0435\u043b\u0435\u0444\u043e\u043d\u0430 \u0432\u0438.",
"install_devices_router_list_2": "\u041d\u0430\u043c\u0435\u0440\u0435\u0442\u0430 DHCP\/DNS \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438. \u0412 \u043f\u043e\u0434 \u0440\u0430\u0437\u0434\u0435\u043b DHCP \u0440\u0437\u0433\u043b\u0435\u0434\u0430\u0439\u0442\u0435 \u0438 \u043d\u0430\u043c\u0435\u0440\u0435\u0442\u0435 \u043a\u044a\u0434\u0435 \u0435 \u043f\u043e\u043b\u0435\u0442\u043e \u0437\u0430 DNS \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0430 \u0432 \u043a\u043e\u0435\u0442\u043e \u043c\u043e\u0436\u0435 \u0434\u0430 \u0432\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u043f\u0435\u0440\u0441\u043e\u043d\u0430\u043b\u0438\u0437\u0438\u0440\u0430\u043d\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438 \u0437\u0430 DNS \u0441\u044a\u0440\u0432\u044a\u0440\u0438.",
"install_devices_router_list_3": "\u0412\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u0430\u0434\u0440\u0435\u0441\u044a\u0442 \u043d\u0430 AdGuard Home \u0441\u044a\u0440\u0432\u044a\u0440\u0430.",
"install_devices_windows_list_1": "\u041e\u0442\u0432\u043e\u0440\u0435\u0442\u0435 \u041a\u043e\u043d\u0442\u0440\u043e\u043b\u043d\u0438\u044f \u041f\u0430\u043d\u0435\u043b \u043f\u0440\u0435\u0437 \u0421\u0442\u0430\u0440\u0442 \u043c\u0435\u043d\u044e \u0438\u043b\u0438 \u0447\u0440\u0435\u0437 \u0444\u0443\u043d\u043a\u0446\u0438\u044f \u0442\u044a\u0440\u0441\u0435\u043d\u0435 \u043d\u0430 Windows.",
"install_devices_windows_list_2": "\u0412\u044a\u0440\u0432\u0435\u0442\u0435 \u0434\u043e \u041d\u0430\u0441\u0442\u0440\u0439\u043a\u0438 \u043d\u0430 \u041c\u0440\u0435\u0436\u0438 \u0438 \u0418\u043d\u0442\u0435\u0440\u043d\u0435\u0442 \u0438 \u043e\u0442 \u0442\u0430\u043c \u0438\u0437\u0431\u0435\u0440\u0435\u0442\u0435 \u041c\u0440\u0435\u0436\u0438 \u0438 \u0426\u0435\u043d\u0442\u044a\u0440 \u0437\u0430 \u0421\u043f\u043e\u0434\u0435\u043b\u044f\u043d\u0435.",
"install_devices_windows_list_3": "\u041e\u0442 \u043b\u044f\u0432\u043e \u043d\u0430 \u0435\u043a\u0440\u0430\u043d\u0430 \u043d\u0430\u043c\u0435\u0440\u0435\u0442\u0435 \u0421\u043c\u0435\u043d\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u043a\u0438 \u043d\u0430 \u043c\u0440\u0435\u0436\u043e\u0432\u0438\u044f \u0430\u0434\u0430\u043f\u0442\u0435\u0440 \u0438 \u043a\u043b\u0438\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 \u043d\u0435\u0433\u043e.",
"install_devices_windows_list_4": "\u0418\u0437\u0431\u0435\u0440\u0435\u0442\u0435 \u0442\u043e\u0437\u0438 \u043a\u043e\u0439\u0442\u043e \u0435 \u0430\u043a\u0442\u0438\u0432\u0435\u043d, \u0434\u044f\u0441\u043d\u043e-\u043a\u043b\u0438\u043a\u0432\u0430\u043d\u0435 \u0438 \u0438\u0437\u0431\u0435\u0440\u0435\u0442\u0430 \u0421\u0432\u043e\u0439\u0441\u0442\u0432\u0430.",
"install_devices_windows_list_5": "\u041d\u0430\u043c\u0435\u0440\u0435\u0442\u0435 \u0418\u043d\u0442\u0435\u0440\u043d\u0435\u0442 \u041f\u0440\u043e\u0442\u043e\u043a\u043e\u043b \u0412\u0435\u0440\u0441\u0438\u044f 4 (TCP\/IP) \u0432 \u0441\u043f\u0438\u0441\u044a\u043a\u0430, \u0438\u0437\u0431\u0435\u0440\u0435\u0442\u0435 \u0438 \u043a\u043b\u0438\u043a\u043d\u0435\u0442\u0435 \u043e\u0442\u043d\u043e\u0432\u043e \u043d\u0430 \u0421\u0432\u043e\u0439\u0441\u0442\u0432\u0430.",
"install_devices_windows_list_6": "\u0418\u0437\u0431\u0435\u0440\u0435\u0442\u0435 \u0418\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0439 \u0441\u043b\u0435\u0434\u043d\u0438\u0442\u0435 \u0430\u0434\u0440\u0435\u0441\u0438 \u0437\u0430 DNS \u0441\u044a\u0440\u0441\u044a\u0440\u0438 \u0438 \u0432\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u0430\u0434\u0440\u0435\u0441\u0430 \u043d\u0430 AdGuard Home \u0441\u044a\u0440\u0432\u044a\u0440\u0430 \u0432\u0438.",
"install_devices_macos_list_1": "\u0426\u044a\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 Apple \u0438\u043a\u043e\u043d\u043a\u0430\u0442\u0430 \u0438 \u0438\u0437\u0431\u0435\u0440\u0435\u0442\u0435 System Preferences...",
"install_devices_macos_list_2": "\u0426\u044a\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 Network.",
"install_devices_macos_list_3": "\u0418\u0437\u0431\u0435\u0440\u0435\u0442\u0435 \u0437\u0435\u043b\u0435\u043d\u0430\u0442\u0430-\u0430\u043a\u0442\u0438\u0432\u043d\u0430 \u0432\u0440\u044a\u0437\u043a\u0430 \u0432 \u0441\u043f\u0438\u0441\u044a\u043a\u0430 \u0438 \u043a\u043b\u0438\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 Advanced.",
"install_devices_macos_list_4": "\u0418\u0437\u0431\u0435\u0440\u0435\u0442\u0435 DNS \u0442\u0430\u0431 \u0438 \u043a\u043b\u0438\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 + \u0437\u0430 \u0434\u0430 \u0432\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u0430\u0434\u0440\u0435\u0441\u0430 \u043d\u0430 AdGuard Home \u0441\u044a\u0440\u0432\u044a\u0440\u0430.",
"install_devices_android_list_1": "\u0418\u0437\u0431\u0435\u0440\u0435\u0442\u0435 Android \u041c\u0435\u043d\u044e \u043e\u0442 \u0434\u043e\u043c\u0430\u0448\u043d\u0438\u044f \u0435\u043a\u0440\u0430\u043d, \u0438 \u0446\u044a\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 \u041d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438.",
"install_devices_android_list_2": "\u0426\u044a\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 Wi-Fi \u043c\u0435\u043d\u044e. \u041d\u0430 \u0435\u043a\u0440\u0430\u043d\u0430 \u0449\u0435 \u0441\u0435 \u043f\u043e\u044f\u0432\u0430\u0442 \u0432\u0441\u0438\u0447\u043a\u0438 \u0431\u0435\u0437\u0436\u0438\u0447\u043d\u0438 \u043f\u0440\u0435\u0436\u0438 (\u0442\u0430\u043c \u043d\u044f\u043c\u0430 \u0432\u044a\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442 \u0437\u0430 \u0432\u044a\u0432\u0435\u0436\u0434\u0430\u043d\u0435 \u043d\u0430 DNS \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438).",
"install_devices_android_list_3": "\u0426\u044a\u043a\u043d\u0435\u0442\u0435 \u0438 \u0437\u0430\u0434\u0440\u044a\u0436\u0434\u0435 \u0432\u044a\u0440\u0445\u0443 \u0412\u0438\u0435 \u0441\u0442\u0435 \u0441\u0432\u044a\u0440\u0437\u0430\u043d\u0438 \u0441.., \u0438 \u043a\u043b\u0438\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 \u041c\u043e\u0434\u0438\u0444\u0438\u0446\u0438\u0440\u0430\u0439 \u043c\u0440\u0435\u0436\u0430.",
"install_devices_android_list_4": "\u041d\u0430 \u043d\u044f\u043a\u043e\u0439 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430 \u043c\u043e\u0436\u0435 \u0434\u0430 \u0435 \u043d\u0435\u043e\u0445\u043e\u0434\u0438\u043c\u043e \u0434\u0430 \u043c\u0430\u0440\u043a\u0438\u0440\u0430\u0442\u0435 \u043f\u043e\u043a\u0430\u0436\u0438 \u0420\u0430\u0437\u0448\u0438\u0440\u0435\u043d\u0438, \u0437\u0430 \u0434\u0430 \u0432\u0438\u0434\u0438\u0442\u0435 \u0432\u0441\u0438\u0447\u043a\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438. \u0417\u0430 \u0434\u0430 \u043f\u0440\u043e\u043c\u0435\u043d\u0438\u0442\u0435 Android DNS \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438\u0442\u0435, \u043c\u043e\u0436\u0435 \u0434\u0430 \u0441\u0435 \u043d\u0430\u043b\u043e\u0436\u0438 \u0434\u0430 \u043f\u0440\u043e\u043c\u0435\u043d\u0438\u0442\u0435 IP \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438\u0442\u0435 \u043e\u0442 DHCP \u043d\u0430 \u0421\u0442\u0430\u0442\u0438\u0447\u043d\u0438.",
"install_devices_android_list_5": "\u041f\u0440\u043e\u043c\u0435\u043d\u0435\u0442\u0435 \u0441\u0442\u043e\u0439\u043d\u043e\u0441\u0442\u0438\u0442\u0435 \u043d\u0430 DNS 1 \u0438 DNS 2 \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442 AdGuard Home \u0441\u044a\u0440\u0432\u044a\u0440\u0430.",
"install_devices_ios_list_1": "\u041e\u0442 \u043d\u0430\u0447\u0430\u043b\u0435\u043d \u0435\u043a\u0440\u0430\u043d, \u0446\u044a\u043a\u043d\u0435\u0442\u0435 \u043d\u0430 Settings.",
"install_devices_ios_list_2": "\u0418\u0437\u0431\u0435\u0440\u0435\u0442\u0435 Wi-Fi \u043e\u0442 \u043b\u044f\u0432\u043e\u0442\u043e \u043c\u0435\u043d\u044e (\u0442\u0430\u043c \u043d\u044f\u043c\u0430 \u0432\u044a\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442 \u0437\u0430 \u0432\u044a\u0432\u0435\u0436\u0434\u0430\u043d\u0435 \u043d\u0430 DNS \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438).",
"install_devices_ios_list_3": "\u041a\u043b\u0438\u043d\u0435\u0442\u0435 \u043d\u0430 \u0438\u043c\u0435\u0442\u043e \u043d\u0430 \u0430\u043a\u0442\u0438\u0432\u043d\u0430\u0442\u0430 \u043c\u0440\u0435\u0436\u0430 \u043a\u044a\u043c \u043a\u043e\u044f\u0442\u043e \u0441\u0442\u0435 \u0441\u0432\u044a\u0440\u0437\u0430\u043d\u0438.",
"install_devices_ios_list_4": "\u0412 \u043f\u043e\u043b\u0435\u0442\u043e \u0437\u0430 DNS \u0438\u0437\u0431\u0435\u0440\u0435\u0442\u0435 \u0440\u044a\u0447\u043d\u043e \u0438 \u0432\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u0430\u0434\u0440\u0435\u0441\u0430 \u043d\u0430 AdGuard Home \u0441\u044a\u0440\u0432\u044a\u0440\u0430.",
"get_started": "\u0414\u0430 \u0437\u0430\u043f\u043e\u0447\u0432\u0430\u043c\u0435",
"next": "\u0421\u043b\u0435\u0434\u0432\u0430\u0449",
"open_dashboard": "\u041e\u0442\u0432\u043e\u0440\u0438 \u0442\u0430\u0431\u043b\u043e",
"install_saved": "\u0423\u0441\u043f\u0435\u0448\u043d\u043e \u0437\u0430\u043f\u0438\u0441\u0430\u043d\u043e",
"encryption_title": "\u041a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d\u0435",
"encryption_desc": "\u041f\u043e\u0434\u044a\u0440\u0436\u0430 \u0441\u0435 \u0441\u0438\u0433\u0443\u0440\u043d\u0430 \u0432\u0440\u044a\u0437\u043a\u0430 (HTTPS\/TLS) \u0432\u043a\u043b\u044e\u0447\u0438\u0442\u0435\u043b\u043d\u043e \u0437\u0430 DNS \u0438 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430\u0442\u0430 \u0437\u0430 \u0430\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f",
"encryption_config_saved": "\u041a\u043e\u043d\u0444\u0438\u0433\u0443\u0440\u0430\u0446\u0438\u044f\u0442\u0430 \u0435 \u0443\u0441\u043f\u0435\u0448\u043d\u043e \u0437\u0430\u043f\u0438\u0441\u0430\u043d\u0430",
"encryption_server": "\u0418\u043c\u0435 \u043d\u0430 \u0441\u044a\u0440\u0432\u044a\u0440\u0430",
"encryption_server_enter": "\u0412\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u0438\u043c\u0435 \u043d\u0430 \u0434\u043e\u043c\u0435\u0439\u043d\u0430",
"encryption_server_desc": "\u0417\u0430 \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 HTTPS, \u0442\u0440\u044f\u0431\u0432\u0430 \u0438\u043c\u0435\u0442\u043e \u043d\u0430 \u0441\u044a\u0440\u0432\u044a\u0440\u0430 \u0434\u0430 \u0441\u044a\u0432\u043f\u0430\u0434\u0430 \u0441 \u0442\u043e\u0432\u0430 \u043d\u0430 SSL \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u0430.",
"encryption_redirect": "\u0410\u0432\u0442\u043e\u043c\u0430\u0442\u0438\u0447\u043d\u043e \u043f\u0440\u0435\u043d\u0430\u0441\u043e\u0447\u0432\u0430\u043d\u0435 \u043a\u044a\u043c HTTPS",
"encryption_redirect_desc": "\u0421\u043b\u0443\u0436\u0438 \u0437\u0430 \u0430\u0432\u0442\u043e\u043c\u0430\u0442\u0438\u0447\u043d\u043e \u043f\u0440\u0435\u043d\u0430\u0441\u043e\u0447\u0432\u0430\u043d\u0435 \u043e\u0442 HTTP \u043a\u044a\u043c HTTPS \u043d\u0430 \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430\u0442\u0430 \u0437\u0430 \u0410\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f \u0432 AdGuard Home.",
"encryption_https": "HTTPS \u043f\u043e\u0440\u0442",
"encryption_https_desc": "\u0410\u043a\u043e \u0437\u0430\u0434\u0430\u0434\u0435\u0442\u0435 HTTPS \u043f\u043e\u0440\u0442, \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430\u0442\u0430 \u0437\u0430 \u0410\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f \u043d\u0430 AdGuard Home \u0449\u0435 \u0431\u044a\u0434\u0435 \u0434\u043e\u0441\u0442\u044a\u043f\u043d\u0430 \u043d\u0430 HTTPS, \u0438 \u0441\u044a\u0449\u043e \u0449\u0435 \u043e\u0442\u0433\u043e\u0432\u0430\u0440\u044f \u043d\u0430 DNS-\u0432\u044a\u0440\u0445\u0443-HTTPS '\/dns-\u0437\u0430\u043f\u0438\u0442\u0432\u0430\u043d\u0438\u044f'.",
"encryption_dot": "DNS-\u0432\u044a\u0440\u0445\u0443-TLS \u043f\u043e\u0440\u0442",
"encryption_dot_desc": "\u0410\u043a\u043e \u043f\u043e\u0440\u0442\u0430 \u0435 \u043a\u043e\u043d\u0444\u0438\u0433\u0443\u0440\u0438\u0440\u0430\u043d, AdGuard Home \u0449\u0435 \u0441\u0442\u0430\u0440\u0442\u0438\u0440\u0430 \u0438 \u0441\u044a\u0440\u0432\u044a\u0440 \u0437\u0430 DNS-\u0432\u044a\u0440\u0445\u0443-TLS.",
"encryption_certificates": "\u0421\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u0438",
"encryption_certificates_desc": "\u0417\u0430 \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 \u0441\u0438\u0433\u0443\u0440\u043d\u0430 \u0432\u0440\u044a\u0437\u043a\u0430, \u0449\u0435 \u0442\u0440\u044f\u0431\u0432\u0430 \u0434\u0430 \u043e\u0441\u0438\u0433\u0443\u0440\u0438\u0442\u0435 SSL \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u0438 \u0437\u0430 \u0432\u0430\u0448\u0438\u044f \u0434\u043e\u043c\u0435\u0439\u043d. \u041c\u043e\u0436\u0435 \u0434\u0430 \u0437\u0430\u044f\u0432\u0438\u0442\u0435 \u0431\u0435\u0437\u043f\u043b\u0430\u0442\u0435\u043d \u043e\u0442 <0>{{link}}<\/0> \u0438\u043b\u0438 \u0434\u0430 \u0437\u0430\u043a\u0443\u043f\u0438\u0442\u0435 \u043e\u0442 Certificate Authorities.",
"encryption_certificates_input": "\u041a\u043e\u043f\u0438\u0440\u0430\u0439\/\u043f\u043e\u0441\u0442\u0430\u0432\u0438 \u0432\u0430\u0448\u0438\u044f PEM-\u043a\u043e\u0434\u0438\u0440\u0430\u043d \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442 \u0442\u0443\u043a.",
"encryption_status": "\u0421\u044a\u0441\u0442\u043e\u044f\u043d\u0438\u0435",
"encryption_expire": "\u0413\u043e\u0434\u0435\u043d \u0434\u043e",
"encryption_key": "\u0427\u0430\u0441\u0442\u0435\u043d \u043a\u043b\u044e\u0447",
"encryption_key_input": "\u041a\u043e\u043f\u0438\u0440\u0430\u0439\/\u043f\u043e\u0441\u0442\u0430\u0432\u0438 \u0432\u0430\u0448\u0438\u044f PEM-\u043a\u043e\u0434\u0438\u0440\u0430\u043d \u0447p\u0430\u0441\u0442\u0435\u043d \u043a\u043b\u044e\u0447 \u0437\u0430 \u0432\u0430\u0448\u0438\u044f \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442 \u0442\u0443\u043a.",
"encryption_enable": "\u0420\u0430\u0437p\u0435\u0448\u0438 \u043a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d\u0435 (HTTPS, DNS-\u0432\u044a\u0440\u0445\u0443-HTTPS, \u0438 DNS-\u0432\u044a\u0440\u0445\u0443-TLS)",
"encryption_enable_desc": "\u0410\u043a\u043e \u0441\u0442\u0435 \u0440\u0430\u0437\u0440\u0435\u0448\u0438\u043b\u0438 \u043a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d\u0435, \u0441\u0442\u0440\u0430\u043d\u0438\u0446\u0430\u0442\u0430 \u0437\u0430 \u0410\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f \u043d\u0430 AdGuard Home \u0449\u0435 \u0431\u044a\u0434\u0435 \u0434\u043e\u0441\u0442\u044a\u043f\u043d\u0430 \u043f\u0440\u0435\u0437 HTTPS, \u0438 DNS \u0441\u044a\u0440\u0432\u044a\u0440\u0430 \u0449\u0435 \u043e\u0442\u0433\u043e\u0432\u0430\u0440\u044f \u0441\u044a\u0449\u043e \u043d\u0430 \u0437\u0430\u043f\u0438\u0442\u0432\u0430\u043d\u0438\u044f DNS-\u0432\u044a\u0440\u0445\u0443-HTTPS \u0438 DNS-\u0432\u044a\u0440\u0445\u0443-TLS.",
"encryption_chain_valid": "\u0419\u0435\u0440\u0430\u0440\u0445\u0438\u044f\u0442\u0430 \u043e\u0442 \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u0438 \u0435 \u0432\u0430\u043b\u0438\u0434\u043d\u0430",
"encryption_chain_invalid": "\u0419\u0435\u0440\u0430\u0440\u0445\u0438\u044f\u0442\u0430 \u043e\u0442 \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u0438 \u0435 \u043d\u0435\u0432\u0430\u043b\u0438\u0434\u043d\u0430",
"encryption_key_valid": "\u0422\u043e\u0432\u0430 \u0435 \u0432\u0430\u043b\u0438\u0434\u0435\u043d {{type}} \u0447\u0430\u0441\u0442\u0435\u043d \u043a\u043b\u044e\u0447",
"encryption_key_invalid": "\u0422\u043e\u0432\u0430 \u0435 \u043d\u0435\u0432\u0430\u043b\u0438\u0434\u0435\u043d {{type}} \u0447\u0430\u0441\u0442\u0435\u043d \u043a\u043b\u044e\u0447",
"encryption_subject": "\u0422\u0435\u043c\u0430",
"encryption_issuer": "\u0418\u0437\u043f\u044a\u043b\u043d\u0438\u0442\u0435\u043b",
"encryption_hostnames": "\u0418\u043c\u0435\u043d\u0430 \u043d\u0430 \u0445\u043e\u0441\u0442\u0430",
"encryption_reset": "\u0421\u0438\u0433\u0443\u0440\u043d\u0438 \u043b\u0438 \u0441\u0442\u0435 \u0447\u0435 \u0438\u0441\u043a\u0430\u0442\u0435 \u0434\u0430 \u0438\u0437\u0442\u0440\u0438\u0435\u0442\u0435 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438\u0442\u0435 \u0437\u0430 \u043a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d\u0435?",
"topline_expiring_certificate": "\u0412\u0430\u0448\u0438\u044f\u0442 SSL \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442 \u0438\u0437\u0442\u0438\u0447\u0430. \u041e\u0431\u043d\u043e\u0432\u0438 <0>\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438 \u0437\u0430 \u043a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d\u0435<\/0>.",
"topline_expired_certificate": "\u0412\u0430\u0448\u0438\u044f\u0442 SSL \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442 \u0435 \u0438\u0437\u0442\u0435\u043a\u044a\u043b. \u041e\u0431\u043d\u043e\u0432\u0438 <0>\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438 \u0437\u0430 \u043a\u0440\u0438\u043f\u0442\u0438\u0440\u0430\u043d\u0435<\/0>.",
"form_error_port_range": "\u0412\u044a\u0432\u0435\u0434\u0435\u0442\u0435 \u043f\u043e\u0440\u0442 \u0432 \u0434\u0438\u0430\u043f\u0430\u0437\u043e\u043d\u0430 80-65535",
"form_error_port_unsafe": "\u041d\u0435 \u0435 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0434\u0430 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430\u0442\u0435 \u0442\u043e\u0437\u0438 \u043f\u043e\u0440\u0442",
"form_error_equal": "\u041d\u0435 \u0442\u0440\u044f\u0431\u0432\u0430 \u0434\u0430 \u0441\u044a\u0432\u043f\u0430\u0434\u0430",
"form_error_password": "\u041f\u0430\u0440\u043e\u043b\u0430\u0442\u0430 \u043d\u0435 \u0441\u044a\u0432\u043f\u0430\u0434\u0430",
"reset_settings": "\u0418\u0437\u0442\u0440\u0438\u0439 \u0432\u0441\u0438\u0447\u043a\u0438 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438",
"update_announcement": "\u0418\u043c\u0430 \u043d\u043e\u0432\u0430 AdGuard Home {{version}}! <0>\u0426\u044a\u043a\u043d\u0438 \u0442\u0443\u043a<\/0> \u0437\u0430 \u043f\u043e\u0432\u0435\u0447\u0435 \u0438\u043d\u0444\u043e\u0440\u043c\u0430\u0446\u0438\u044f."
"url_added_successfully": "Успешно добавен URL",
"check_dhcp_servers": "Проверка за активен DHCP сървър",
"save_config": "Запиши настройките",
"enabled_dhcp": "DHCP е разрешен",
"disabled_dhcp": "DHCP е забранен",
"dhcp_title": "DHCP сървър (тестови!)",
"dhcp_description": "Ако рутера ви не раздава DHCP адреси, може да използвате вградения в AdGuard DHCP сървър.",
"dhcp_enable": "Рзреши DHCP сървъра",
"dhcp_disable": "Забрани DHCP сървъра",
"dhcp_not_found": "Вашата мрежа няма активен DHCP сървър. Безопасно е ползването на вградения DHCP сървър.",
"dhcp_found": "Вашата мрежа вече има активен DHCP сървър. Не е безопасно ползването на втори!",
"dhcp_leases": "DHCP раздадени адреси",
"dhcp_leases_not_found": "Няма намерени активни DHCP адреси",
"dhcp_config_saved": "Запиши конфигурацията на DHCP сървъра",
"form_error_required": "Задължително поле",
"form_error_ip_format": "Невалиден IPv4 адрес",
"form_error_positive": "Проверете дали е положително число",
"dhcp_form_gateway_input": "IP шлюз",
"dhcp_form_subnet_input": "Мрежова маска",
"dhcp_form_range_title": "Група от IP адреси",
"dhcp_form_range_start": "Първи адрес",
"dhcp_form_range_end": "Последен адрес",
"dhcp_form_lease_title": "Отдадени адреси (секунди)",
"dhcp_form_lease_input": "Отчет за раздадени адреси",
"dhcp_interface_select": "Изберете мрежов адаптер за DHCP",
"dhcp_hardware_address": "Хардуерни адреси (MAC)",
"dhcp_ip_addresses": "IP адреси",
"dhcp_table_hostname": "Име на устройство",
"dhcp_table_expires": "История",
"dhcp_warning": "Ако искате да използвате вградения DHCP сървър, трябва да няма друг активен DHCP в мрежата Ви!",
"back": "Назад",
"dashboard": "Табло",
"settings": "Настройки",
"filters": "Филтри",
"query_log": "История на заявките",
"faq": "ЧЗВ",
"version": "версия",
"address": "адрес",
"on": "ВКЛЮЧЕНО",
"off": "ИЗКЛЮЧЕНО",
"copyright": "Авторско право",
"homepage": "Домашна страница",
"report_an_issue": "Съобщи за проблем",
"enable_protection": "Разреши защита",
"enabled_protection": "Защитата е разрешена",
"disable_protection": "Забрани защита",
"disabled_protection": "Защитата е забранена",
"refresh_statics": "Обнови статистиката",
"dns_query": "DNS запитвания",
"blocked_by": "Блокирани от",
"stats_malware_phishing": "вируси/атаки",
"stats_adult": "сайтове за възрастни",
"stats_query_domain": "Най-отваряни страници",
"for_last_24_hours": "за последните 24 часа",
"no_domains_found": "Няма намерени резултати",
"requests_count": "Сума на заявките",
"top_blocked_domains": "Най-блокирани страници",
"top_clients": "Най-активни IP адреси",
"no_clients_found": "Нямa намерени адреси",
"general_statistics": "Обща статисика",
"number_of_dns_query_24_hours": "Сума на DNS заявки за последните 24 часа",
"number_of_dns_query_blocked_24_hours": "Сума на блокирани DNS заявки от филтрите за реклама и местни",
"number_of_dns_query_blocked_24_hours_by_sec": "Сума на блокирани DNS заявки от AdGuard свързани със сигурността",
"number_of_dns_query_blocked_24_hours_adult": "Сума на блокирани сайтове за възрастни",
"enforced_save_search": "Активирано Безопасно Търсене",
"number_of_dns_query_to_safe_search": "Сума на DNS заявки при който е приложено Безопасно Търсене",
"average_processing_time": "Средно време за обработка",
"average_processing_time_hint": "Средно време за обработка на DNS заявки в милисекунди",
"block_domain_use_filters_and_hosts": "Блокирани домейни - общи и местни филтри",
"filters_block_toggle_hint": "Може да зададете собствени настройки в <a href='#filters'>Филтри</a>.",
"use_adguard_browsing_sec": "Използвайте AdGuard модул за сигурността",
"use_adguard_browsing_sec_hint": "Модул Сигурност в AdGuard Home проверява всяка страница която отваряте дали е в черните списъци застрашаващи вашата сигурност. Използва се програмен интерфейс който защитава вашата анонимност и изпраща само SHA256 сума базирана на част от домейна който посещавате.",
"use_adguard_parental": "Включи AdGuard Родителски Надзор",
"use_adguard_parental_hint": "Модул XXX в AdGuard Home ще провери дали страницата има материали за възвъстни. Използва се същия API за анонимност като при модула за Сигурност.",
"enforce_safe_search": "Включи Безопасно Търсене",
"enforce_save_search_hint": "AdGuard Home прилага Безопасно Търсене в следните търсачки и сайтове: Google, Youtube, Bing, и Yandex.",
"no_servers_specified": "Няма избрани услуги",
"no_settings": "Няма настройки",
"general_settings": "Общи настройки",
"upstream_dns": "Главен DNS сървър",
"upstream_dns_hint": "Ако оставите празно, AdGuard Home ще използва <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> за главен. Използвай tls:// представка за DNS използващи TLS връзка.",
"test_upstream_btn": "Тествай главния DNS",
"apply_btn": "Приложи",
"disabled_filtering_toast": "Забрани филтрирането",
"enabled_filtering_toast": "Разреши фитрирането",
"disabled_safe_browsing_toast": "Забрани безопасно-сърфиране",
"enabled_safe_browsing_toast": "Рзреши безопасно-сърфиране",
"disabled_parental_toast": "Забрани Родителски Надзор",
"enabled_parental_toast": "Разреши Родителски Надзор",
"disabled_safe_search_toast": "Забрани Безопасно Търсене",
"enabled_save_search_toast": "Разреши Безопасно Търсене",
"enabled_table_header": "Разреши",
"name_table_header": "Име",
"filter_url_table_header": "URL филтър",
"rules_count_table_header": "Правила общо",
"last_time_updated_table_header": "Последно обновен",
"actions_table_header": "Действия",
"delete_table_action": "Изтрий",
"filters_and_hosts": "Черни списъци с общи и местни филтри",
"filters_and_hosts_hint": "AdGuard Home разбира adblock и host синтаксис.",
"no_filters_added": "Няма добавени филтри",
"add_filter_btn": "Добави филтър",
"cancel_btn": "Откажи",
"enter_name_hint": "Въведи име",
"enter_url_hint": "Въведи URL",
"check_updates_btn": "Провери за актуализация",
"new_filter_btn": "Въведи нов филтър",
"enter_valid_filter_url": "Моля въведете валиден URL за филтъра или проверете host правописа.",
"custom_filter_rules": "Местни правила за филтриране",
"custom_filter_rules_hint": "Въвеждайте всяко правило на нов ред. Може да използвате adblock или hosts файлов синтаксис.",
"examples_title": "Примери",
"example_meaning_filter_block": "Блокирай достъп до домейн example.org и всички под домейни.",
"example_meaning_filter_whitelist": "Разреши достъп до домейн example.org и всичките му под домейни.",
"example_meaning_host_block": "AdGuard Home ще отговори с 127.0.0.1 = празен адрес за домейн example.org (но не и за под домейни).",
"example_comment": "! Това е коментар",
"example_comment_meaning": "пример за коментар",
"example_comment_hash": "# Това е също коментар",
"example_upstream_regular": "класически DNS (UDP протокол)",
"example_upstream_dot": "криптиран <a href='https://en.wikipedia.org/wiki/DNS_over_TLS' target='_blank'>DNS-върху-TLS</a>",
"example_upstream_doh": "криптиран <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-върху-HTTPS</a>",
"example_upstream_sdns": "може да ползвате <a href='https://dnscrypt.info/stamps/' target='_blank'>DNS Подписване</a> за <a href='https://dnscrypt.info/' target='_blank'>DNSCrypt</a> или <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-върху-HTTPS</a> сървъри",
"example_upstream_tcp": "класически DNS (TCP протокол)",
"all_filters_up_to_date_toast": "Всички филти са актуализирани",
"updated_upstream_dns_toast": "Глобалните DNS сървъри са обновени",
"dns_test_ok_toast": "Въведените DNS сървъри работят коректно",
"dns_test_not_ok_toast": "Сървър \"{{key}}\": не работи, моля проверете дали е въведен коректно",
"unblock_btn": "Отблокирай",
"block_btn": "Блокирай",
"time_table_header": "Време",
"domain_name_table_header": "Име на домейн",
"type_table_header": "Тип",
"response_table_header": "Отговор",
"client_table_header": "Клиент",
"empty_response_status": "Празен",
"show_all_filter_type": "Покажи всички",
"show_filtered_type": "Покажи филтрирани",
"no_logs_found": "Няма история",
"disabled_log_btn": "Забрани историята",
"download_log_file_btn": "Смъкни историята",
"refresh_btn": "Обнови",
"enabled_log_btn": "Разреши историята",
"last_dns_queries": "Последните 5000 DNS заявки",
"previous_btn": "Предходен",
"next_btn": "Следващ",
"loading_table_status": "Зареждане...",
"page_table_footer_text": "Страница",
"of_table_footer_text": "от",
"rows_table_footer_text": "редове",
"updated_custom_filtering_toast": "Обновени местни правила за филтриране",
"rule_removed_from_custom_filtering_toast": "Премахнато от местни правила за филтриране",
"rule_added_to_custom_filtering_toast": "Добавено до местни правила за филтриране",
"query_log_disabled_toast": "Историята е забранена",
"query_log_enabled_toast": "Историята е разрешена",
"source_label": "Източник",
"found_in_known_domain_db": "Намерен в списъците с домейни.",
"category_label": "Категория",
"rule_label": "Правило",
"filter_label": "Филтър",
"unknown_filter": "Непознат филтър {{filterId}}",
"install_welcome_title": "Добре дошли в AdGuard Home!",
"install_welcome_desc": "AdGuard Home e мрежово решение за блокиране на реклами и тракери на DNS ниво. Създадено е за да ви даде пълен контрол над мрежата и всичките ви устройства, без да е необходимо допълнително инсталиране на друг софтуер.",
"install_settings_title": "Администрация",
"install_settings_listen": "Активни интерфейси",
"install_settings_port": "Порт",
"install_settings_interface_link": "Вашата AdGuard Home страница за администрация ще е достъпна на този адрес:",
"form_error_port": "Моля въведете валиден порт",
"install_settings_dns": "DNS сървър",
"install_settings_dns_desc": "За да работи, ще трябва да настроите вашият рутер или устройства да ползват DNS сървър с адрес:",
"install_settings_all_interfaces": "Всички интерфейси",
"install_auth_title": "Удостоверяване",
"install_auth_desc": "Много е важно да зададете име и парола за достъп до вашия панел за администрация на AdGuard Home. Препоръчваме ви да зададете име и парола независимо че го ползвате само в къщи.",
"install_auth_username": "Потребител",
"install_auth_password": "Парола",
"install_auth_confirm": "Потвърдете паролата",
"install_auth_username_enter": "Въведете потребител",
"install_auth_password_enter": "Въведете парола",
"install_step": "Стъпка",
"install_devices_title": "Настройте вашето устройство",
"install_devices_desc": "Да започнете да използвате AdGuard Home, е необходимо да настроите вашите устройства.",
"install_submit_title": "Поздравления!",
"install_submit_desc": "Настройката е завършена, може да започнете да ползвате AdGuard Home.",
"install_devices_router": "Рутер",
"install_devices_router_desc": "Ако настроите вашият рутер няма нужда ръчно да настройвате всяко едно от устрйствата в мрежата.",
"install_devices_address": "AdGuard Home DNS сървърът е на следния адрес",
"install_devices_router_list_1": "Отворете страницата за настройки на вашия рутер. Обикновено тя се намира на URL (тук http://192.168.0.1/ или тук http://192.168.1.1/). За достъп може да ви трябва парола. Ако сте забравили паролата може да я ресетнете като натиснета скрития ресет бутон - внимание това ще ресетне всички настройки на рутера до фабрични! Някой рутери могат да бъдате администрирани от софтуер или приложение, който би трябвало да е вече инсталиран на компютъра/телефона ви.",
"install_devices_router_list_2": "Намерета DHCP/DNS настройки. В под раздел DHCP рзгледайте и намерете къде е полето за DNS настройка в което може да въведете персонализирани настройки за DNS сървъри.",
"install_devices_router_list_3": "Въведете адресът на AdGuard Home сървъра.",
"install_devices_windows_list_1": "Отворете Контролния Панел през Старт меню или чрез функция търсене на Windows.",
"install_devices_windows_list_2": "Вървете до Настрйки на Мрежи и Интернет и от там изберете Мрежи и Център за Споделяне.",
"install_devices_windows_list_3": "От ляво на екрана намерете Смени настроки на мрежовия адаптер и кликнете на него.",
"install_devices_windows_list_4": "Изберете този който е активен, дясно-кликване и изберета Свойства.",
"install_devices_windows_list_5": "Намерете Интернет Протокол Версия 4 (TCP/IP) в списъка, изберете и кликнете отново на Свойства.",
"install_devices_windows_list_6": "Изберете Използвай следните адреси за DNS сърсъри и въведете адреса на AdGuard Home сървъра ви.",
"install_devices_macos_list_1": "Цъкнете на Apple иконката и изберете System Preferences...",
"install_devices_macos_list_2": "Цъкнете на Network.",
"install_devices_macos_list_3": "Изберете зелената-активна връзка в списъка и кликнете на Advanced.",
"install_devices_macos_list_4": "Изберете DNS таб и кликнете на + за да въведете адреса на AdGuard Home сървъра.",
"install_devices_android_list_1": "Изберете Android Меню от домашния екран, и цъкнете на Настройки.",
"install_devices_android_list_2": "Цъкнете на Wi-Fi меню. На екрана ще се появат всички безжични прежи (там няма възможност за въвеждане на DNS настройки).",
"install_devices_android_list_3": "Цъкнете и задръжде върху Вие сте свързани с.., и кликнете на Модифицирай мрежа.",
"install_devices_android_list_4": "На някой устройства може да е неоходимо да маркирате покажи Разширени, за да видите всички настройки. За да промените Android DNS настройките, може да се наложи да промените IP настройките от DHCP на Статични.",
"install_devices_android_list_5": "Променете стойностите на DNS 1 и DNS 2 да използват AdGuard Home сървъра.",
"install_devices_ios_list_1": "От начален екран, цъкнете на Settings.",
"install_devices_ios_list_2": "Изберете Wi-Fi от лявото меню (там няма възможност за въвеждане на DNS настройки).",
"install_devices_ios_list_3": "Клинете на името на активната мрежа към която сте свързани.",
"install_devices_ios_list_4": "В полето за DNS изберете ръчно и въведете адреса на AdGuard Home сървъра.",
"get_started": "Да започваме",
"next": "Следващ",
"open_dashboard": "Отвори табло",
"install_saved": "Успешно записано",
"encryption_title": "Криптиране",
"encryption_desc": "Подържа се сигурна връзка (HTTPS/TLS) включително за DNS и страницата за администрация",
"encryption_config_saved": "Конфигурацията е успешно записана",
"encryption_server": "Име на сървъра",
"encryption_server_enter": "Въведете име на домейна",
"encryption_server_desc": "За да използвате HTTPS, трябва името на сървъра да съвпада с това на SSL сертификата.",
"encryption_redirect": "Автоматично пренасочване към HTTPS",
"encryption_redirect_desc": "Служи за автоматично пренасочване от HTTP към HTTPS на страницата за Администрация в AdGuard Home.",
"encryption_https": "HTTPS порт",
"encryption_https_desc": "Ако зададете HTTPS порт, страницата за Администрация на AdGuard Home ще бъде достъпна на HTTPS, и също ще отговаря на DNS-върху-HTTPS '/dns-запитвания'.",
"encryption_dot": "DNS-върху-TLS порт",
"encryption_dot_desc": "Ако порта е конфигуриран, AdGuard Home ще стартира и сървър за DNS-върху-TLS.",
"encryption_certificates": "Сертификати",
"encryption_certificates_desc": "За да използвате сигурна връзка, ще трябва да осигурите SSL сертификати за вашия домейн. Може да заявите безплатен от <0>{{link}}</0> или да закупите от Certificate Authorities.",
"encryption_certificates_input": "Копирай/постави вашия PEM-кодиран сертификат тук.",
"encryption_status": "Състояние",
"encryption_expire": "Годен до",
"encryption_key": "Частен ключ",
"encryption_key_input": "Копирай/постави вашия PEM-кодиран чpастен ключ за вашия сертификат тук.",
"encryption_enable": "Разpеши криптиране (HTTPS, DNS-върху-HTTPS, и DNS-върху-TLS)",
"encryption_enable_desc": "Ако сте разрешили криптиране, страницата за Администрация на AdGuard Home ще бъде достъпна през HTTPS, и DNS сървъра ще отговаря също на запитвания DNS-върху-HTTPS и DNS-върху-TLS.",
"encryption_chain_valid": "Йерархията от сертификати е валидна",
"encryption_chain_invalid": "Йерархията от сертификати е невалидна",
"encryption_key_valid": "Това е валиден {{type}} частен ключ",
"encryption_key_invalid": "Това е невалиден {{type}} частен ключ",
"encryption_subject": "Тема",
"encryption_issuer": "Изпълнител",
"encryption_hostnames": "Имена на хоста",
"encryption_reset": "Сигурни ли сте че искате да изтриете настройките за криптиране?",
"topline_expiring_certificate": "Вашият SSL сертификат изтича. Обнови <0>Настройки за криптиране</0>.",
"topline_expired_certificate": "Вашият SSL сертификат е изтекъл. Обнови <0>Настройки за криптиране</0>.",
"form_error_port_range": "Въведете порт в диапазона 80-65535",
"form_error_port_unsafe": "Не е безопасно да използвате този порт",
"form_error_equal": "Не трябва да съвпада",
"form_error_password": "Паролата не съвпада",
"reset_settings": "Изтрий всички настройки",
"update_announcement": "Има нова AdGuard Home {{version}}! <0>Цъкни тук</0> за повече информация."
}

View File

@@ -1,8 +1,9 @@
{
"example_upstream_reserved": "you can specify DNS upstream <0>for a specific domain(s)<\/0>",
"client_settings": "Client settings",
"example_upstream_reserved": "you can specify DNS upstream <0>for a specific domain(s)</0>",
"upstream_parallel": "Use parallel queries to speed up resolving by simultaneously querying all upstream servers",
"bootstrap_dns": "Bootstrap DNS servers",
"bootstrap_dns_desc": "Bootstrap DNS servers are used to resolve IP addresses of the DoH\/DoT resolvers you specify as upstreams.",
"bootstrap_dns_desc": "Bootstrap DNS servers are used to resolve IP addresses of the DoH/DoT resolvers you specify as upstreams.",
"url_added_successfully": "URL added successfully",
"check_dhcp_servers": "Check for DHCP servers",
"save_config": "Save config",
@@ -15,10 +16,12 @@
"dhcp_not_found": "It is safe to enable the built-in DHCP server - we didn't find any active DHCP servers on the network. However, we encourage you to re-check it manually as our automatic test currently doesn't give 100% guarantee.",
"dhcp_found": "An active DHCP server is found on the network. It is not safe to enable the built-in DHCP server.",
"dhcp_leases": "DHCP leases",
"dhcp_static_leases": "DHCP static leases",
"dhcp_leases_not_found": "No DHCP leases found",
"dhcp_config_saved": "Saved DHCP server config",
"form_error_required": "Required field",
"form_error_ip_format": "Invalid IPv4 format",
"form_error_mac_format": "Invalid MAC format",
"form_error_positive": "Must be greater than 0",
"dhcp_form_gateway_input": "Gateway IP",
"dhcp_form_subnet_input": "Subnet mask",
@@ -36,6 +39,13 @@
"dhcp_error": "We could not determine whether there is another DHCP server in the network.",
"dhcp_static_ip_error": "In order to use DHCP server a static IP address must be set. We failed to determine if this network interface is configured using static IP address. Please set a static IP address manually.",
"dhcp_dynamic_ip_found": "Your system uses dynamic IP address configuration for interface <0>{{interfaceName}}</0>. In order to use DHCP server a static IP address must be set. Your current IP address is <0>{{ipAddress}}</0>. We will automatically set this IP address as static if you press Enable DHCP button.",
"dhcp_lease_added": "Static lease \"{{key}}\" successfully added",
"dhcp_lease_deleted": "Static lease \"{{key}}\" successfully deleted",
"dhcp_new_static_lease": "New static lease",
"dhcp_static_leases_not_found": "No DHCP static leases found",
"dhcp_add_static_lease": "Add static lease",
"delete_confirm": "Are you sure you want to delete \"{{key}}\"?",
"form_enter_hostname": "Enter hostname",
"error_details": "Error details",
"back": "Back",
"dashboard": "Dashboard",
@@ -43,7 +53,7 @@
"filters": "Filters",
"query_log": "Query Log",
"faq": "FAQ",
"version": "version",
"version": "Version",
"address": "address",
"on": "ON",
"off": "OFF",
@@ -58,7 +68,7 @@
"refresh_statics": "Refresh statistics",
"dns_query": "DNS Queries",
"blocked_by": "Blocked by Filters",
"stats_malware_phishing": "Blocked malware\/phishing",
"stats_malware_phishing": "Blocked malware/phishing",
"stats_adult": "Blocked adult websites",
"stats_query_domain": "Top queried domains",
"for_last_24_hours": "for the last 24 hours",
@@ -77,7 +87,7 @@
"average_processing_time": "Average processing time",
"average_processing_time_hint": "Average time in milliseconds on processing a DNS request",
"block_domain_use_filters_and_hosts": "Block domains using filters and hosts files",
"filters_block_toggle_hint": "You can setup blocking rules in the <a href='#filters'>Filters<\/a> settings.",
"filters_block_toggle_hint": "You can setup blocking rules in the <a href='#filters'>Filters</a> settings.",
"use_adguard_browsing_sec": "Use AdGuard browsing security web service",
"use_adguard_browsing_sec_hint": "AdGuard Home will check if domain is blacklisted by the browsing security web service. It will use privacy-friendly lookup API to perform the check: only a short prefix of the domain name SHA256 hash is sent to the server.",
"use_adguard_parental": "Use AdGuard parental control web service",
@@ -87,8 +97,11 @@
"no_servers_specified": "No servers specified",
"no_settings": "No settings",
"general_settings": "General settings",
"dns_settings": "DNS settings",
"encryption_settings": "Encryption settings",
"dhcp_settings": "DHCP settings",
"upstream_dns": "Upstream DNS servers",
"upstream_dns_hint": "If you keep this field empty, AdGuard Home will use <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> as an upstream.",
"upstream_dns_hint": "If you keep this field empty, AdGuard Home will use <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> as an upstream.",
"test_upstream_btn": "Test upstreams",
"apply_btn": "Apply",
"disabled_filtering_toast": "Disabled filtering",
@@ -105,6 +118,7 @@
"rules_count_table_header": "Rules count",
"last_time_updated_table_header": "Last time updated",
"actions_table_header": "Actions",
"edit_table_action": "Edit",
"delete_table_action": "Delete",
"filters_and_hosts": "Filters and hosts blocklists",
"filters_and_hosts_hint": "AdGuard Home understands basic adblock rules and hosts files syntax.",
@@ -125,11 +139,11 @@
"example_comment": "! Here goes a comment",
"example_comment_meaning": "just a comment",
"example_comment_hash": "# Also a comment",
"example_regex_meaning": "block access to the domains matching the specified regular expression",
"example_regex_meaning": "block access to the domains matching the <0>specified regular expression</0>",
"example_upstream_regular": "regular DNS (over UDP)",
"example_upstream_dot": "encrypted <0>DNS-over-TLS<\/0>",
"example_upstream_doh": "encrypted <0>DNS-over-HTTPS<\/0>",
"example_upstream_sdns": "you can use <0>DNS Stamps<\/0> for <1>DNSCrypt<\/1> or <2>DNS-over-HTTPS<\/2> resolvers",
"example_upstream_dot": "encrypted <0>DNS-over-TLS</0>",
"example_upstream_doh": "encrypted <0>DNS-over-HTTPS</0>",
"example_upstream_sdns": "you can use <0>DNS Stamps</0> for <1>DNSCrypt</1> or <2>DNS-over-HTTPS</2> resolvers",
"example_upstream_tcp": "regular DNS (over TCP)",
"all_filters_up_to_date_toast": "All filters are already up-to-date",
"updated_upstream_dns_toast": "Updated the upstream DNS servers",
@@ -187,20 +201,20 @@
"install_auth_password_enter": "Enter password",
"install_step": "Step",
"install_devices_title": "Configure your devices",
"install_devices_desc": "In order for AdGuard Home to start working, you need to configure your devices to use it.",
"install_devices_desc": "To start using AdGuard Home, you need to configure your devices to use it.",
"install_submit_title": "Congratulations!",
"install_submit_desc": "The setup procedure is finished and you are ready to start using AdGuard Home.",
"install_devices_router": "Router",
"install_devices_router_desc": "This setup will automatically cover all the devices connected to your home router and you will not need to configure each of them manually.",
"install_devices_address": "AdGuard Home DNS server is listening to the following addresses",
"install_devices_router_list_1": "Open the preferences for your router. Usually, you can access it from your browser via a URL (like http:\/\/192.168.0.1\/ or http:\/\/192.168.1.1\/). You may be asked to enter the password. If you don't remember it, you can often reset the password by pressing a button on the router itself. Some routers require a specific application, which in that case should be already installed on your computer\/phone.",
"install_devices_router_list_2": "Find the DHCP\/DNS settings. Look for the DNS letters next to a field which allows two or three sets of numbers, each broken into four groups of one to three digits.",
"install_devices_address": "AdGuard Home DNS server is listening on the following addresses",
"install_devices_router_list_1": "Open the preferences for your router. Usually, you can access it from your browser via a URL (like http://192.168.0.1/ or http://192.168.1.1/). You may be asked to enter the password. If you don't remember it, you can often reset the password by pressing a button on the router itself. Some routers require a specific application, which in that case should be already installed on your computer/phone.",
"install_devices_router_list_2": "Find the DHCP/DNS settings. Look for the DNS letters next to a field which allows two or three sets of numbers, each broken into four groups of one to three digits.",
"install_devices_router_list_3": "Enter your AdGuard Home server addresses there.",
"install_devices_windows_list_1": "Open Control Panel through Start menu or Windows search.",
"install_devices_windows_list_2": "Go to Network and Internet category and then to Network and Sharing Center.",
"install_devices_windows_list_3": "On the left side of the screen find Change adapter settings and click on it.",
"install_devices_windows_list_4": "Select your active connection, right-click on it and choose Properties.",
"install_devices_windows_list_5": "Find Internet Protocol Version 4 (TCP\/IP) in the list, select it and then click on Properties again.",
"install_devices_windows_list_5": "Find Internet Protocol Version 4 (TCP/IP) in the list, select it and then click on Properties again.",
"install_devices_windows_list_6": "Choose Use the following DNS server addresses and enter your AdGuard Home server addresses.",
"install_devices_macos_list_1": "Click on Apple icon and go to System Preferences.",
"install_devices_macos_list_2": "Click on Network.",
@@ -220,7 +234,7 @@
"open_dashboard": "Open Dashboard",
"install_saved": "Saved successfully",
"encryption_title": "Encryption",
"encryption_desc": "Encryption (HTTPS\/TLS) support for both DNS and admin web interface",
"encryption_desc": "Encryption (HTTPS/TLS) support for both DNS and admin web interface",
"encryption_config_saved": "Encryption config saved",
"encryption_server": "Server name",
"encryption_server_enter": "Enter your domain name",
@@ -228,16 +242,16 @@
"encryption_redirect": "Redirect to HTTPS automatically",
"encryption_redirect_desc": "If checked, AdGuard Home will automatically redirect you from HTTP to HTTPS addresses.",
"encryption_https": "HTTPS port",
"encryption_https_desc": "If HTTPS port is configured, AdGuard Home admin interface will be accessible via HTTPS, and it will also provide DNS-over-HTTPS on '\/dns-query' location.",
"encryption_https_desc": "If HTTPS port is configured, AdGuard Home admin interface will be accessible via HTTPS, and it will also provide DNS-over-HTTPS on '/dns-query' location.",
"encryption_dot": "DNS-over-TLS port",
"encryption_dot_desc": "If this port is configured, AdGuard Home will run a DNS-over-TLS server on this port.",
"encryption_certificates": "Certificates",
"encryption_certificates_desc": "In order to use encryption, you need to provide a valid SSL certificates chain for your domain. You can get a free certificate on <0>{{link}}<\/0> or you can buy it from one of the trusted Certificate Authorities.",
"encryption_certificates_input": "Copy\/paste your PEM-encoded certificates here.",
"encryption_certificates_desc": "In order to use encryption, you need to provide a valid SSL certificates chain for your domain. You can get a free certificate on <0>{{link}}</0> or you can buy it from one of the trusted Certificate Authorities.",
"encryption_certificates_input": "Copy/paste your PEM-encoded certificates here.",
"encryption_status": "Status",
"encryption_expire": "Expires",
"encryption_key": "Private key",
"encryption_key_input": "Copy\/paste your PEM-encoded private key for your certificate here.",
"encryption_key_input": "Copy/paste your PEM-encoded private key for your certificate here.",
"encryption_enable": "Enable Encryption (HTTPS, DNS-over-HTTPS, and DNS-over-TLS)",
"encryption_enable_desc": "If encryption is enabled, AdGuard Home admin interface will work over HTTPS, and the DNS server will listen for requests over DNS-over-HTTPS and DNS-over-TLS.",
"encryption_chain_valid": "Certificate chain is valid",
@@ -248,16 +262,96 @@
"encryption_issuer": "Issuer",
"encryption_hostnames": "Hostnames",
"encryption_reset": "Are you sure you want to reset encryption settings?",
"topline_expiring_certificate": "Your SSL certificate is about to expire. Update <0>Encryption settings<\/0>.",
"topline_expired_certificate": "Your SSL certificate is expired. Update <0>Encryption settings<\/0>.",
"topline_expiring_certificate": "Your SSL certificate is about to expire. Update <0>Encryption settings</0>.",
"topline_expired_certificate": "Your SSL certificate is expired. Update <0>Encryption settings</0>.",
"form_error_port_range": "Enter port value in the range of 80-65535",
"form_error_port_unsafe": "This is an unsafe port",
"form_error_equal": "Shouldn't be equal",
"form_error_password": "Password mismatched",
"reset_settings": "Reset settings",
"update_announcement": "AdGuard Home {{version}} is now available! <0>Click here<\/0> for more info.",
"update_announcement": "AdGuard Home {{version}} is now available! <0>Click here</0> for more info.",
"setup_guide": "Setup guide",
"dns_addresses": "DNS addresses",
"down": "Down",
"fix": "Fix"
"fix": "Fix",
"dns_providers": "Here is a <0>list of known DNS providers</0> to choose from.",
"update_now": "Update now",
"update_failed": "Auto-update failed. Please <a href='https://github.com/AdguardTeam/AdGuardHome/wiki/Getting-Started#update'>follow the steps</a> to update manually.",
"processing_update": "Please wait, AdGuard Home is being updated",
"clients_title": "Clients",
"clients_desc": "Configure devices connected to AdGuard Home",
"settings_global": "Global",
"settings_custom": "Custom",
"table_client": "Client",
"table_name": "Name",
"save_btn": "Save",
"client_add": "Add Client",
"client_new": "New Client",
"client_edit": "Edit Client",
"client_identifier": "Identifier",
"ip_address": "IP address",
"client_identifier_desc": "Clients can be identified by the IP address or MAC address. Please note, that using MAC as identifier is possible only if AdGuard Home is also a <0>DHCP server</0>",
"form_enter_ip": "Enter IP",
"form_enter_mac": "Enter MAC",
"form_client_name": "Enter client name",
"client_global_settings": "Use global settings",
"client_deleted": "Client \"{{key}}\" successfully deleted",
"client_added": "Client \"{{key}}\" successfully added",
"client_updated": "Client \"{{key}}\" successfully updated",
"table_statistics": "Requests count (last 24 hours)",
"clients_not_found": "No clients found",
"client_confirm_delete": "Are you sure you want to delete client \"{{key}}\"?",
"filter_confirm_delete": "Are you sure you want to delete filter?",
"auto_clients_title": "Clients (runtime)",
"auto_clients_desc": "Data on the clients that use AdGuard Home, but not stored in the configuration",
"access_title": "Access settings",
"access_desc": "Here you can configure access rules for the AdGuard Home DNS server.",
"access_allowed_title": "Allowed clients",
"access_allowed_desc": "A list of CIDR or IP addresses. If configured, AdGuard Home will accept requests from these IP addresses only.",
"access_disallowed_title": "Disallowed clients",
"access_disallowed_desc": "A list of CIDR or IP addresses. If configured, AdGuard Home will drop requests from these IP addresses.",
"access_blocked_title": "Blocked domains",
"access_blocked_desc": "Don't confuse this with filters. AdGuard Home will drop DNS queries with these domains in query's question.",
"access_settings_saved": "Access settings successfully saved",
"updates_checked": "Updates successfully checked",
"updates_version_equal": "AdGuard Home is up-to-date",
"check_updates_now": "Check for updates now",
"dns_privacy": "DNS Privacy",
"setup_dns_privacy_1": "<0>DNS-over-TLS:</0> Use <1>{{address}}</1> string.",
"setup_dns_privacy_2": "<0>DNS-over-HTTPS:</0> Use <1>{{address}}</1> string.",
"setup_dns_privacy_3": "<0>Please note that encrypted DNS protocols are supported only on Android 9. So you need to install additional software for other operating systems.</0><0>Here's a list of software you can use.</0>",
"setup_dns_privacy_android_1": "Android 9 supports DNS-over-TLS natively. To configure it, go to Settings → Network & internet → Advanced → Private DNS and enter your domain name there.",
"setup_dns_privacy_android_2": "<0>AdGuard for Android</0> supports <1>DNS-over-HTTPS</1> and <1>DNS-over-TLS</1>.",
"setup_dns_privacy_android_3": "<0>Intra</0> adds <1>DNS-over-HTTPS</1> support to Android.",
"setup_dns_privacy_ios_1": "<0>DNSCloak</0> supports <1>DNS-over-HTTPS</1>, but in order to configure it to use your own server, you'll need to generate a <2>DNS Stamp</2> for it.",
"setup_dns_privacy_ios_2": "<0>AdGuard for iOS</0> supports <1>DNS-over-HTTPS</1> and <1>DNS-over-TLS</1> setup.",
"setup_dns_privacy_other_title": "Other implementations",
"setup_dns_privacy_other_1": "AdGuard Home itself can be a secure DNS client on any platform.",
"setup_dns_privacy_other_2": "<0>dnsproxy</0> supports all known secure DNS protocols.",
"setup_dns_privacy_other_3": "<0>dnscrypt-proxy</0> supports <1>DNS-over-HTTPS</1>.",
"setup_dns_privacy_other_4": "<0>Mozilla Firefox</0> supports <1>DNS-over-HTTPS</1>.",
"setup_dns_privacy_other_5": "You will find more implementations <0>here</0> and <1>here</1>.",
"setup_dns_notice": "In order to use <1>DNS-over-HTTPS</1> or <1>DNS-over-TLS</1>, you need to <0>configure Encryption</0> in AdGuard Home settings.",
"rewrite_added": "DNS rewrite for \"{{key}}\" successfully added",
"rewrite_deleted": "DNS rewrite for \"{{key}}\" successfully deleted",
"rewrite_add": "Add DNS rewrite",
"rewrite_not_found": "No DNS rewrites found",
"rewrite_confirm_delete": "Are you sure you want to delete DNS rewrite for \"{{key}}\"?",
"rewrite_desc": "Allows to easily configure custom DNS response for a specific domain name.",
"rewrite_applied": "Applied Rewrite rule",
"dns_rewrites": "DNS rewrites",
"form_domain": "Enter domain",
"form_answer": "Enter IP address or domain name",
"form_error_domain_format": "Invalid domain format",
"form_error_answer_format": "Invalid answer format",
"configure": "Configure",
"main_settings": "Main settings",
"block_services": "Block specific services",
"blocked_services": "Blocked services",
"blocked_services_desc": "Allows to quickly block popular sites and services.",
"blocked_services_saved": "Blocked services successfully saved",
"blocked_services_global": "Use global blocked services",
"blocked_service": "Blocked service",
"block_all": "Block all",
"unblock_all": "Unblock all"
}

View File

@@ -1,135 +1,154 @@
{
"example_upstream_reserved": "puede especificar el DNS de subida <0>para un dominio espec\u00edfico<\/0>",
"upstream_parallel": "Usar consultas paralelas para acelerar la resoluci\u00f3n al consultar simult\u00e1neamente a todos los servidores de subida",
"client_settings": "Configuración de clientes",
"example_upstream_reserved": "puede especificar el DNS de subida <0>para un dominio específico</0>",
"upstream_parallel": "Usar consultas paralelas para acelerar la resolución al consultar simultáneamente a todos los servidores de subida",
"bootstrap_dns": "Servidores DNS de arranque",
"bootstrap_dns_desc": "Los servidores DNS de arranque se utilizan para resolver las direcciones IP de los resolutores DoH\/DoT que especifique como DNS de subida.",
"url_added_successfully": "URL a\u00f1adida correctamente",
"check_dhcp_servers": "Compruebe si hay servidores DHCP",
"save_config": "Guardar configuraci\u00f3n",
"bootstrap_dns_desc": "Los servidores DNS de arranque se utilizan para resolver las direcciones IP de los resolutores DoH/DoT que usted especifique como DNS de subida.",
"url_added_successfully": "URL añadida correctamente",
"check_dhcp_servers": "Comprobar si hay servidores DHCP",
"save_config": "Guardar configuración",
"enabled_dhcp": "Servidor DHCP habilitado",
"disabled_dhcp": "Servidor DHCP deshabilitado",
"dhcp_title": "Servidor DHCP (experimental)",
"dhcp_description": "Si su router no proporciona la configuraci\u00f3n DHCP, puede utilizar el propio servidor DHCP incorporado de AdGuard.",
"dhcp_description": "Si su router no proporciona la configuración DHCP, puede utilizar el propio servidor DHCP incorporado de AdGuard.",
"dhcp_enable": "Habilitar servidor DHCP",
"dhcp_disable": "Deshabilitar el servidor DHCP",
"dhcp_not_found": "No se han encontrado servidores DHCP activos en la red. Es seguro habilitar el servidor DHCP incorporado.",
"dhcp_found": "Algunos servidores DHCP activos se encuentran en la red. No es seguro habilitar el servidor DHCP incorporado.",
"dhcp_leases": "Concesi\u00f3nes DHCP",
"dhcp_leases_not_found": "No se encontraron concesi\u00f3nes DHCP",
"dhcp_config_saved": "Configuraci\u00f3n del servidor DHCP guardada",
"dhcp_disable": "Deshabilitar servidor DHCP",
"dhcp_not_found": "Es seguro habilitar el servidor DHCP incorporado. No se ha encontrado ningún servidor DHCP activo en la red, sin embargo le recomendamos que lo vuelva a comprobar manualmente, ya que nuestra prueba automática no ofrece actualmente una garantía del 100%.",
"dhcp_found": "Un servidor DHCP activo se encuentra en la red. No es seguro habilitar el servidor DHCP incorporado.",
"dhcp_leases": "Asignaciones DHCP",
"dhcp_static_leases": "Asignaciones DHCP estáticas",
"dhcp_leases_not_found": "No se han encontrado asignaciones DHCP",
"dhcp_config_saved": "Configuración del servidor DHCP guardada",
"form_error_required": "Campo obligatorio",
"form_error_ip_format": "Formato IPv4 no v\u00e1lido",
"form_error_ip_format": "Formato IPv4 no válido",
"form_error_mac_format": "Formato MAC no válido",
"form_error_positive": "Debe ser mayor que 0",
"dhcp_form_gateway_input": "IP de puerta de enlace",
"dhcp_form_subnet_input": "M\u00e1scara de subred",
"dhcp_form_subnet_input": "Máscara de subred",
"dhcp_form_range_title": "Rango de direcciones IP",
"dhcp_form_range_start": "Inicio de rango",
"dhcp_form_range_end": "Final de rango",
"dhcp_form_lease_title": "Tiempo de concesi\u00f3n DHCP (en segundos)",
"dhcp_form_lease_input": "Duraci\u00f3n de la concesi\u00f3n",
"dhcp_form_lease_title": "Tiempo de asignación DHCP (en segundos)",
"dhcp_form_lease_input": "Duración de asignación",
"dhcp_interface_select": "Seleccione la interfaz DHCP",
"dhcp_hardware_address": "Direcci\u00f3n MAC",
"dhcp_hardware_address": "Dirección MAC",
"dhcp_ip_addresses": "Direcciones IP",
"dhcp_table_hostname": "Nombre del host",
"dhcp_table_expires": "Expira",
"dhcp_warning": "Si desea habilitar el servidor DHCP incorporado, aseg\u00farese de que no hay otro servidor DHCP activo. \u00a1De lo contrario, puede dejar sin Internet a los dispositivos conectados!",
"back": "Atr\u00e1s",
"dhcp_warning": "Si de todos modos desea habilitar el servidor DHCP, asegúrese de que no hay otro servidor DHCP activo en su red. ¡De lo contrario, puede dejar sin Internet a los dispositivos conectados!",
"dhcp_error": "No pudimos determinar si hay otro servidor DHCP en la red.",
"dhcp_static_ip_error": "Para poder utilizar el servidor DHCP se debe establecer una dirección IP estática. No hemos podido determinar si esta interfaz de red está configurada utilizando una dirección IP estática. Por favor establezca una dirección IP estática manualmente.",
"dhcp_dynamic_ip_found": "Su sistema utiliza la configuración de dirección IP dinámica para la interfaz <0>{{interfaceName}}</0>. Para poder utilizar el servidor DHCP se debe establecer una dirección IP estática. Su dirección IP actual es <0>{{ipAddress}}</0>. Si presiona el botón Habilitar servidor DHCP, estableceremos automáticamente esta dirección IP como estática.",
"dhcp_lease_added": "Asignación estática \"{{key}}\" añadido correctamente",
"dhcp_lease_deleted": "Asignación estática \"{{key}}\" eliminado correctamente",
"dhcp_new_static_lease": "Nueva asignación estática",
"dhcp_static_leases_not_found": "No se han encontrado asignaciones DHCP estáticas",
"dhcp_add_static_lease": "Añadir asignación estática",
"delete_confirm": "¿Está seguro de que desea eliminar \"{{key}}\"?",
"form_enter_hostname": "Ingrese el nombre del host",
"error_details": "Detalles del error",
"back": "Atrás",
"dashboard": "Panel de control",
"settings": "Configuraci\u00f3n",
"settings": "Configuración",
"filters": "Filtros",
"query_log": "Registro de consultas",
"faq": "Preguntas frecuentes",
"version": "versi\u00f3n",
"address": "direcci\u00f3n",
"version": "Versión",
"address": "dirección",
"on": "Activado",
"off": "Desactivado",
"copyright": "Copyright",
"homepage": "P\u00e1gina de inicio",
"homepage": "Página de inicio",
"report_an_issue": "Reportar un error",
"enable_protection": "Habilitar protecci\u00f3n",
"enabled_protection": "Protecci\u00f3n habilitada",
"disable_protection": "Deshabilitar protecci\u00f3n",
"disabled_protection": "Protecci\u00f3n deshabilitada",
"refresh_statics": "Restablecer estad\u00edsticas",
"privacy_policy": "Política de privacidad",
"enable_protection": "Habilitar protección",
"enabled_protection": "Protección habilitada",
"disable_protection": "Deshabilitar protección",
"disabled_protection": "Protección deshabilitada",
"refresh_statics": "Restablecer estadísticas",
"dns_query": "Consultas DNS",
"blocked_by": "Bloqueado por filtros",
"stats_malware_phishing": "Malware\/phishing bloqueado",
"stats_adult": "Sitios para adultos bloqueado",
"stats_query_domain": "Dominios m\u00e1s consultados",
"for_last_24_hours": "en las \u00faltimas 24 horas",
"no_domains_found": "Dominios no encontrados",
"requests_count": "N\u00famero de solicitudes",
"top_blocked_domains": "Dominios m\u00e1s bloqueados",
"top_clients": "Clientes m\u00e1s frecuentes",
"no_clients_found": "No hay clientes",
"general_statistics": "Estad\u00edsticas generales",
"number_of_dns_query_24_hours": "N\u00famero de consultas DNS procesadas durante las \u00faltimas 24 horas",
"number_of_dns_query_blocked_24_hours": "N\u00famero de peticiones DNS bloqueadas por los filtros de publicidad y listas de bloqueo de hosts",
"number_of_dns_query_blocked_24_hours_by_sec": "N\u00famero de peticiones DNS bloqueadas por el m\u00f3dulo de navegaci\u00f3n segura de AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "N\u00famero de sitios para adultos bloqueado",
"enforced_save_search": "B\u00fasquedas seguras forzadas",
"number_of_dns_query_to_safe_search": "N\u00famero de peticiones DNS a los motores de b\u00fasqueda para los que se aplic\u00f3 la b\u00fasqueda segura forzada",
"stats_malware_phishing": "Malware/phishing bloqueado",
"stats_adult": "Sitios web para adultos bloqueado",
"stats_query_domain": "Dominios más consultados",
"for_last_24_hours": "en las últimas 24 horas",
"no_domains_found": "No se han encontrado dominios",
"requests_count": "Número de peticiones",
"top_blocked_domains": "Dominios más bloqueados",
"top_clients": "Clientes más frecuentes",
"no_clients_found": "No se han encontrado clientes",
"general_statistics": "Estadísticas generales",
"number_of_dns_query_24_hours": "Número de consultas DNS procesadas durante las últimas 24 horas",
"number_of_dns_query_blocked_24_hours": "Número de peticiones DNS bloqueadas por los filtros y listas de bloqueo de hosts",
"number_of_dns_query_blocked_24_hours_by_sec": "Número de peticiones DNS bloqueadas por el módulo de seguridad de navegación de AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "Número de sitios web para adultos bloqueado",
"enforced_save_search": "Búsquedas seguras forzadas",
"number_of_dns_query_to_safe_search": "Número de peticiones DNS a los motores de búsqueda para los que se aplicó la búsqueda segura forzada",
"average_processing_time": "Tiempo promedio de procesamiento",
"average_processing_time_hint": "Tiempo promedio en milisegundos al procesar una petici\u00f3n DNS",
"average_processing_time_hint": "Tiempo promedio en milisegundos al procesar una petición DNS",
"block_domain_use_filters_and_hosts": "Bloquear dominios usando filtros y archivos hosts",
"filters_block_toggle_hint": "Puede configurar las reglas de bloqueo en la configuraci\u00f3n de <a href='#filters'>filtros<\/a>.",
"use_adguard_browsing_sec": "Usar el servicio web de seguridad de navegaci\u00f3n de AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home comprobar\u00e1 si el dominio est\u00e1 en la lista negra del servicio web de seguridad de navegaci\u00f3n. Utilizar\u00e1 una API de b\u00fasqueda amigable con la privacidad para realizar la comprobaci\u00f3n: solo se env\u00eda al servidor un prefijo corto de hash del nombre de dominio SHA256.",
"filters_block_toggle_hint": "Puede configurar las reglas de bloqueo en la configuración de <a href='#filters'>filtros</a>.",
"use_adguard_browsing_sec": "Usar el servicio web de seguridad de navegación de AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home comprobará si el dominio está en la lista negra del servicio web de seguridad de navegación. Utilizará la API de búsqueda amigable con la privacidad para realizar la comprobación: solo se envía al servidor un prefijo corto del nombre de dominio con hash SHA256.",
"use_adguard_parental": "Usar el control parental de AdGuard",
"use_adguard_parental_hint": "AdGuard Home comprobar\u00e1 si el dominio contiene materiales para adultos. Utiliza la misma API amigable con la privacidad que el servicio web de seguridad de navegaci\u00f3n.",
"enforce_safe_search": "Forzar b\u00fasqueda segura",
"enforce_save_search_hint": "AdGuard Home puede forzar la b\u00fasqueda segura en los siguientes motores de b\u00fasqueda: Google, YouTube, Bing y Yandex.",
"use_adguard_parental_hint": "AdGuard Home comprobará si el dominio contiene materiales para adultos. Utiliza la misma API amigable con la privacidad del servicio web de seguridad de navegación.",
"enforce_safe_search": "Forzar búsqueda segura",
"enforce_save_search_hint": "AdGuard Home puede forzar la búsqueda segura en los siguientes motores de búsqueda: Google, YouTube, Bing, DuckDuckGo y Yandex.",
"no_servers_specified": "No hay servidores especificados",
"no_settings": "Sin configuraci\u00f3n",
"general_settings": "Configuraci\u00f3n general",
"no_settings": "Sin configuración",
"general_settings": "Configuración general",
"dns_settings": "Configuración del DNS",
"encryption_settings": "Configuración de cifrado",
"dhcp_settings": "Configuración DHCP",
"upstream_dns": "Servidores DNS de subida",
"upstream_dns_hint": "Si mantiene este campo vac\u00edo, AdGuard Home utilizar\u00e1 <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> como DNS de subida. Utilice el prefijo tls:\/\/ para los servidores DNS mediante TLS.",
"upstream_dns_hint": "Si mantiene este campo vacío, AdGuard Home utilizará <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> como DNS de subida. Utilice el prefijo tls:// para los servidores DNS mediante TLS.",
"test_upstream_btn": "Probar DNS de subida",
"apply_btn": "Aplicar",
"disabled_filtering_toast": "Filtrado deshabilitado",
"enabled_filtering_toast": "Filtrado habilitado",
"disabled_safe_browsing_toast": "B\u00fasqueda segura deshabilitada",
"enabled_safe_browsing_toast": "B\u00fasqueda segura habilitada",
"disabled_safe_browsing_toast": "Búsqueda segura deshabilitada",
"enabled_safe_browsing_toast": "Búsqueda segura habilitada",
"disabled_parental_toast": "Control parental deshabilitado",
"enabled_parental_toast": "Control parental habilitado",
"disabled_safe_search_toast": "B\u00fasqueda segura deshabilitada",
"enabled_save_search_toast": "B\u00fasqueda segura habilitada",
"disabled_safe_search_toast": "Búsqueda segura deshabilitada",
"enabled_save_search_toast": "Búsqueda segura habilitada",
"enabled_table_header": "Habilitado",
"name_table_header": "Nombre",
"filter_url_table_header": "URL del filtro",
"rules_count_table_header": "N\u00famero de reglas",
"last_time_updated_table_header": "\u00daltima actualizaci\u00f3n",
"rules_count_table_header": "Número de reglas",
"last_time_updated_table_header": "Última actualización",
"actions_table_header": "Acciones",
"edit_table_action": "Editar",
"delete_table_action": "Eliminar",
"filters_and_hosts": "Filtros y listas de bloqueo de hosts",
"filters_and_hosts_hint": "AdGuard Home entiende reglas b\u00e1sicas de bloqueo y la sintaxis de los archivos de hosts.",
"no_filters_added": "No hay filtros a\u00f1adidos",
"add_filter_btn": "A\u00f1adir filtro",
"filters_and_hosts_hint": "AdGuard Home entiende las reglas básicas de bloqueo y la sintaxis de los archivos hosts.",
"no_filters_added": "No hay filtros añadidos",
"add_filter_btn": "Añadir filtro",
"cancel_btn": "Cancelar",
"enter_name_hint": "Ingrese el nombre",
"enter_url_hint": "Ingrese la URL",
"check_updates_btn": "Buscar actualizaciones",
"new_filter_btn": "Nueva suscripci\u00f3n de filtro",
"enter_valid_filter_url": "Ingrese una URL v\u00e1lida para suscribirse o un archivo de hosts.",
"custom_filter_rules": "Personalizar reglas del filtrado",
"custom_filter_rules_hint": "Ingrese una regla en una l\u00ednea. Puede utilizar reglas de bloqueo de anuncios o la sintaxis de archivos de hosts.",
"new_filter_btn": "Nueva suscripción a filtro",
"enter_valid_filter_url": "Ingrese una URL válida para suscribirse a un filtro o archivo hosts.",
"custom_filter_rules": "Reglas de filtrado personalizado",
"custom_filter_rules_hint": "Ingrese una regla por línea. Puede utilizar reglas de bloqueo o la sintaxis de los archivos hosts.",
"examples_title": "Ejemplos",
"example_meaning_filter_block": "bloquea el acceso al dominio ejemplo.org\ny a todos sus subdominios",
"example_meaning_filter_whitelist": "desbloquea el acceso al dominio ejemplo.org y a todos sus subdominios",
"example_meaning_host_block": "AdGuard Home regresar\u00e1 la direcci\u00f3n 127.0.0.1 para el dominio ejemplo.org (pero no para sus subdominios).",
"example_comment": "! Aqu\u00ed va un comentario",
"example_meaning_host_block": "AdGuard Home regresará la dirección 127.0.0.1 para el dominio ejemplo.org (pero no para sus subdominios).",
"example_comment": "! Aquí va un comentario",
"example_comment_meaning": "solo un comentario",
"example_comment_hash": "# Tambi\u00e9n un comentario",
"example_regex_meaning": "bloquear el acceso a los dominios que coincidan con la expresi\u00f3n regular especificada",
"example_comment_hash": "# También un comentario",
"example_regex_meaning": "bloquear el acceso a los dominios que coincidan con la <0>expresión regular especificada</0>",
"example_upstream_regular": "DNS regular (mediante UDP)",
"example_upstream_dot": "cifrado <0>DNS mediante TLS<\/0>",
"example_upstream_doh": "cifrado <0>DNS mediante HTTPS<\/0>",
"example_upstream_sdns": "puedes usar <0>DNS Stamps<\/0> para <1>DNSCrypt<\/1> o resolutores <2>DNS mediante HTTPS<\/2>",
"example_upstream_dot": "cifrado <0>DNS mediante TLS</0>",
"example_upstream_doh": "cifrado <0>DNS mediante HTTPS</0>",
"example_upstream_sdns": "puedes usar <0>DNS Stamps</0> para <1>DNSCrypt</1> o resolutores <2>DNS mediante HTTPS</2>",
"example_upstream_tcp": "DNS regular (mediante TCP)",
"all_filters_up_to_date_toast": "Todos los filtros ya est\u00e1n actualizados",
"all_filters_up_to_date_toast": "Todos los filtros ya están actualizados",
"updated_upstream_dns_toast": "Servidores DNS de subida actualizados",
"dns_test_ok_toast": "Los servidores DNS especificados funcionan correctamente",
"dns_test_not_ok_toast": "Servidor \"{{key}}\": no puede ser usado, por favor, revise si lo ha escrito correctamente",
"dns_test_not_ok_toast": "Servidor \"{{key}}\": no se puede utilizar, por favor revise si lo ha escrito correctamente",
"unblock_btn": "Desbloquear",
"block_btn": "Bloquear",
"time_table_header": "Hora",
@@ -137,7 +156,7 @@
"type_table_header": "Tipo",
"response_table_header": "Respuesta",
"client_table_header": "Cliente",
"empty_response_status": "Vac\u00edo",
"empty_response_status": "Vacío",
"show_all_filter_type": "Mostrar todo",
"show_filtered_type": "Mostrar filtrados",
"no_logs_found": "No se han encontrado registros",
@@ -145,112 +164,194 @@
"download_log_file_btn": "Descargar archivo de registro",
"refresh_btn": "Actualizar",
"enabled_log_btn": "Habilitar registro",
"last_dns_queries": "\u00daltimas 5000 consultas DNS",
"previous_btn": "Atr\u00e1s",
"last_dns_queries": "Últimas 5000 consultas DNS",
"previous_btn": "Atrás",
"next_btn": "Siguiente",
"loading_table_status": "Cargando...",
"page_table_footer_text": "P\u00e1gina",
"page_table_footer_text": "Página",
"of_table_footer_text": "de",
"rows_table_footer_text": "filas",
"updated_custom_filtering_toast": "Reglas de filtrado personalizado actualizadas",
"rule_removed_from_custom_filtering_toast": "Regla eliminada de las reglas de filtrado personalizado",
"rule_added_to_custom_filtering_toast": "Regla a\u00f1adida a las reglas de filtrado personalizado",
"rule_added_to_custom_filtering_toast": "Regla añadida a las reglas de filtrado personalizado",
"query_log_disabled_toast": "Registro de consultas deshabilitado",
"query_log_enabled_toast": "Registro de consultas habilitado",
"source_label": "Fuente",
"found_in_known_domain_db": "Encontrado en la base de datos de dominios conocidos.",
"category_label": "Categor\u00eda",
"category_label": "Categoría",
"rule_label": "Regla",
"filter_label": "Filtro",
"unknown_filter": "Filtro desconocido {{filterId}}",
"install_welcome_title": "\u00a1Bienvenido a AdGuard Home!",
"install_welcome_desc": "AdGuard Home es un servidor DNS de bloqueo de anuncios y rastreadores en toda la red. Su prop\u00f3sito es permitirle controlar toda su red y todos sus dispositivos, y no requiere el uso de un programa del lado del cliente.",
"install_settings_title": "Interfaz web de administraci\u00f3n",
"install_welcome_title": "¡Bienvenido a AdGuard Home!",
"install_welcome_desc": "AdGuard Home es un servidor DNS para bloqueo de anuncios y rastreadores a nivel de red. Su propósito es permitirle controlar toda su red y todos sus dispositivos, y no requiere el uso de un programa del lado del cliente.",
"install_settings_title": "Interfaz web de administración",
"install_settings_listen": "Interfaz de escucha",
"install_settings_port": "Puerto",
"install_settings_interface_link": "Su interfaz web de administraci\u00f3n de AdGuard Home estar\u00e1 disponible en las siguientes direcciones:",
"form_error_port": "Ingrese un valor de puerto v\u00e1lido",
"install_settings_interface_link": "Su interfaz web de administración de AdGuard Home estará disponible en las siguientes direcciones:",
"form_error_port": "Ingrese un valor de puerto válido",
"install_settings_dns": "Servidor DNS",
"install_settings_dns_desc": "Deber\u00e1 configurar sus dispositivos o router para usar el servidor DNS en las siguientes direcciones:",
"install_settings_dns_desc": "Deberá configurar sus dispositivos o router para usar el servidor DNS en las siguientes direcciones:",
"install_settings_all_interfaces": "Todas las interfaces",
"install_auth_title": "Autenticaci\u00f3n",
"install_auth_desc": "Se recomienda encarecidamente configurar la autenticaci\u00f3n por contrase\u00f1a para la interfaz web del administraci\u00f3n de AdGuard Home. Incluso si solo es accesible en su red local, es importante que est\u00e9 protegido contra el acceso no autorizado.",
"install_auth_title": "Autenticación",
"install_auth_desc": "Se recomienda encarecidamente configurar la autenticación por contraseña para la interfaz web de administración de AdGuard Home. Incluso si solo es accesible en su red local, es importante que esté protegido contra el acceso no autorizado.",
"install_auth_username": "Usuario",
"install_auth_password": "Contrase\u00f1a",
"install_auth_confirm": "Confirmar contrase\u00f1a",
"install_auth_password": "Contraseña",
"install_auth_confirm": "Confirmar contraseña",
"install_auth_username_enter": "Ingrese su nombre de usuario",
"install_auth_password_enter": "Ingrese su contrase\u00f1a",
"install_auth_password_enter": "Ingrese su contraseña",
"install_step": "Paso",
"install_devices_title": "Configure sus dispositivos",
"install_devices_desc": "Para que AdGuard Home comience a funcionar, necesita configurar sus dispositivos para usarlo.",
"install_submit_title": "\u00a1Felicitaciones!",
"install_submit_desc": "El proceso de configuraci\u00f3n ha finalizado y est\u00e1 listo para comenzar a usar AdGuard Home.",
"install_devices_desc": "Para comenzar a utilizar AdGuard Home, debe configurar sus dispositivos para usarlo.",
"install_submit_title": "¡Felicitaciones!",
"install_submit_desc": "El proceso de configuración ha finalizado y está listo para comenzar a usar AdGuard Home.",
"install_devices_router": "Router",
"install_devices_router_desc": "Esta configuraci\u00f3n cubrir\u00e1 autom\u00e1ticamente todos los dispositivos conectados a su router dom\u00e9stico y no necesitar\u00e1 configurar cada uno de ellos manualmente.",
"install_devices_address": "El servidor DNS de AdGuard Home est\u00e1 escuchando las siguientes direcciones",
"install_devices_router_list_1": "Abra las preferencias de su router. Por lo general, puede acceder a \u00e9l desde su navegador a trav\u00e9s de una URL (como http:\/\/192.168.0.1\/ o http:\/\/192.168.1.1\/). Se le puede pedir que ingrese la contrase\u00f1a. Si no lo recuerda, a menudo puede restablecer la contrase\u00f1a presionando un bot\u00f3n en el router. Algunos routers requieren una aplicaci\u00f3n espec\u00edfica, que en ese caso ya deber\u00eda estar instalada en su computadora\/tel\u00e9fono.",
"install_devices_router_list_2": "Busque la configuraci\u00f3n de DHCP\/DNS. Busque las letras DNS junto a un campo que permita ingresar dos o tres grupos de n\u00fameros, cada uno dividido en cuatro grupos de uno a tres d\u00edgitos.",
"install_devices_router_list_3": "Ingrese las direcciones de su servidor AdGuard Home all\u00ed.",
"install_devices_windows_list_1": "Abra el Panel de control a trav\u00e9s del men\u00fa Inicio o en el buscador de Windows.",
"install_devices_windows_list_2": "Vaya a la categor\u00eda Red e Internet, luego al Centro de redes y recursos compartidos.",
"install_devices_windows_list_3": "En el lado izquierdo de la pantalla, busque Cambiar la configuraci\u00f3n del adaptador y haga clic en \u00e9l.",
"install_devices_windows_list_4": "Seleccione su conexi\u00f3n activa, luego haga clic derecho sobre ella y elija Propiedades.",
"install_devices_windows_list_5": "Busque el Protocolo de Internet versi\u00f3n 4 (TCP\/IP) en la lista, selecci\u00f3nelo y luego haga clic en Propiedades nuevamente.",
"install_devices_router_desc": "Esta configuración cubrirá automáticamente todos los dispositivos conectados a su router doméstico y no necesitará configurar cada uno de ellos manualmente.",
"install_devices_address": "El servidor DNS de AdGuard Home está escuchando en las siguientes direcciones",
"install_devices_router_list_1": "Abra las preferencias de su router. Por lo general, puede acceder a él desde su navegador a través de una URL (como http://192.168.0.1/ o http://192.168.1.1/). Se le puede pedir que ingrese la contraseña. Si no lo recuerda, a menudo puede restablecer la contraseña presionando un botón en el router. Algunos routers requieren una aplicación específica, que en ese caso ya debería estar instalada en su computadora/teléfono.",
"install_devices_router_list_2": "Busque la configuración de DHCP/DNS. Busque las letras DNS junto a un campo que permita ingresar dos o tres grupos de números, cada uno dividido en cuatro grupos de uno a tres dígitos.",
"install_devices_router_list_3": "Ingrese las direcciones de su servidor AdGuard Home allí.",
"install_devices_windows_list_1": "Abra el Panel de control a través del menú Inicio o en el buscador de Windows.",
"install_devices_windows_list_2": "Vaya a la categoría Redes e Internet, luego a Centro de redes y recursos compartidos.",
"install_devices_windows_list_3": "En el lado izquierdo de la pantalla, busque Cambiar configuración del adaptador y luego haga clic en él.",
"install_devices_windows_list_4": "Seleccione su conexión activa, haga clic derecho sobre ella y elija Propiedades.",
"install_devices_windows_list_5": "Busque en la lista el Protocolo de Internet versión 4 (TCP/IP), selecciónelo y vuelva a hacer clic en Propiedades.",
"install_devices_windows_list_6": "Elija Usar las siguientes direcciones de servidor DNS e ingrese las direcciones de su servidor AdGuard Home.",
"install_devices_macos_list_1": "Haga clic en el icono de Apple y vaya a Preferencias del sistema.",
"install_devices_macos_list_2": "Haga clic en Red.",
"install_devices_macos_list_3": "Seleccione la primera conexi\u00f3n de la lista y haga clic en Avanzado.",
"install_devices_macos_list_4": "Seleccione la pesta\u00f1a DNS e ingrese las direcciones de su servidor AdGuard Home.",
"install_devices_android_list_1": "En la pantalla de inicio del men\u00fa Android, pulse en Configuraci\u00f3n.",
"install_devices_android_list_2": "Pulse Wi-Fi en el men\u00fa. Aparecer\u00e1 la pantalla que lista todas las redes disponibles (es imposible configurar DNS personalizados para la conexi\u00f3n m\u00f3vil).",
"install_devices_android_list_3": "Mantenga presionada la red a la que est\u00e1 conectado y pulse Modificar red.",
"install_devices_android_list_4": "En algunos dispositivos, es posible que deba marcar la casilla Avanzado para ver m\u00e1s configuraciones. Para ajustar la configuraci\u00f3n DNS de su Android, deber\u00e1 cambiar la configuraci\u00f3n de IP de DHCP a Est\u00e1tica.",
"install_devices_macos_list_3": "Seleccione la primera conexión de la lista y haga clic en Avanzado.",
"install_devices_macos_list_4": "Seleccione la pestaña DNS e ingrese las direcciones de su servidor AdGuard Home.",
"install_devices_android_list_1": "En la pantalla de inicio del menú Android, pulse en Configuración.",
"install_devices_android_list_2": "Pulse Wi-Fi en el menú. Aparecerá la pantalla que lista todas las redes disponibles (es imposible configurar DNS personalizados para la conexión móvil).",
"install_devices_android_list_3": "Mantenga presionada la red a la que está conectado y pulse Modificar red.",
"install_devices_android_list_4": "En algunos dispositivos, es posible que deba marcar la casilla Avanzado para ver más configuraciones. Para ajustar la configuración DNS de su Android, deberá cambiar la configuración de IP de DHCP a Estática.",
"install_devices_android_list_5": "Cambie los valores de DNS 1 y DNS 2 a las direcciones de su servidor AdGuard Home.",
"install_devices_ios_list_1": "En la pantalla de inicio, pulse en Configuraci\u00f3n.",
"install_devices_ios_list_2": "Elija Wi-Fi en el men\u00fa de la izquierda (es imposible configurar DNS para redes m\u00f3viles).",
"install_devices_ios_list_1": "En la pantalla de inicio, pulse en Configuración.",
"install_devices_ios_list_2": "Elija Wi-Fi en el menú de la izquierda (es imposible configurar DNS para redes móviles).",
"install_devices_ios_list_3": "Pulse sobre el nombre de la red activa en ese momento.",
"install_devices_ios_list_4": "En ese campo DNS ingrese las direcciones de su servidor AdGuard Home.",
"install_devices_ios_list_4": "En el campo DNS ingrese las direcciones de su servidor AdGuard Home.",
"get_started": "Comenzar",
"next": "Siguiente",
"open_dashboard": "Abrir panel de control",
"install_saved": "Guardado correctamente",
"encryption_title": "Cifrado",
"encryption_desc": "Soporte para cifrado (HTTPS\/TLS) tanto para DNS como para la interfaz web de administraci\u00f3n",
"encryption_config_saved": "Configuraci\u00f3n de cifrado guardado",
"encryption_desc": "Soporte de cifrado (HTTPS/TLS) tanto para DNS como para la interfaz web de administración",
"encryption_config_saved": "Configuración de cifrado guardado",
"encryption_server": "Nombre del servidor",
"encryption_server_enter": "Ingrese su nombre de dominio",
"encryption_server_desc": "Para utilizar HTTPS, debe ingresar el nombre del servidor que coincida con su certificado SSL.",
"encryption_redirect": "Redireccionar a HTTPS autom\u00e1ticamente",
"encryption_redirect_desc": "Si est\u00e1 marcado, AdGuard Home redireccionar\u00e1 autom\u00e1ticamente de HTTP a las direcciones HTTPS.",
"encryption_redirect": "Redireccionar a HTTPS automáticamente",
"encryption_redirect_desc": "Si está marcado, AdGuard Home redireccionará automáticamente de HTTP a las direcciones HTTPS.",
"encryption_https": "Puerto HTTPS",
"encryption_https_desc": "Si el puerto HTTPS est\u00e1 configurado, la interfaz de administraci\u00f3n de AdGuard Home ser\u00e1 accesible a trav\u00e9s de HTTPS, y tambi\u00e9n proporcionar\u00e1 DNS mediante HTTPS en la ubicaci\u00f3n '\/dns-query'.",
"encryption_dot": "Puerto para DNS mediante TLS",
"encryption_dot_desc": "Si este puerto est\u00e1 configurado, AdGuard Home ejecutar\u00e1 un servidor DNS mediante TLS en este puerto.",
"encryption_https_desc": "Si el puerto HTTPS está configurado, la interfaz de administración de AdGuard Home será accesible a través de HTTPS, y también proporcionará DNS mediante HTTPS en la ubicación '/dns-query'.",
"encryption_dot": "Puerto DNS mediante TLS",
"encryption_dot_desc": "Si este puerto está configurado, AdGuard Home ejecutará un servidor DNS mediante TLS en este puerto.",
"encryption_certificates": "Certificados",
"encryption_certificates_desc": "Para utilizar el cifrado, debe proporcionar una cadena de certificados SSL v\u00e1lida para su dominio. Puede obtener un certificado gratuito en <0>{{link}}<\/0> o puede comprarlo en una de las autoridades de certificaci\u00f3n de confianza.",
"encryption_certificates_input": "Copie\/pegue aqu\u00ed sus certificados codificados PEM.",
"encryption_certificates_desc": "Para utilizar el cifrado, debe proporcionar una cadena de certificados SSL válida para su dominio. Puede obtener un certificado gratuito en <0>{{link}}</0> o puede comprarlo en una de las autoridades de certificación de confianza.",
"encryption_certificates_input": "Copie/pegue aquí sus certificados codificados PEM.",
"encryption_status": "Estado",
"encryption_expire": "Expira",
"encryption_key": "Clave privada",
"encryption_key_input": "Copie\/pegue aqu\u00ed su clave privada codificada PEM para su certificado.",
"encryption_enable": "Habilitar el cifrado (HTTPS, DNS mediante HTTPS y DNS mediante TLS)",
"encryption_enable_desc": "Si el cifrado est\u00e1 habilitado, la interfaz de administraci\u00f3n de AdGuard Home funcionar\u00e1 a trav\u00e9s de HTTPS, y el servidor DNS escuchar\u00e1 las peticiones DNS mediante HTTPS y DNS mediante TLS.",
"encryption_chain_valid": "La cadena de certificado es v\u00e1lida",
"encryption_chain_invalid": "La cadena de certificado no es v\u00e1lida",
"encryption_key_valid": "Esta es una clave privada {{type}} v\u00e1lida",
"encryption_key_invalid": "Esta es una clave privada {{type}} no v\u00e1lida",
"encryption_key_input": "Copie/pegue aquí su clave privada codificada PEM para su certificado.",
"encryption_enable": "Habilitar cifrado (HTTPS, DNS mediante HTTPS y DNS mediante TLS)",
"encryption_enable_desc": "Si el cifrado está habilitado, la interfaz de administración de AdGuard Home funcionará a través de HTTPS, y el servidor DNS escuchará las peticiones DNS mediante HTTPS y DNS mediante TLS.",
"encryption_chain_valid": "La cadena de certificado es válida",
"encryption_chain_invalid": "La cadena de certificado no es válida",
"encryption_key_valid": "Esta es una clave privada {{type}} válida",
"encryption_key_invalid": "Esta es una clave privada {{type}} no válida",
"encryption_subject": "Asunto",
"encryption_issuer": "Emisor",
"encryption_hostnames": "Nombres de hosts",
"encryption_reset": "\u00bfEst\u00e1 seguro de que desea restablecer la configuraci\u00f3n de cifrado?",
"topline_expiring_certificate": "Su certificado SSL est\u00e1 a punto de expirar. Actualice la <0>configuraci\u00f3n del cifrado<\/0>.",
"topline_expired_certificate": "Su certificado SSL ha expirado. Actualice la <0>configuraci\u00f3n del cifrado<\/0>.",
"form_error_port_range": "Ingrese el valor del puerto en el rango de 80 - 65535",
"encryption_reset": "¿Está seguro de que desea restablecer la configuración de cifrado?",
"topline_expiring_certificate": "Su certificado SSL está a punto de expirar. Actualice la <0>configuración del cifrado</0>.",
"topline_expired_certificate": "Su certificado SSL ha expirado. Actualice la <0>configuración del cifrado</0>.",
"form_error_port_range": "Ingrese el valor del puerto en el rango de 80 a 65535",
"form_error_port_unsafe": "Este es un puerto inseguro",
"form_error_equal": "No deber\u00eda ser igual",
"form_error_password": "La contrase\u00f1a no coincide",
"reset_settings": "Restablecer configuraci\u00f3n",
"update_announcement": "\u00a1AdGuard Home {{version}} ya est\u00e1 disponible! <0>Haga clic aqu\u00ed<\/0> para m\u00e1s informaci\u00f3n.",
"setup_guide": "Gu\u00eda de configuraci\u00f3n",
"dns_addresses": "Direcciones DNS"
"form_error_equal": "No debería ser igual",
"form_error_password": "La contraseña no coincide",
"reset_settings": "Restablecer configuración",
"update_announcement": "¡AdGuard Home {{version}} ya está disponible! <0>Haga clic aquí</0> para más información.",
"setup_guide": "Guía de configuración",
"dns_addresses": "Direcciones DNS",
"down": "Abajo",
"fix": "Corregir",
"dns_providers": "Aquí hay una <0>lista de proveedores DNS</0> conocidos para elegir.",
"update_now": "Actualizar ahora",
"update_failed": "Error en la actualización automática. Por favor <a href='https://github.com/AdguardTeam/AdGuardHome/wiki/Getting-Started#update'>siga los pasos</a> para actualizar manualmente.",
"processing_update": "Por favor espere, AdGuard Home se está actualizando",
"clients_title": "Clientes",
"clients_desc": "Configurar dispositivos conectados con AdGuard Home",
"settings_global": "Global",
"settings_custom": "Personalizado",
"table_client": "Cliente",
"table_name": "Nombre",
"save_btn": "Guardar",
"client_add": "Añadir cliente",
"client_new": "Cliente nuevo",
"client_edit": "Editar cliente",
"client_identifier": "Identificador",
"ip_address": "Dirección IP",
"client_identifier_desc": "Los clientes pueden ser identificados por la dirección IP o MAC. Tenga en cuenta que el uso de MAC como identificador solo es posible si AdGuard Home también es un <0>servidor DHCP</0>.",
"form_enter_ip": "Ingresar IP",
"form_enter_mac": "Ingresar MAC",
"form_client_name": "Ingrese el nombre del cliente",
"client_global_settings": "Usar configuración global",
"client_deleted": "Cliente \"{{key}}\" eliminado correctamente",
"client_added": "Cliente \"{{key}}\" añadido correctamente",
"client_updated": "Cliente \"{{key}}\" actualizado correctamente",
"table_statistics": "Número de peticiones (últimas 24 horas)",
"clients_not_found": "No se han encontrado clientes",
"client_confirm_delete": "¿Está seguro de que desea eliminar el cliente \"{{key}}\"?",
"filter_confirm_delete": "¿Está seguro de que desea eliminar el filtro?",
"auto_clients_title": "Clientes (activos)",
"auto_clients_desc": "Datos de los clientes que utilizan AdGuard Home, pero no se almacenan en la configuración",
"access_title": "Configuración de acceso",
"access_desc": "Aquí puede configurar las reglas de acceso para el servidor DNS de AdGuard Home.",
"access_allowed_title": "Clientes permitidos",
"access_allowed_desc": "Lista de CIDR o direcciones IP. Si está configurado, AdGuard Home solo aceptará peticiones de estas direcciones IP.",
"access_disallowed_title": "Clientes no permitidos",
"access_disallowed_desc": "Lista de CIDR o direcciones IP. Si está configurado, AdGuard Home eliminará las peticiones de estas direcciones IP.",
"access_blocked_title": "Dominios bloqueados",
"access_blocked_desc": "No confundas esto con filtros. AdGuard Home eliminará las consultas DNS con estos dominios en la pregunta de la consulta.",
"access_settings_saved": "Configuración de acceso guardado correctamente",
"updates_checked": "Actualizaciones comprobadas correctamente",
"updates_version_equal": "AdGuard Home está actualizado",
"check_updates_now": "Buscar actualizaciones ahora",
"dns_privacy": "DNS con privacidad",
"setup_dns_privacy_1": "<0>DNS mediante TLS:</0> Utilice la cadena <1>{{address}}</1>.",
"setup_dns_privacy_2": "<0>DNS mediante HTTPS:</0> Utilice la cadena <1>{{address}}</1>.",
"setup_dns_privacy_3": "<0>Tenga en cuenta que los protocolos DNS cifrados solo son compatibles con Android 9. Por lo tanto, necesita instalar software adicional para otros sistemas operativos.</0><0>Aquí hay una lista de software que puedes usar.</0>",
"setup_dns_privacy_android_1": "Android 9 soporta DNS mediante TLS de forma nativa. Para configurarlo, vaya a Configuración → Red e Internet → Avanzado → DNS privado e ingrese su nombre de dominio allí.",
"setup_dns_privacy_android_2": "<0>AdGuard para Android</0> soporta <1>DNS mediante HTTPS</1> y <1>DNS mediante TLS</1>.",
"setup_dns_privacy_android_3": "<0>Intra</0> añade soporte a Android para <1>DNS mediante HTTPS</1>.",
"setup_dns_privacy_ios_1": "<0>DNSCloak</0> soporta <1>DNS mediante HTTPS</1>, pero para configurarlo y que use tu propio servidor, necesitará generar un <2>DNS Stamp</2> para ello.",
"setup_dns_privacy_ios_2": "<0>AdGuard para iOS</0> soporta la configuración <1>DNS mediante HTTPS</1> y <1>DNS mediante TLS</1>.",
"setup_dns_privacy_other_title": "Otras implementaciones",
"setup_dns_privacy_other_1": "AdGuard Home en sí mismo puede ser un cliente DNS seguro en cualquier plataforma.",
"setup_dns_privacy_other_2": "<0>dnsproxy</0> soporta todos los protocolos DNS seguros conocidos.",
"setup_dns_privacy_other_3": "<0>dnscrypt-proxy</0> soporta <1>DNS mediante HTTPS</1>.",
"setup_dns_privacy_other_4": "<0>Mozilla Firefox</0> soporta <1>DNS mediante HTTPS</1>.",
"setup_dns_privacy_other_5": "Encontrará más implementaciones <0>aquí</0> y <1>aquí</1>.",
"setup_dns_notice": "Para utilizar <1>DNS mediante HTTPS</1> o <1>DNS mediante TLS</1>, debe <0>configurar el cifrado</0> en la configuración de AdGuard Home.",
"rewrite_added": "Reescritura DNS para \"{{key}}\" añadido correctamente",
"rewrite_deleted": "Reescritura DNS para \"{{key}}\" eliminado correctamente",
"rewrite_add": "Añadir reescritura DNS",
"rewrite_not_found": "No se han encontrado reescrituras DNS",
"rewrite_confirm_delete": "¿Está seguro de que desea eliminar la reescritura DNS para \"{{key}}\"?",
"rewrite_desc": "Permite configurar fácilmente la respuesta DNS personalizada para un nombre de dominio específico.",
"rewrite_applied": "Regla de reescritura aplicada",
"dns_rewrites": "Reescrituras DNS",
"form_domain": "Ingrese el dominio",
"form_answer": "Ingrese la dirección IP o el nombre del dominio",
"form_error_domain_format": "Formato de dominio no válido",
"form_error_answer_format": "Formato de respuesta no válido",
"configure": "Configurar",
"main_settings": "Configuración principal",
"block_services": "Bloquear servicios específicos",
"blocked_services": "Servicios bloqueados",
"blocked_services_desc": "Permite bloquear rápidamente sitios y servicios populares.",
"blocked_services_saved": "Servicios bloqueados guardado correctamente",
"blocked_services_global": "Usar servicios bloqueados globalmente",
"blocked_service": "Servicio bloqueado",
"block_all": "Bloquear todo",
"unblock_all": "Desbloquear todo"
}

View File

@@ -1,160 +1,173 @@
{
"url_added_successfully": "Url ajout\u00e9e",
"client_settings": "Paramètres du client",
"example_upstream_reserved": "vous pouvez spécifier un DNS upstream <0>pour un/des domaine(s) spécifique(s)</0>",
"upstream_parallel": "Utilisez des requêtes parallèles pour accélérer la résolution en requêtant simultanément tous les serveurs upstream",
"bootstrap_dns": "Serveurs DNS d'amorçage",
"bootstrap_dns_desc": "Les serveurs DNS d'amorçage sont utilisés pour résoudre les adresses IP des résolveurs DoH/DoT que vous spécifiez comme upstream.",
"url_added_successfully": "Url ajoutée",
"check_dhcp_servers": "Rechercher les serveurs DHCP",
"save_config": "Sauvegarder la configuration",
"enabled_dhcp": "Serveur DHCP activ\u00e9",
"disabled_dhcp": "Serveur DHCP d\u00e9sactiv\u00e9",
"enabled_dhcp": "Serveur DHCP activé",
"disabled_dhcp": "Serveur DHCP désactivé",
"dhcp_title": "Serveur DHCP (experimental !)",
"dhcp_description": "Si votre routeur ne fonctionne pas avec les r\u00e9glages DHCP, vous pouvez utiliser le serveur DHCP par d\u00e9faut d'AdGuard.",
"dhcp_description": "Si votre routeur ne fonctionne pas avec les réglages DHCP, vous pouvez utiliser le serveur DHCP par défaut d'AdGuard.",
"dhcp_enable": "Activer le serveur DHCP",
"dhcp_disable": "D\u00e9sactiver le serveur DHCP",
"dhcp_not_found": "Aucun serveur DHCP actif trouv\u00e9 sur le r\u00e9seau. Vous pouvez activer le serveur DHCP int\u00e9gr\u00e9.",
"dhcp_found": "Il y a plusieurs serveurs DHCP actifs sur le r\u00e9seau. Ce n'est pas prudent d'activer le serveur DHCP int\u00e9gr\u00e9 en ce moment.",
"dhcp_disable": "Désactiver le serveur DHCP",
"dhcp_not_found": "Aucun serveur DHCP actif trouvé sur le réseau. Vous pouvez activer le serveur DHCP intégré.",
"dhcp_found": "Il y a plusieurs serveurs DHCP actifs sur le réseau. Ce n'est pas prudent d'activer le serveur DHCP intégré en ce moment.",
"dhcp_leases": "Locations des serveurs DHCP",
"dhcp_leases_not_found": "Aucune location des serveurs DHCP trouv\u00e9e",
"dhcp_config_saved": "La configuration du serveur DHCP est sauvegard\u00e9e",
"dhcp_leases_not_found": "Aucune location des serveurs DHCP trouvée",
"dhcp_config_saved": "La configuration du serveur DHCP est sauvegardée",
"form_error_required": "Champ requis",
"form_error_ip_format": "Format IPv4 invalide",
"form_error_positive": "Doit \u00eatre sup\u00e9rieur \u00e0 0\u001c",
"form_error_positive": "Doit être supérieur à 0",
"dhcp_form_gateway_input": "IP de la passerelle",
"dhcp_form_subnet_input": "Masque de sous-r\u00e9seau",
"dhcp_form_range_title": "Rang\u00e9e des adresses IP",
"dhcp_form_range_start": "D\u00e9but de la rang\u00e9e",
"dhcp_form_range_end": "Fin de la rang\u00e9e",
"dhcp_form_lease_title": "P\u00e9riode de location du serveur DHCP (secondes)",
"dhcp_form_lease_input": "Dur\u00e9e de la location",
"dhcp_interface_select": "S\u00e9lectionner l'interface du serveur DHCP",
"dhcp_form_subnet_input": "Masque de sous-réseau",
"dhcp_form_range_title": "Rangée des adresses IP",
"dhcp_form_range_start": "Début de la rangée",
"dhcp_form_range_end": "Fin de la rangée",
"dhcp_form_lease_title": "Période de location du serveur DHCP (secondes)",
"dhcp_form_lease_input": "Durée de la location",
"dhcp_interface_select": "Sélectionner l'interface du serveur DHCP",
"dhcp_hardware_address": "Adresse de la machine",
"dhcp_ip_addresses": "Adresses IP",
"dhcp_table_hostname": "Nom de machine",
"dhcp_table_expires": "Expire le",
"back": "Retour",
"dashboard": "Tableau de bord",
"settings": "Param\u00e8tres",
"settings": "Paramètres",
"filters": "Filtres",
"query_log": "Journal des requ\u00eates\u001c",
"faq": "FAQ",
"query_log": "Journal des requêtes",
"version": "version",
"address": "addresse",
"on": "Activ\u00e9",
"off": "\u00c9teint",
"copyright": "Copyright",
"on": "Activé",
"off": "Éteint",
"homepage": "Page d'accueil",
"report_an_issue": "Signaler un probl\u00e8me",
"report_an_issue": "Signaler un problème",
"enable_protection": "Activer la protection",
"enabled_protection": "Protection activ\u00e9e",
"disable_protection": "D\u00e9sactiver la protection",
"disabled_protection": "Protection d\u00e9sactiv\u00e9e",
"enabled_protection": "Protection activée",
"disable_protection": "Désactiver la protection",
"disabled_protection": "Protection désactivée",
"refresh_statics": "Renouveler les statistiques",
"dns_query": "Requ\u00eates\u001c DNS",
"blocked_by": "Bloqu\u00e9 par Filtres",
"stats_malware_phishing": "Tentative de malware\/hamme\u00e7onnage bloqu\u00e9e",
"stats_adult": "Sites \u00e0 contenu adulte bloqu\u00e9s",
"stats_query_domain": "Domaines les plus recherch\u00e9s",
"for_last_24_hours": "pendant les derni\u00e8res 24 heures",
"no_domains_found": "Pas de domaines trouv\u00e9s",
"requests_count": "Nombre de requ\u00eates",
"top_blocked_domains": "Les domaines les plus fr\u00e9quemment bloqu\u00e9s",
"dns_query": "Requêtes DNS",
"blocked_by": "Bloqué par Filtres",
"stats_malware_phishing": "Tentative de malware/hammeçonnage bloquée",
"stats_adult": "Sites à contenu adulte bloqués",
"stats_query_domain": "Domaines les plus recherchés",
"for_last_24_hours": "pendant les dernières 24 heures",
"no_domains_found": "Pas de domaines trouvés",
"requests_count": "Nombre de requêtes",
"top_blocked_domains": "Les domaines les plus fréquemment bloqués",
"top_clients": "Meilleurs clients",
"no_clients_found": "Pas de clients trouv\u00e9s",
"general_statistics": "Statistiques g\u00e9n\u00e9rales",
"number_of_dns_query_24_hours": "Un nombre de requ\u00eates DNS quieries trait\u00e9es pendant les 24 heures derni\u00e8res",
"number_of_dns_query_blocked_24_hours": "Un nombre de requ\u00eates DNS bloqu\u00e9es par les filtres adblock et les listes de blocage des hosts",
"number_of_dns_query_blocked_24_hours_by_sec": "Un nombre de requ\u00eates DNS bloqu\u00e9es par le module S\u00e9curit\u00e9 de navigation d'AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "Un nombre de sites \u00e0 contenu adulte bloqu\u00e9s",
"enforced_save_search": "Recherche s\u00e9curis\u00e9e renforc\u00e9e",
"number_of_dns_query_to_safe_search": "Un nombre de requ\u00eates DNS faites avec la Recherche securis\u00e9e",
"no_clients_found": "Pas de clients trouvés",
"general_statistics": "Statistiques générales",
"number_of_dns_query_24_hours": "Un nombre de requêtes DNS quieries traitées pendant les 24 heures dernières",
"number_of_dns_query_blocked_24_hours": "Un nombre de requêtes DNS bloquées par les filtres adblock et les listes de blocage des hosts",
"number_of_dns_query_blocked_24_hours_by_sec": "Un nombre de requêtes DNS bloquées par le module Sécurité de navigation d'AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "Un nombre de sites à contenu adulte bloqués",
"enforced_save_search": "Recherche sécurisée renforcée",
"number_of_dns_query_to_safe_search": "Un nombre de requêtes DNS faites avec la Recherche securisée",
"average_processing_time": "Temps moyen de traitement",
"average_processing_time_hint": "Temps moyen (en millisecondes) de traitement d'une requ\u00eate DNS",
"block_domain_use_filters_and_hosts": "Bloquez les domaines \u00e0 l'aide des filtres et fichiers hosts",
"filters_block_toggle_hint": "Vous pouvez configurer les r\u00e8gles de filtrage dans les param\u00e8tres des <a href='#filters'>Filtres<\/a>.",
"use_adguard_browsing_sec": "Utilisez le service S\u00e9curit\u00e9 de navigation d'AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home va v\u00e9rifier si le domaine est dans la liste noire du service de s\u00e9curit\u00e9 de navigation. Pour cela il va utiliser un lookup API discret : le pr\u00e9fixe court du hash du nom de domaine SHA256 sera envoy\u00e9 au serveur.",
"use_adguard_parental": "Utiliser le contr\u00f4le parental d'AdGuard",
"use_adguard_parental_hint": "AdGuard Home va v\u00e9rifier s'il y a du contenu pour adultes sur le domaine. Ce sera fait par aide du m\u00eame API discret que celui utilis\u00e9 par le service de S\u00e9curit\u00e9 de navigation.",
"enforce_safe_search": "Renforcer la recherche s\u00e9curis\u00e9e",
"enforce_save_search_hint": "AdGuard Home peut renforcer la Recherche s\u00e9curis\u00e9e dans les moteurs de recherche suivants : Google, Youtube, Bing et Yandex.",
"no_servers_specified": "Pas de serveurs sp\u00e9cifi\u00e9s",
"no_settings": "Pas de param\u00e8tres",
"general_settings": "Param\u00e8tres g\u00e9n\u00e9raux",
"average_processing_time_hint": "Temps moyen (en millisecondes) de traitement d'une requête DNS",
"block_domain_use_filters_and_hosts": "Bloquez les domaines à l'aide des filtres et fichiers hosts",
"filters_block_toggle_hint": "Vous pouvez configurer les règles de filtrage dans les paramètres des <a href='#filters'>Filtres</a>.",
"use_adguard_browsing_sec": "Utilisez le service Sécurité de navigation d'AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home va vérifier si le domaine est dans la liste noire du service de sécurité de navigation. Pour cela il va utiliser un lookup API discret : le préfixe court du hash du nom de domaine SHA256 sera envoyé au serveur.",
"use_adguard_parental": "Utiliser le contrôle parental d'AdGuard",
"use_adguard_parental_hint": "AdGuard Home va vérifier s'il y a du contenu pour adultes sur le domaine. Ce sera fait par aide du même API discret que celui utilisé par le service de Sécurité de navigation.",
"enforce_safe_search": "Renforcer la recherche sécurisée",
"enforce_save_search_hint": "AdGuard Home peut renforcer la Recherche sécurisée dans les moteurs de recherche suivants : Google, Youtube, Bing et Yandex.",
"no_servers_specified": "Pas de serveurs spécifiés",
"no_settings": "Pas de paramètres",
"general_settings": "Paramètres généraux",
"upstream_dns": "Serveurs DNS upstream",
"upstream_dns_hint": "Si vous laissez ce champ vide, AdGuard Home va utiliser <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> somme upstream. Utilisez le pr\u00e9fixe tls:\/\/ pour DNS via les serveurs TLS .",
"upstream_dns_hint": "Si vous laissez ce champ vide, AdGuard Home va utiliser <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> somme upstream. Utilisez le préfixe tls:// pour DNS via les serveurs TLS .",
"test_upstream_btn": "Tester les upstreams",
"apply_btn": "Appliquer",
"disabled_filtering_toast": "Filtrage d\u00e9sactiv\u00e9",
"enabled_filtering_toast": "Filtrage activ\u00e9",
"disabled_safe_browsing_toast": "Surfing s\u00e9curis\u00e9 d\u00e9sactiv\u00e9",
"enabled_safe_browsing_toast": "Surfing s\u00e9curis\u00e9 activ\u00e9",
"disabled_parental_toast": "Contr\u00f4le parental d\u00e9sactiv\u00e9",
"enabled_parental_toast": "Contr\u00f4le parental activ\u00e9",
"disabled_safe_search_toast": "Recherche s\u00e9curis\u00e9e d\u00e9sactiv\u00e9e",
"enabled_save_search_toast": "Recherche s\u00e9curis\u00e9e activ\u00e9e",
"enabled_table_header": "Activ\u00e9",
"disabled_filtering_toast": "Filtrage désactivé",
"enabled_filtering_toast": "Filtrage activé",
"disabled_safe_browsing_toast": "Surfing sécurisé désactivé",
"enabled_safe_browsing_toast": "Surfing sécurisé activé",
"disabled_parental_toast": "Contrôle parental désactivé",
"enabled_parental_toast": "Contrôle parental activé",
"disabled_safe_search_toast": "Recherche sécurisée désactivée",
"enabled_save_search_toast": "Recherche sécurisée activée",
"enabled_table_header": "Activé",
"name_table_header": "Nom",
"filter_url_table_header": "URL du filtre",
"rules_count_table_header": "Nombre des r\u00e8gles",
"last_time_updated_table_header": "Derni\u00e8re mise \u00e0 jour",
"actions_table_header": "Actions",
"rules_count_table_header": "Nombre des règles",
"last_time_updated_table_header": "Dernière mise à jour",
"delete_table_action": "Supprimer",
"filters_and_hosts": "Listes de blocage des filtres et hosts",
"filters_and_hosts_hint": "AdGuard Home comprend les r\u00e8gles basiques de blocage ainsi que la syntaxe des fichiers hosts.",
"no_filters_added": "Aucun filtre ajout\u00e9",
"filters_and_hosts_hint": "AdGuard Home comprend les règles basiques de blocage ainsi que la syntaxe des fichiers hosts.",
"no_filters_added": "Aucun filtre ajouté",
"add_filter_btn": "Ajouter filtre",
"cancel_btn": "Annuler",
"enter_name_hint": "Saisir nom",
"enter_url_hint": "Saisir URL",
"check_updates_btn": "V\u00e9rifier les mises \u00e0 jour",
"new_filter_btn": "Abonnement \u00e0 un nouveau filtre",
"enter_valid_filter_url": "Saisir un URL valide pour s'abonner au filtre ou \u00e0 un fichier host.",
"custom_filter_rules": "R\u00e8gles de filtrage d'utilisateur",
"custom_filter_rules_hint": "Saisissez la r\u00e8gle en une ligne. C'est possible d'utiliser les r\u00e8gles de blocage ou la syntaxe des fichiers hosts.",
"check_updates_btn": "Vérifier les mises à jour",
"new_filter_btn": "Abonnement à un nouveau filtre",
"enter_valid_filter_url": "Saisir un URL valide pour s'abonner au filtre ou à un fichier host.",
"custom_filter_rules": "Règles de filtrage d'utilisateur",
"custom_filter_rules_hint": "Saisissez la règle en une ligne. C'est possible d'utiliser les règles de blocage ou la syntaxe des fichiers hosts.",
"examples_title": "Exemples",
"example_meaning_filter_block": "bloquer l'acc\u00e9s au domaine exemple.org et \u00e0 tous ses sous-domaines",
"example_meaning_filter_whitelist": "d\u00e9bloquer l'acc\u00e9s au domaine exemple.org et \u00e0 tous ses sous-domaines",
"example_meaning_filter_block": "bloquer l'accés au domaine exemple.org et à tous ses sous-domaines",
"example_meaning_filter_whitelist": "débloquer l'accés au domaine exemple.org et à tous ses sous-domaines",
"example_meaning_host_block": "AdGuard Home va retourner l'adresse 127.0.0.1 au domaine example.org (mais pas aux sous-domaines).",
"example_comment": "! Voici comment ajouter une d\u00e9scription",
"example_comment": "! Voici comment ajouter une déscription",
"example_comment_meaning": "commentaire",
"example_comment_hash": "# Et comme \u00e7a aussi on peut laisser des commentaires",
"example_comment_hash": "# Et comme ça aussi on peut laisser des commentaires",
"example_regex_meaning": "block access to the domains matching the specified regular expression",
"example_upstream_regular": "DNS classique (au-dessus de UDP)",
"example_upstream_dot": "<0>DNS-au-dessus-de-TLS<\/0> chiffr\u00e9",
"example_upstream_doh": "<0>DNS-au-dessus-de-HTTPS<\/0> chiffr\u00e9",
"example_upstream_sdns": "vous pouvez utiliser <0>DNS Stamps<\/0> pour <1>DNSCrypt<\/1> ou les resolveurs <2>DNS-au-dessus-de-HTTPS<\/2>",
"example_upstream_dot": "<a href='https://en.wikipedia.org/wiki/DNS_over_TLS' target='_blank'>DNS-au-dessus-de-TLS</a> chiffré",
"example_upstream_doh": "<a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-au-dessus-de-HTTPS</a> chiffré",
"example_upstream_sdns": "vous pouvez utiliser <a href='https://dnscrypt.info/stamps/' target='_blank'>DNS Stamps</a> pour <a href='https://dnscrypt.info/' target='_blank'>DNSCrypt</a> ou les resolveurs <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-au-dessus-de-HTTPS</a>",
"example_upstream_tcp": "DNS classique (au-dessus de TCP)",
"all_filters_up_to_date_toast": "Tous les filtres sont mis \u00e0 jour",
"updated_upstream_dns_toast": "Les serveurs DNS upstream sont mis \u00e0 jour",
"dns_test_ok_toast": "Les serveurs DNS sp\u00e9cifi\u00e9s fonctionnent de mani\u00e8re incorrecte",
"dns_test_not_ok_toast": "Impossible d'utiliser le serveur \"{{key}}\": veuillez v\u00e9rifier si le nom saisi est bien correct",
"unblock_btn": "D\u00e9bloquer",
"all_filters_up_to_date_toast": "Tous les filtres sont mis à jour",
"updated_upstream_dns_toast": "Les serveurs DNS upstream sont mis à jour",
"dns_test_ok_toast": "Les serveurs DNS spécifiés fonctionnent de manière incorrecte",
"dns_test_not_ok_toast": "Impossible d'utiliser le serveur \"{{key}}\": veuillez vérifier si le nom saisi est bien correct",
"unblock_btn": "Débloquer",
"block_btn": "Bloquer",
"time_table_header": "Temps",
"domain_name_table_header": "Nom de domaine",
"type_table_header": "Type",
"response_table_header": "R\u00e9ponse",
"client_table_header": "Client",
"response_table_header": "Réponse",
"empty_response_status": "Vide",
"show_all_filter_type": "Montrer tout",
"show_filtered_type": "Montrer les sites filtr\u00e9s",
"no_logs_found": "Aucun journal trouv\u00e9",
"disabled_log_btn": "D\u00e9sactiver le journal",
"download_log_file_btn": "T\u00e9l\u00e9charger le fichier de journal",
"show_filtered_type": "Montrer les sites filtrés",
"no_logs_found": "Aucun journal trouvé",
"disabled_log_btn": "Désactiver le journal",
"download_log_file_btn": "Télécharger le fichier de journal",
"refresh_btn": "Actualiser",
"enabled_log_btn": "Activer le journal",
"last_dns_queries": "5000 derni\u00e8res requ\u00eates DNS",
"previous_btn": "Pr\u00e9c\u00e9dent",
"last_dns_queries": "5000 dernières requêtes DNS",
"previous_btn": "Précédent",
"next_btn": "Suivant",
"loading_table_status": "Chargement en cours ...",
"page_table_footer_text": "Page",
"of_table_footer_text": "de",
"rows_table_footer_text": "lignes",
"updated_custom_filtering_toast": "R\u00e8gles de filtrage d'utilisateur mises \u00e0 jour",
"rule_removed_from_custom_filtering_toast": "R\u00e8gle retir\u00e9e des r\u00e8gles d'utilisateur",
"rule_added_to_custom_filtering_toast": "R\u00e8gle ajout\u00e9e aux r\u00e8gles d'utilisateur",
"query_log_disabled_toast": "Journal de requ\u00eates d\u00e9sactiv\u00e9",
"query_log_enabled_toast": "Journal de requ\u00eates activ\u00e9",
"source_label": "Source",
"found_in_known_domain_db": "Trouv\u00e9 dans la base de donn\u00e9es des domaines connus",
"category_label": "Cat\u00e9gorie",
"rule_label": "R\u00e8gle",
"updated_custom_filtering_toast": "Règles de filtrage d'utilisateur mises à jour",
"rule_removed_from_custom_filtering_toast": "Règle retirée des règles d'utilisateur",
"rule_added_to_custom_filtering_toast": "Règle ajoutée aux règles d'utilisateur",
"query_log_disabled_toast": "Journal de requêtes désactivé",
"query_log_enabled_toast": "Journal de requêtes activé",
"found_in_known_domain_db": "Trouvé dans la base de données des domaines connus",
"category_label": "Catégorie",
"rule_label": "Règle",
"filter_label": "Filtre",
"unknown_filter": "Filtre inconnu {{filterId}}"
"unknown_filter": "Filtre inconnu {{filterId}}",
"install_devices_desc": "Pour commencer à utiliser AdGuard Home, vous devez configurer vos appareils.",
"install_submit_title": "Félicitations !",
"install_submit_desc": "La procédure d'installation est terminée et vous êtes prêt(e) pour commencer à utiliser AdGuard Home.",
"install_devices_router": "Routeur",
"install_devices_router_desc": "Cette installation impactera automatiquement tous les appareils connectés au routeur de votre maison et vous n'aurez pas besoin de configurer manuellement chaque appareil.",
"install_devices_address": "Le serveur DNS AdGuard Home écoute sur les adresses suivantes",
"install_devices_router_list_1": "Ouvrez les préférences de votre routeur. Normalement, vous pouvez y accéder depuis votre navigateur Web via une URL (exemple http://192.168.0.1/ ou http://192.168.1.1/). Vous devrez peut-être saisir le mot de passe. Si vous ne vous en rappelez plus, vous pouvez le réinitialiser en appuyant sur le bouton du routeur. Certains routeurs fonctionnent sous une application spécifique, qui devrait être déjà installée sur votre ordinateur/téléphone.",
"install_devices_router_list_2": "Trouvez les paramètres DHCP/DNS. Recherchez les lettres DNS près d'une zone qui permet la saisie de 2 ou 3 blocs de chiffres, chacun composé de 4 parties de 1 à 3 chiffres.",
"install_devices_router_list_3": "Saisissez vos adresses de serveur AdGuard Home ici.",
"install_devices_windows_list_1": "Ouvrez votre Panneau de configuration depuis le menu Démarrer ou la recherche Windows.",
"install_devices_windows_list_2": "Allez dans la catégorie Réseau et Internet et ensuite dans le Centre Réseau et Partage.",
"install_devices_windows_list_3": "Sur la partie gauche de l'écran, recherchez Modifier les paramètres de la carte et cliquez dessus.",
"install_devices_windows_list_4": "Sélectionnez votre connexion active, clic droit dessus et sélectionnez Propriétés.",
"install_devices_windows_list_5": "Recherchez la version du protocole Internet 4 (TCP/IP) dans la liste, sélectionnez-la puis cliquez à nouveau sur Propriétés."
}

View File

@@ -1,159 +1,357 @@
{
"check_dhcp_servers": "DHCP\u30b5\u30fc\u30d0\u3092\u30c1\u30a7\u30c3\u30af\u3059\u308b",
"save_config": "\u8a2d\u5b9a\u3092\u4fdd\u5b58\u3059\u308b",
"enabled_dhcp": "DHCP\u30b5\u30fc\u30d0\u3092\u6709\u52b9\u306b\u3057\u307e\u3057\u305f",
"disabled_dhcp": "DHCP\u30b5\u30fc\u30d0\u3092\u7121\u52b9\u306b\u3057\u307e\u3057\u305f",
"dhcp_title": "DHCP\u30b5\u30fc\u30d0\uff08\u5b9f\u9a13\u7684\uff01\uff09",
"dhcp_description": "\u3042\u306a\u305f\u306e\u30eb\u30fc\u30bf\u304cDHCP\u306e\u8a2d\u5b9a\u3092\u63d0\u4f9b\u3057\u3066\u3044\u306a\u3044\u306e\u306a\u3089\u3001AdGuard\u306b\u5185\u8535\u3055\u308c\u3066\u3044\u308bDHCP\u30b5\u30fc\u30d0\u3092\u5229\u7528\u3067\u304d\u307e\u3059\u3002",
"dhcp_enable": "DHCP\u30b5\u30fc\u30d0\u3092\u6709\u52b9\u306b\u3059\u308b",
"dhcp_disable": "DHCP\u30b5\u30fc\u30d0\u3092\u7121\u52b9\u306b\u3059\u308b",
"dhcp_not_found": "\u30cd\u30c3\u30c8\u30ef\u30fc\u30af\u5185\u306b\u52d5\u4f5c\u3057\u3066\u3044\u308bDHCP\u30b5\u30fc\u30d0\u306f\u3042\u308a\u307e\u305b\u3093\u3002\u5185\u8535\u3055\u308c\u3066\u3044\u308bDHCP\u30b5\u30fc\u30d0\u3092\u6709\u52b9\u306b\u3057\u3066\u3082\u5b89\u5168\u3067\u3059\u3002",
"dhcp_found": "\u30cd\u30c3\u30c8\u30ef\u30fc\u30af\u5185\u306b\u52d5\u4f5c\u3057\u3066\u3044\u308bDHCP\u30b5\u30fc\u30d0\u3092\u898b\u3064\u3051\u307e\u3057\u305f\u3002\u5185\u81d3\u3055\u308c\u3066\u3044\u308bDHCP\u30b5\u30fc\u30d0\u3092\u6709\u52b9\u306b\u3059\u308b\u306b\u306f\u5b89\u5168\u3067\u306f\u3042\u308a\u307e\u305b\u3093\u3002",
"dhcp_leases": "DHCP\u5272\u5f53",
"dhcp_leases_not_found": "DHCP\u5272\u5f53\u306f\u3042\u308a\u307e\u305b\u3093",
"dhcp_config_saved": "DHCP\u30b5\u30fc\u30d0\u306e\u8a2d\u5b9a\u3092\u4fdd\u5b58\u3057\u307e\u3057\u305f",
"form_error_required": "\u5fc5\u9808\u9805\u76ee\u3067\u3059",
"form_error_ip_format": "IPv4\u30d5\u30a9\u30fc\u30de\u30c3\u30c8\u3067\u306f\u3042\u308a\u307e\u305b\u3093",
"form_error_positive": "0\u3088\u308a\u5927\u304d\u3044\u5fc5\u8981\u304c\u3042\u308a\u307e\u3059",
"dhcp_form_gateway_input": "\u30b2\u30fc\u30c8\u30a6\u30a7\u30a4IP",
"dhcp_form_subnet_input": "\u30b5\u30d6\u30cd\u30c3\u30c8\u30de\u30b9\u30af",
"dhcp_form_range_title": "IP\u30a2\u30c9\u30ec\u30b9\u306e\u7bc4\u56f2",
"dhcp_form_range_start": "\u7bc4\u56f2\u306e\u958b\u59cb",
"dhcp_form_range_end": "\u7bc4\u56f2\u306e\u7d42\u4e86",
"dhcp_form_lease_title": "DHCP\u5272\u5f53\u6642\u9593\uff08\u79d2\u5358\u4f4d\uff09",
"dhcp_form_lease_input": "\u5272\u5f53\u671f\u9593",
"dhcp_interface_select": "DHCP\u30a4\u30f3\u30bf\u30d5\u30a7\u30fc\u30b9\u306e\u9078\u629e",
"dhcp_hardware_address": "MAC\u30a2\u30c9\u30ec\u30b9",
"dhcp_ip_addresses": "IP\u30a2\u30c9\u30ec\u30b9",
"dhcp_table_hostname": "\u30db\u30b9\u30c8\u540d",
"dhcp_table_expires": "\u6709\u52b9\u671f\u9650",
"back": "\u623b\u308b",
"dashboard": "\u30c0\u30c3\u30b7\u30e5\u30dc\u30fc\u30c9",
"settings": "\u8a2d\u5b9a",
"filters": "\u30d5\u30a3\u30eb\u30bf",
"query_log": "\u30af\u30a8\u30ea\u30fb\u30ed\u30b0",
"faq": "\u3088\u304f\u3042\u308b\u8cea\u554f",
"version": "\u30d0\u30fc\u30b8\u30e7\u30f3",
"address": "\u30a2\u30c9\u30ec\u30b9",
"on": "\u30aa\u30f3",
"off": "\u30aa\u30d5",
"copyright": "\u8457\u4f5c\u6a29",
"homepage": "\u30db\u30fc\u30e0\u30da\u30fc\u30b8",
"report_an_issue": "\u554f\u984c\u3092\u5831\u544a\u3059\u308b",
"enable_protection": "\u4fdd\u8b77\u3092\u6709\u52b9\u306b\u3059\u308b",
"enabled_protection": "\u4fdd\u8b77\u3092\u6709\u52b9\u306b\u3057\u307e\u3057\u305f",
"disable_protection": "\u4fdd\u8b77\u3092\u7121\u52b9\u306b\u3059\u308b",
"disabled_protection": "\u4fdd\u8b77\u3092\u7121\u52b9\u306b\u3057\u307e\u3057\u305f",
"refresh_statics": "\u7d71\u8a08\u30c7\u30fc\u30bf\u3092\u6700\u65b0\u306b\u3059\u308b",
"dns_query": "DNS\u30af\u30a8\u30ea",
"blocked_by": "\u30d5\u30a3\u30eb\u30bf\u306b\u30d6\u30ed\u30c3\u30af\u3055\u308c\u305fDNS\u30af\u30a8\u30ea",
"stats_malware_phishing": "\u30d6\u30ed\u30c3\u30af\u3055\u308c\u305f\u30de\u30eb\u30a6\u30a7\u30a2\uff0f\u30d5\u30a3\u30c3\u30b7\u30f3\u30b0",
"stats_adult": "\u30d6\u30ed\u30c3\u30af\u3055\u308c\u305f\u30a2\u30c0\u30eb\u30c8\u30a6\u30a7\u30d6\u30b5\u30a4\u30c8",
"stats_query_domain": "\u6700\u3082\u554f\u5408\u305b\u3055\u308c\u305f\u30c9\u30e1\u30a4\u30f3",
"for_last_24_hours": "\u904e\u53bb24\u6642\u9593\u4ee5\u5185",
"no_domains_found": "\u30c9\u30e1\u30a4\u30f3\u60c5\u5831\u306f\u3042\u308a\u307e\u305b\u3093",
"requests_count": "\u30ea\u30af\u30a8\u30b9\u30c8\u6570",
"top_blocked_domains": "\u6700\u3082\u30d6\u30ed\u30c3\u30af\u3055\u308c\u305f\u30c9\u30e1\u30a4\u30f3",
"top_clients": "\u30c8\u30c3\u30d7\u30af\u30e9\u30a4\u30a2\u30f3\u30c8",
"no_clients_found": "\u30af\u30e9\u30a4\u30a2\u30f3\u30c8\u60c5\u5831\u306f\u3042\u308a\u307e\u305b\u3093",
"general_statistics": "\u5168\u822c\u7684\u306a\u7d71\u8a08",
"number_of_dns_query_24_hours": "\u904e\u53bb24\u6642\u9593\u306b\u51e6\u7406\u3055\u308c\u305fDNS\u30af\u30a8\u30ea\u306e\u6570",
"number_of_dns_query_blocked_24_hours": "\u5e83\u544a\u30d6\u30ed\u30c3\u30af\u30d5\u30a3\u30eb\u30bf\u3068hosts\u30d6\u30ed\u30c3\u30af\u30ea\u30b9\u30c8\u306b\u3088\u3063\u3066\u30d6\u30ed\u30c3\u30af\u3055\u308c\u305fDNS\u30ea\u30af\u30a8\u30b9\u30c8\u306e\u6570",
"number_of_dns_query_blocked_24_hours_by_sec": "AdGuard\u30d6\u30e9\u30a6\u30b8\u30f3\u30b0\u30bb\u30ad\u30e5\u30ea\u30c6\u30a3\u30e2\u30b8\u30e5\u30fc\u30eb\u306b\u3088\u3063\u3066\u30d6\u30ed\u30c3\u30af\u3055\u308c\u305fDNS\u30ea\u30af\u30a8\u30b9\u30c8\u306e\u6570",
"number_of_dns_query_blocked_24_hours_adult": "\u30d6\u30ed\u30c3\u30af\u3055\u308c\u305f\u30a2\u30c0\u30eb\u30c8\u30a6\u30a7\u30d6\u30b5\u30a4\u30c8\u306e\u6570",
"enforced_save_search": "\u5f37\u5236\u3055\u308c\u305f\u30bb\u30fc\u30d5\u30b5\u30fc\u30c1",
"number_of_dns_query_to_safe_search": "\u30bb\u30fc\u30d5\u30b5\u30fc\u30c1\u304c\u5f37\u5236\u3055\u308c\u305f\u691c\u7d22\u30a8\u30f3\u30b8\u30f3\u306b\u5bfe\u3059\u308bDNS\u30ea\u30af\u30a8\u30b9\u30c8\u306e\u6570",
"average_processing_time": "\u5e73\u5747\u51e6\u7406\u6642\u9593",
"average_processing_time_hint": "DNS\u30ea\u30af\u30a8\u30b9\u30c8\u306e\u51e6\u7406\u306b\u304b\u304b\u308b\u5e73\u5747\u6642\u9593\uff08\u30df\u30ea\u79d2\u5358\u4f4d\uff09",
"block_domain_use_filters_and_hosts": "\u30d5\u30a3\u30eb\u30bf\u3068hosts\u30d5\u30a1\u30a4\u30eb\u3092\u4f7f\u7528\u3057\u3066\u30c9\u30e1\u30a4\u30f3\u3092\u30d6\u30ed\u30c3\u30af\u3059\u308b",
"filters_block_toggle_hint": "<a href='#filters'>\u30d5\u30a3\u30eb\u30bf<\/a>\u306e\u8a2d\u5b9a\u3067\u30d6\u30ed\u30c3\u30af\u3059\u308b\u30eb\u30fc\u30eb\u3092\u8a2d\u5b9a\u3059\u308b\u3053\u3068\u304c\u3067\u304d\u307e\u3059\u3002",
"use_adguard_browsing_sec": "AdGuard\u30d6\u30e9\u30a6\u30b8\u30f3\u30b0\u30bb\u30ad\u30e5\u30ea\u30c6\u30a3\u30fb\u30a6\u30a7\u30d6\u30b5\u30fc\u30d3\u30b9\u3092\u4f7f\u7528\u3059\u308b",
"use_adguard_browsing_sec_hint": "AdGuard Home\u306f\u3001\u30d6\u30e9\u30a6\u30b8\u30f3\u30b0\u30bb\u30ad\u30e5\u30ea\u30c6\u30a3\u30fb\u30a6\u30a7\u30d6\u30b5\u30fc\u30d3\u30b9\u306b\u3088\u3063\u3066\u30c9\u30e1\u30a4\u30f3\u304c\u30d6\u30e9\u30c3\u30af\u30ea\u30b9\u30c8\u306b\u767b\u9332\u3055\u308c\u3066\u3044\u308b\u304b\u3069\u3046\u304b\u3092\u78ba\u8a8d\u3057\u307e\u3059\u3002 \u3053\u308c\u306f\u30d7\u30e9\u30a4\u30d0\u30b7\u30fc\u3092\u8003\u616e\u3057\u305fAPI\u3092\u4f7f\u7528\u3057\u3066\u30c1\u30a7\u30c3\u30af\u3092\u5b9f\u884c\u3057\u307e\u3059\u3002\u30c9\u30e1\u30a4\u30f3\u540dSHA256\u30cf\u30c3\u30b7\u30e5\u306e\u77ed\u3044\u30d7\u30ec\u30d5\u30a3\u30c3\u30af\u30b9\u306e\u307f\u304c\u30b5\u30fc\u30d0\u306b\u9001\u4fe1\u3055\u308c\u307e\u3059\u3002",
"use_adguard_parental": "AdGuard\u30da\u30a2\u30ec\u30f3\u30bf\u30eb\u30b3\u30f3\u30c8\u30ed\u30fc\u30eb\u30fb\u30a6\u30a7\u30d6\u30b5\u30fc\u30d3\u30b9\u3092\u4f7f\u7528\u3059\u308b",
"use_adguard_parental_hint": "AdGuard Home\u306f\u3001\u30c9\u30e1\u30a4\u30f3\u306b\u30a2\u30c0\u30eb\u30c8\u30b3\u30f3\u30c6\u30f3\u30c4\u304c\u542b\u307e\u308c\u3066\u3044\u308b\u304b\u3069\u3046\u304b\u3092\u78ba\u8a8d\u3057\u307e\u3059\u3002 \u30d6\u30e9\u30a6\u30b8\u30f3\u30b0\u30bb\u30ad\u30e5\u30ea\u30c6\u30a3\u30fb\u30a6\u30a7\u30d6\u30b5\u30fc\u30d3\u30b9\u3068\u540c\u3058\u30d7\u30e9\u30a4\u30d0\u30b7\u30fc\u306b\u512a\u3057\u3044API\u3092\u4f7f\u7528\u3057\u307e\u3059\u3002",
"enforce_safe_search": "\u30bb\u30fc\u30d5\u30b5\u30fc\u30c1\u3092\u5f37\u5236\u3059\u308b",
"enforce_save_search_hint": "AdGuard Home\u306f\u3001Google\u3001Youtube\u3001Bing\u3001Yandex\u306e\u691c\u7d22\u30a8\u30f3\u30b8\u30f3\u3067\u30bb\u30fc\u30d5\u30b5\u30fc\u30c1\u3092\u5f37\u5236\u3067\u304d\u307e\u3059\u3002",
"no_servers_specified": "\u30b5\u30fc\u30d0\u304c\u6307\u5b9a\u3055\u308c\u3066\u3044\u307e\u305b\u3093",
"no_settings": "\u8a2d\u5b9a\u306a\u3057",
"general_settings": "\u4e00\u822c\u8a2d\u5b9a",
"upstream_dns": "\u4e0a\u6d41DNS\u30b5\u30fc\u30d0",
"upstream_dns_hint": "\u3053\u306e\u30d5\u30a3\u30fc\u30eb\u30c9\u3092\u672a\u5165\u529b\u306e\u307e\u307e\u306b\u3059\u308b\u3068\u3001AdGuard Home\u306f\u4e0a\u6d41\u3068\u3057\u3066<a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a>\u3092\u4f7f\u7528\u3057\u307e\u3059\u3002DNS over TLS\u30b5\u30fc\u30d0\u306b\u306f\u3001\uff62tls:\/\/\u300d\u30d7\u30ec\u30d5\u30a3\u30c3\u30af\u30b9\u3092\u4f7f\u7528\u3057\u3066\u304f\u3060\u3055\u3044\u3002",
"test_upstream_btn": "\u4e0a\u6d41\u30b5\u30fc\u30d0\u3092\u30c6\u30b9\u30c8\u3059\u308b",
"apply_btn": "\u9069\u7528\u3059\u308b",
"disabled_filtering_toast": "\u30d5\u30a3\u30eb\u30bf\u30ea\u30f3\u30b0\u3092\u7121\u52b9\u306b\u3057\u307e\u3057\u305f",
"enabled_filtering_toast": "\u30d5\u30a3\u30eb\u30bf\u30ea\u30f3\u30b0\u3092\u6709\u52b9\u306b\u3057\u307e\u3057\u305f",
"disabled_safe_browsing_toast": "\u30bb\u30fc\u30d5\u30d6\u30e9\u30a6\u30b8\u30f3\u30b0\u3092\u7121\u52b9\u306b\u3057\u307e\u3057\u305f",
"enabled_safe_browsing_toast": "\u30bb\u30fc\u30d5\u30d6\u30e9\u30a6\u30b8\u30f3\u30b0\u3092\u6709\u52b9\u306b\u3057\u307e\u3057\u305f",
"disabled_parental_toast": "\u30da\u30a2\u30ec\u30f3\u30bf\u30eb\u30b3\u30f3\u30c8\u30ed\u30fc\u30eb\u3092\u7121\u52b9\u306b\u3057\u307e\u3057\u305f",
"enabled_parental_toast": "\u30da\u30a2\u30ec\u30f3\u30bf\u30eb\u30b3\u30f3\u30c8\u30ed\u30fc\u30eb\u3092\u6709\u52b9\u306b\u3057\u307e\u3057\u305f",
"disabled_safe_search_toast": "\u30bb\u30fc\u30d5\u30b5\u30fc\u30c1\u3092\u7121\u52b9\u306b\u3057\u307e\u3057\u305f",
"enabled_save_search_toast": "\u30bb\u30fc\u30d5\u30b5\u30fc\u30c1\u3092\u6709\u52b9\u306b\u3057\u307e\u3057\u305f",
"enabled_table_header": "\u6709\u52b9",
"name_table_header": "\u540d\u79f0",
"filter_url_table_header": "\u30d5\u30a3\u30eb\u30bf\u306eURL",
"rules_count_table_header": "\u30eb\u30fc\u30eb\u6570",
"last_time_updated_table_header": "\u6700\u7d42\u66f4\u65b0\u6642\u523b",
"actions_table_header": "\u64cd\u4f5c",
"delete_table_action": "\u524a\u9664\u3059\u308b",
"filters_and_hosts": "\u30d5\u30a3\u30eb\u30bf\u3068hosts\u30d6\u30ed\u30c3\u30af\u30ea\u30b9\u30c8",
"filters_and_hosts_hint": "AdGuard Home\u306f\u3001\u57fa\u672c\u7684\u306a\u5e83\u544a\u30d6\u30ed\u30c3\u30af\u30eb\u30fc\u30eb\u3068hosts\u30d5\u30a1\u30a4\u30eb\u306e\u69cb\u6587\u3092\u7406\u89e3\u3057\u307e\u3059\u3002",
"no_filters_added": "\u30d5\u30a3\u30eb\u30bf\u306f\u8ffd\u52a0\u3055\u308c\u307e\u305b\u3093\u3067\u3057\u305f",
"add_filter_btn": "\u30d5\u30a3\u30eb\u30bf\u3092\u8ffd\u52a0\u3059\u308b",
"cancel_btn": "\u30ad\u30e3\u30f3\u30bb\u30eb",
"enter_name_hint": "\u540d\u79f0\u3092\u5165\u529b",
"enter_url_hint": "URL\u3092\u5165\u529b",
"check_updates_btn": "\u30a2\u30c3\u30d7\u30c7\u30fc\u30c8\u3092\u78ba\u8a8d\u3059\u308b",
"new_filter_btn": "\u65b0\u3057\u3044\u30d5\u30a3\u30eb\u30bf\u30fb\u30b5\u30d6\u30b9\u30af\u30ea\u30d7\u30b7\u30e7\u30f3",
"enter_valid_filter_url": "\u30d5\u30a3\u30eb\u30bf\u30fb\u30b5\u30d6\u30b9\u30af\u30ea\u30d7\u30b7\u30e7\u30f3\u3082\u3057\u304f\u306fhosts\u30d5\u30a1\u30a4\u30eb\u306e\u6709\u52b9\u306aURL\u3092\u5165\u529b\u3057\u3066\u304f\u3060\u3055\u3044\u3002",
"custom_filter_rules": "\u30ab\u30b9\u30bf\u30e0\u30fb\u30d5\u30a3\u30eb\u30bf\u30ea\u30f3\u30b0\u30eb\u30fc\u30eb",
"custom_filter_rules_hint": "1\u3064\u306e\u884c\u306b1\u3064\u306e\u30eb\u30fc\u30eb\u3092\u5165\u529b\u3057\u3066\u304f\u3060\u3055\u3044\u3002 \u5e83\u544a\u30d6\u30ed\u30c3\u30af\u30eb\u30fc\u30eb\u3084hosts\u30d5\u30a1\u30a4\u30eb\u69cb\u6587\u3092\u4f7f\u7528\u3067\u304d\u307e\u3059\u3002",
"examples_title": "\u4f8b",
"example_meaning_filter_block": "example.org\u30c9\u30e1\u30a4\u30f3\u3068\u305d\u306e\u3059\u3079\u3066\u306e\u30b5\u30d6\u30c9\u30e1\u30a4\u30f3\u3078\u306e\u30a2\u30af\u30bb\u30b9\u3092\u30d6\u30ed\u30c3\u30af\u3059\u308b",
"example_meaning_filter_whitelist": "example.org\u30c9\u30e1\u30a4\u30f3\u3068\u305d\u306e\u3059\u3079\u3066\u306e\u30b5\u30d6\u30c9\u30e1\u30a4\u30f3\u3078\u306e\u30a2\u30af\u30bb\u30b9\u306e\u30d6\u30ed\u30c3\u30af\u3092\u89e3\u9664\u3059\u308b",
"example_meaning_host_block": "AdGuard Home\u306f\u3001example.org\u30c9\u30e1\u30a4\u30f3\uff08\u30b5\u30d6\u30c9\u30e1\u30a4\u30f3\u3092\u9664\u304f\uff09\u306b\u5bfe\u3057\u3066127.0.0.1\u306e\u30a2\u30c9\u30ec\u30b9\u3092\u8fd4\u3059\u3088\u3046\u306b\u306a\u308a\u307e\u3059\u3002",
"example_comment": "! \u3053\u3053\u306b\u306f\u30b3\u30e1\u30f3\u30c8\u304c\u5165\u308a\u307e\u3059",
"example_comment_meaning": "\u305f\u3060\u306e\u30b3\u30e1\u30f3\u30c8\u3067\u3059",
"example_comment_hash": "# \u3053\u3053\u3082\u30b3\u30e1\u30f3\u30c8\u3067\u3059",
"example_upstream_regular": "\u901a\u5e38\u306eDNS\uff08UDP\u3067\u306e\u554f\u3044\u5408\u308f\u305b\uff09",
"example_upstream_dot": "\u6697\u53f7\u5316\u3055\u308c\u3066\u3044\u308b <0>DNS-over-TLS<\/0>",
"example_upstream_doh": "\u6697\u53f7\u5316\u3055\u308c\u3066\u3044\u308b <0>DNS-over-HTTPS<\/0>",
"example_upstream_sdns": "<0>DNSCrypt<\/0> \u307e\u305f\u306f <1>DNS-over-HTTPS<\/1> \u30ea\u30be\u30eb\u30d0\u306e\u305f\u3081\u306b <2>DNS Stamps<\/2> \u3092\u4f7f\u3048\u307e\u3059",
"example_upstream_tcp": "\u901a\u5e38\u306eDNS\uff08TCP\u3067\u306e\u554f\u3044\u5408\u308f\u305b\uff09",
"all_filters_up_to_date_toast": "\u3059\u3079\u3066\u306e\u30d5\u30a3\u30eb\u30bf\u306f\u65e2\u306b\u6700\u65b0\u3067\u3059",
"updated_upstream_dns_toast": "\u4e0a\u6d41DNS\u30b5\u30fc\u30d0\u3092\u66f4\u65b0\u3057\u307e\u3057\u305f",
"dns_test_ok_toast": "\u6307\u5b9a\u3055\u308c\u305fDNS\u30b5\u30fc\u30d0\u306f\u6b63\u3057\u304f\u52d5\u4f5c\u3057\u3066\u3044\u307e\u3059",
"dns_test_not_ok_toast": "\u30b5\u30fc\u30d0 \"{{key}}\": \u4f7f\u7528\u3067\u304d\u307e\u305b\u3093\u3067\u3057\u305f\u3002\u6b63\u3057\u304f\u5165\u529b\u3055\u308c\u3066\u3044\u308b\u304b\u3069\u3046\u304b\u3092\u78ba\u8a8d\u3057\u3066\u304f\u3060\u3055\u3044",
"unblock_btn": "\u30d6\u30ed\u30c3\u30af\u89e3\u9664",
"block_btn": "\u30d6\u30ed\u30c3\u30af\u3059\u308b",
"time_table_header": "\u6642\u523b",
"domain_name_table_header": "\u30c9\u30e1\u30a4\u30f3\u540d",
"type_table_header": "\u7a2e\u985e",
"response_table_header": "\u5fdc\u7b54",
"client_table_header": "\u30af\u30e9\u30a4\u30a2\u30f3\u30c8",
"empty_response_status": "\u672a\u5b9a\u7fa9",
"show_all_filter_type": "\u3059\u3079\u3066\u8868\u793a",
"show_filtered_type": "\u30d5\u30a3\u30eb\u30bf\u3055\u308c\u305f\u30ed\u30b0\u3092\u8868\u793a",
"no_logs_found": "\u30ed\u30b0\u306f\u3042\u308a\u307e\u305b\u3093",
"disabled_log_btn": "\u30ed\u30b0\u3092\u7121\u52b9\u306b\u3059\u308b",
"download_log_file_btn": "\u30ed\u30b0\u30d5\u30a1\u30a4\u30eb\u3092\u30c0\u30a6\u30f3\u30ed\u30fc\u30c9\u3059\u308b",
"refresh_btn": "\u6700\u65b0\u306b\u3059\u308b",
"enabled_log_btn": "\u30ed\u30b0\u3092\u6709\u52b9\u306b\u3059\u308b",
"last_dns_queries": "\u6700\u65b05000\u4ef6\u5206\u306eDNS\u30af\u30a8\u30ea",
"previous_btn": "\u524d\u3078",
"next_btn": "\u6b21\u3078",
"loading_table_status": "\u8aad\u307f\u8fbc\u307f\u4e2d\u2026",
"page_table_footer_text": "\u30da\u30fc\u30b8",
"of_table_footer_text": "\uff0f",
"rows_table_footer_text": "\u884c",
"updated_custom_filtering_toast": "\u30ab\u30b9\u30bf\u30e0\u30fb\u30d5\u30a3\u30eb\u30bf\u30ea\u30f3\u30b0\u30eb\u30fc\u30eb\u3092\u66f4\u65b0\u3057\u307e\u3057\u305f",
"rule_removed_from_custom_filtering_toast": "\u30eb\u30fc\u30eb\u3092\u30ab\u30b9\u30bf\u30e0\u30fb\u30d5\u30a3\u30eb\u30bf\u30ea\u30f3\u30b0\u30eb\u30fc\u30eb\u304b\u3089\u9664\u53bb\u3057\u307e\u3057\u305f",
"rule_added_to_custom_filtering_toast": "\u30eb\u30fc\u30eb\u3092\u30ab\u30b9\u30bf\u30e0\u30fb\u30d5\u30a3\u30eb\u30bf\u30ea\u30f3\u30b0\u30eb\u30fc\u30eb\u306b\u8ffd\u52a0\u3057\u307e\u3057\u305f",
"query_log_disabled_toast": "\u30af\u30a8\u30ea\u30fb\u30ed\u30b0\u3092\u7121\u52b9\u306b\u3057\u307e\u3057\u305f",
"query_log_enabled_toast": "\u30af\u30a8\u30ea\u30fb\u30ed\u30b0\u3092\u6709\u52b9\u306b\u3057\u307e\u3057\u305f",
"source_label": "\u30bd\u30fc\u30b9",
"found_in_known_domain_db": "\u65e2\u77e5\u306e\u30c9\u30e1\u30a4\u30f3\u30c7\u30fc\u30bf\u30d9\u30fc\u30b9\u306b\u898b\u3064\u304b\u308a\u307e\u3057\u305f\u3002",
"category_label": "\u30ab\u30c6\u30b4\u30ea",
"rule_label": "\u30eb\u30fc\u30eb",
"filter_label": "\u30d5\u30a3\u30eb\u30bf",
"unknown_filter": "\u4e0d\u660e\u306a\u30d5\u30a3\u30eb\u30bf {{filterId}}"
"client_settings": "クライアント設定",
"example_upstream_reserved": "<0>特定のドメイン</0>に対して上流DNSを指定できます",
"upstream_parallel": "すべての上流サーバに同時に照会することで解決をスピードアップするため、並列クエリを使用する",
"bootstrap_dns": "ブートストラップDNSサーバ",
"bootstrap_dns_desc": "ブートストラップDNSサーバは、上流として指定したDoHDoTリゾルバのIPアドレスを解決するために使用されます。",
"url_added_successfully": "URLの追加に成功しました",
"check_dhcp_servers": "DHCPサーバをチェックする",
"save_config": "設定を保存する",
"enabled_dhcp": "DHCPサーバを有効にしました",
"disabled_dhcp": "DHCPサーバを無効にしました",
"dhcp_title": "DHCPサーバ(実験的!)",
"dhcp_description": "あなたのルータがDHCPの設定を提供していないのなら、AdGuardに内蔵されているDHCPサーバを利用できます。",
"dhcp_enable": "DHCPサーバを有効にする",
"dhcp_disable": "DHCPサーバを無効にする",
"dhcp_not_found": "ネットワーク内に動作しているDHCPサーバはありません。内蔵されているDHCPサーバを有効にしても安全です。",
"dhcp_found": "ネットワーク内に動作しているDHCPサーバが見つかりました。内臓されているDHCPサーバを有効にするのは安全ではありません。",
"dhcp_leases": "DHCP割り当て",
"dhcp_static_leases": "DHCP静的割り当て",
"dhcp_leases_not_found": "DHCP割当はありません",
"dhcp_config_saved": "DHCPサーバの設定を保存しました",
"form_error_required": "必須項目",
"form_error_ip_format": "IPv4フォーマットではありません",
"form_error_mac_format": "MACフォーマットではありません",
"form_error_positive": "0より大きい必要があります",
"dhcp_form_gateway_input": "ゲートウェイIP",
"dhcp_form_subnet_input": "サブネットマスク",
"dhcp_form_range_title": "IPアドレスの範囲",
"dhcp_form_range_start": "範囲の開始",
"dhcp_form_range_end": "範囲の終了",
"dhcp_form_lease_title": "DHCP割当時間秒単位",
"dhcp_form_lease_input": "割当期間",
"dhcp_interface_select": "DHCPインタフェースの選択",
"dhcp_hardware_address": "MACアドレス",
"dhcp_ip_addresses": "IPアドレス",
"dhcp_table_hostname": "ホスト名",
"dhcp_table_expires": "有効期限",
"dhcp_warning": "内蔵しているDHCPサーバを有効にしたい場合は、稼働中のDHCPサーバがないことを確認してください。そうでなければ、接続されたデバイスのためにインターネットを壊すかもしれません",
"dhcp_error": "ネットワーク内に別のDHCPサーバがあるかどうかを判断できませんでした。",
"dhcp_static_ip_error": "DHCPサーバを使用するには、静的IPアドレスを設定する必要があります。このネットワークインターフェイスが静的IPアドレスを使用するように設定されているかどうかを判断できませんでした。手動で静的IPアドレスを設定してください。",
"dhcp_dynamic_ip_found": "ご使用のシステムは、インターフェース<0>{{interfaceName}}</0>に動的IPアドレス構成が使用されています。DHCPサーバを使用するには、静的IPアドレスで設定する必要があります。あなたの現在のIPアドレスは<0>{{ipAddress}}</0>です。「DHCPサーバを有効にする」ボタンを押すと、このIPアドレスを静的IPアドレスに自動設定されます。",
"dhcp_lease_added": "静的割り当て \"{{key}}\" の追加に成功しました",
"dhcp_lease_deleted": "静的割り当て \"{{key}}\" の削除に成功しました",
"dhcp_new_static_lease": "新規静的割り当て",
"dhcp_static_leases_not_found": "DHCP静的割り当てはありません",
"dhcp_add_static_lease": "静的割り当てを追加する",
"delete_confirm": "\"{{key}}\" を削除してもよろしいですか?",
"form_enter_hostname": "ホスト名を入力してください",
"error_details": "エラー詳細",
"back": "戻る",
"dashboard": "ダッシュボード",
"settings": "設定",
"filters": "フィルタ",
"query_log": "クエリ・ログ",
"faq": "よくある質問",
"version": "バージョン",
"address": "アドレス",
"on": "オン",
"off": "オフ",
"copyright": "著作権",
"homepage": "ホームページ",
"report_an_issue": "問題を報告する",
"privacy_policy": "プライバシーポリシー",
"enable_protection": "保護を有効にする",
"enabled_protection": "保護を有効にしました",
"disable_protection": "保護を無効にする",
"disabled_protection": "保護を無効にしました",
"refresh_statics": "統計データを最新にする",
"dns_query": "DNSクエリ",
"blocked_by": "フィルタにブロックされたDNSクエリ",
"stats_malware_phishing": "ブロックされたマルウェア/フィッシング",
"stats_adult": "ブロックされたアダルトウェブサイト",
"stats_query_domain": "最も問合せされたドメイン",
"for_last_24_hours": "過去24時間以内",
"no_domains_found": "ドメイン情報はありません",
"requests_count": "リクエスト数",
"top_blocked_domains": "最もブロックされたドメイン",
"top_clients": "トップクライアント",
"no_clients_found": "クライアント情報はありません",
"general_statistics": "全般的な統計",
"number_of_dns_query_24_hours": "過去24時間に処理されたDNSクエリの数",
"number_of_dns_query_blocked_24_hours": "広告ブロックフィルタとhostsブロックリストによってブロックされたDNSリクエストの数",
"number_of_dns_query_blocked_24_hours_by_sec": "AdGuardブラウジングセキュリティモジュールによってブロックされたDNSリクエストの数",
"number_of_dns_query_blocked_24_hours_adult": "ブロックされたアダルトウェブサイトの数",
"enforced_save_search": "強制されたセーフサーチ",
"number_of_dns_query_to_safe_search": "セーフサーチが強制された検索エンジンに対するDNSリクエストの数",
"average_processing_time": "平均処理時間",
"average_processing_time_hint": "DNSリクエストの処理にかかる平均時間ミリ秒単位",
"block_domain_use_filters_and_hosts": "フィルタとhostsファイルを使用してドメインをブロックする",
"filters_block_toggle_hint": "<a href='#filters'>フィルタ</a>の設定でブロックするルールを設定することができます。",
"use_adguard_browsing_sec": "AdGuardブラウジングセキュリティ・ウェブサービスを使用する",
"use_adguard_browsing_sec_hint": "AdGuard Homeは、ブラウジングセキュリティ・ウェブサービスによってドメインがブラックリストに登録されているかどうかを確認します。 これはプライバシーを考慮したAPIを使用してチェックを実行します。ドメイン名SHA256ハッシュの短いプレフィックスのみがサーバに送信されます。",
"use_adguard_parental": "AdGuardペアレンタルコントロール・ウェブサービスを使用する",
"use_adguard_parental_hint": "AdGuard Homeは、ドメインにアダルトコンテンツが含まれているかどうかを確認します。 ブラウジングセキュリティ・ウェブサービスと同じプライバシーに優しいAPIを使用します。",
"enforce_safe_search": "セーフサーチを強制する",
"enforce_save_search_hint": "AdGuard Homeは、Google、Youtube、Bing、Yandexの検索エンジンでセーフサーチを強制できます。",
"no_servers_specified": "サーバが指定されていません",
"no_settings": "設定なし",
"general_settings": "一般設定",
"dns_settings": "DNS設定",
"encryption_settings": "暗号化設定",
"dhcp_settings": "DHCP設定",
"upstream_dns": "上流DNSサーバ",
"upstream_dns_hint": "このフィールドを未入力のままにすると、AdGuard Homeは上流として<a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a>を使用します。DNS over TLSサーバには、「tls://」プレフィックスを使用してください。",
"test_upstream_btn": "上流サーバをテストする",
"apply_btn": "適用する",
"disabled_filtering_toast": "フィルタリングを無効にしました",
"enabled_filtering_toast": "フィルタリングを有効にしました",
"disabled_safe_browsing_toast": "セーフブラウジングを無効にしました",
"enabled_safe_browsing_toast": "セーフブラウジングを有効にしました",
"disabled_parental_toast": "ペアレンタルコントロールを無効にしました",
"enabled_parental_toast": "ペアレンタルコントロールを有効にしました",
"disabled_safe_search_toast": "セーフサーチを無効にしました",
"enabled_save_search_toast": "セーフサーチを有効にしました",
"enabled_table_header": "有効",
"name_table_header": "名称",
"filter_url_table_header": "フィルタのURL",
"rules_count_table_header": "ルール数",
"last_time_updated_table_header": "最終更新時刻",
"actions_table_header": "操作",
"edit_table_action": "編集する",
"delete_table_action": "削除する",
"filters_and_hosts": "フィルタとhostsブロックリスト",
"filters_and_hosts_hint": "AdGuard Homeは、基本的な広告ブロックルールとhostsファイルの構文を理解します。",
"no_filters_added": "フィルタは追加されませんでした",
"add_filter_btn": "フィルタを追加する",
"cancel_btn": "キャンセル",
"enter_name_hint": "名称を入力",
"enter_url_hint": "URLを入力",
"check_updates_btn": "アップデートを確認する",
"new_filter_btn": "新しいフィルタ・サブスクリプション",
"enter_valid_filter_url": "フィルタ・サブスクリプションもしくはhostsファイルの有効なURLを入力してください。",
"custom_filter_rules": "カスタム・フィルタリングルール",
"custom_filter_rules_hint": "1つの行に1つのルールを入力してください。 広告ブロックルールやhostsファイル構文を使用できます。",
"examples_title": "例",
"example_meaning_filter_block": "example.orgドメインとそのすべてのサブドメインへのアクセスをブロックする",
"example_meaning_filter_whitelist": "example.orgドメインとそのすべてのサブドメインへのアクセスのブロックを解除する",
"example_meaning_host_block": "AdGuard Homeは、example.orgドメインサブドメインを除くに対して127.0.0.1のアドレスを返すようになります。",
"example_comment": "! ここにはコメントが入ります",
"example_comment_meaning": "ただのコメントです",
"example_comment_hash": "# ここもコメントです",
"example_regex_meaning": "<0>指定の正規表現</0>に一致するドメインへのアクセスをブロックします",
"example_upstream_regular": "通常のDNSUDPでの問い合わせ",
"example_upstream_dot": "暗号化されている <a href='https://en.wikipedia.org/wiki/DNS_over_TLS' target='_blank'>DNS-over-TLS</a>",
"example_upstream_doh": "暗号化されている <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a>",
"example_upstream_sdns": "<a href='https://dnscrypt.info/' target='_blank'>DNSCrypt</a> または <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a> リゾルバのために <a href='https://dnscrypt.info/stamps/' target='_blank'>DNS Stamps</a> を使えます",
"example_upstream_tcp": "通常のDNSTCPでの問い合わせ",
"all_filters_up_to_date_toast": "すべてのフィルタは既に最新です",
"updated_upstream_dns_toast": "上流DNSサーバを更新しました",
"dns_test_ok_toast": "指定されたDNSサーバは正しく動作しています",
"dns_test_not_ok_toast": "サーバ \"{{key}}\": 使用できませんでした。正しく入力されているかどうかを確認してください",
"unblock_btn": "ブロック解除",
"block_btn": "ブロックする",
"time_table_header": "時刻",
"domain_name_table_header": "ドメイン名",
"type_table_header": "種類",
"response_table_header": "応答",
"client_table_header": "クライアント",
"empty_response_status": "未定義",
"show_all_filter_type": "すべて表示",
"show_filtered_type": "フィルタされたログを表示",
"no_logs_found": "ログはありません",
"disabled_log_btn": "ログを無効にする",
"download_log_file_btn": "ログファイルをダウンロードする",
"refresh_btn": "最新にする",
"enabled_log_btn": "ログを有効にする",
"last_dns_queries": "最新5000件分のDNSクエリ",
"previous_btn": "前へ",
"next_btn": "次へ",
"loading_table_status": "読み込み中…",
"page_table_footer_text": "ページ",
"of_table_footer_text": "",
"rows_table_footer_text": "行",
"updated_custom_filtering_toast": "カスタム・フィルタリングルールを更新しました",
"rule_removed_from_custom_filtering_toast": "ルールをカスタム・フィルタリングルールから除去しました",
"rule_added_to_custom_filtering_toast": "ルールをカスタム・フィルタリングルールに追加しました",
"query_log_disabled_toast": "クエリ・ログを無効にしました",
"query_log_enabled_toast": "クエリ・ログを有効にしました",
"source_label": "ソース",
"found_in_known_domain_db": "既知のドメインデータベースに見つかりました。",
"category_label": "カテゴリ",
"rule_label": "ルール",
"filter_label": "フィルタ",
"unknown_filter": "不明なフィルタ {{filterId}}",
"install_welcome_title": "ようこそ、AdGuard Home へ!",
"install_welcome_desc": "AdGuard Homeは、ネットワーク全体で広告と追跡をブロックするDNSサーバです。その目的は、ネットワークとデバイスのすべてをあなたが制御できるようにすることであり、クライアント側のプログラムを使用する必要はありません。",
"install_settings_title": "管理用ウェブインターフェイス",
"install_settings_listen": "待ち受けインターフェイス",
"install_settings_port": "ポート",
"install_settings_interface_link": "AdGuard Homeの管理ウェブインターフェイスは、次のアドレスで利用可能になります:",
"form_error_port": "有効なポート番号を入力してください",
"install_settings_dns": "DNSサーバ",
"install_settings_dns_desc": "次のアドレスでDNSサーバを使用するようにあなたのデバイスまたはルータを設定する必要があります:",
"install_settings_all_interfaces": "すべてのインターフェイス",
"install_auth_title": "認証",
"install_auth_desc": "AdGuard Homeの管理ウェブインターフェースにパスワード認証を設定することを強くお勧めします。ローカルネットワークでのみアクセス可能であっても、制限のないアクセスから保護することは重要です。",
"install_auth_username": "ユーザ名",
"install_auth_password": "パスワード",
"install_auth_confirm": "パスワード(確認用)",
"install_auth_username_enter": "ユーザ名を入力してください",
"install_auth_password_enter": "パスワードを入力してください",
"install_step": "手順",
"install_devices_title": "あなたのデバイスの設定",
"install_devices_desc": "AdGuard Homeの利用を開始するには、あなたのデバイスがAdGuard Homeを利用するように設定する必要があります。",
"install_submit_title": "おめでとうございます!",
"install_submit_desc": "設定手順は完了し、AdGuard Homeの利用を開始する準備が整いました。",
"install_devices_router": "ルータ",
"install_devices_router_desc": "この設定では、ルータに接続されているすべてのデバイスを自動的にカバーしますので、各デバイスを手動で設定する必要はありません。",
"install_devices_address": "AdGuard HomeのDNSサーバは次のアドレスで待ち受けています",
"install_devices_router_list_1": "ルータの設定を開きます。通常は、URLhttp://192.168.0.1/ または http://192.168.1.1/ など)を介してブラウザからアクセスできます。パスワードの入力を求められることがあります。パスワードを覚えていない場合は、ルータにあるボタンを押してパスワードをリセットできます。一部のルータは特定のアプリケーションを必要とします。その場合、アプリケーションはあなたのコンピュータ/電話に既にインストールされているはずです。",
"install_devices_router_list_2": "DHCPDNSの設定を見つけます。DNSの文字のある入力欄を探します。それは、1〜3桁の数字で4つのグループに分けられた入力欄で、セットを許可されている欄です。",
"install_devices_router_list_3": "そこにAdGuard Homeサーバのアドレスを入力します。",
"install_devices_windows_list_1": "「スタート」メニューまたはWindowsの検索から「設定」を開きます。",
"install_devices_windows_list_2": "「ネットワークとインターネット」カテゴリに移動し、さらに「ネットワークと共有センター」へ移動します。",
"install_devices_windows_list_3": "画面の左側にある「アダプターの設定の変更」を見つけてクリックします。",
"install_devices_windows_list_4": "動作中の接続を選択して右クリックし、「プロパティ」を選択します。",
"install_devices_windows_list_5": "一覧から「インターネット プロトコル バージョン4TCP/IPv4」を見つけ、それを選択してから、もう一度プロパティをクリックします。",
"install_devices_windows_list_6": "「次のDNSサーバのアドレスを使う」を選択して、AdGuard Homeサーバのアドレスを入力します。",
"install_devices_macos_list_1": "Apple アイコンをクリックして「システム環境設定」へ行きます。",
"install_devices_macos_list_2": "「ネットワーク」をクリックします。",
"install_devices_macos_list_3": "一覧の最初の接続を選択して「詳細...」をクリックします。",
"install_devices_macos_list_4": "「DNS」タブを選択して、AdGuard Homeサーバのアドレスを入力します。",
"install_devices_android_list_1": "Androidメニューのホーム画面から、「設定」をタップします。",
"install_devices_android_list_2": "メニューの「Wi-Fi」をタップします。利用可能なすべてのネットワークの一覧が表示されますモバイル接続用にカスタムDNSを設定することは不可能です。",
"install_devices_android_list_3": "接続しているネットワークを長押しして、「ネットワークの変更」をタップします。",
"install_devices_android_list_4": "一部のデバイスでは、詳細設定のボックスをチェックして詳細設定を確認する必要があります。AndroidのDNS設定を調整するには、IP設定を「DHCP」から「静的IP」へ切り替える必要があります。",
"install_devices_android_list_5": "DNS 1とDNS 2の値をAdGuard Homeサーバのアドレスへ変更します。",
"install_devices_ios_list_1": "ホーム画面から「設定」をタップします。",
"install_devices_ios_list_2": "左側のメニューで「Wi-Fi」を選択しますモバイルネットワーク用にDNSを設定することは不可能です。",
"install_devices_ios_list_3": "現在使用中のネットワークの名前をタップします。",
"install_devices_ios_list_4": "「DNS」欄に、AdGuard Homeサーバのアドレスを入力します。",
"get_started": "始めましょう",
"next": "次へ",
"open_dashboard": "ダッシュボードを開きます",
"install_saved": "保存に成功しました",
"encryption_title": "暗号化",
"encryption_desc": "DNSと管理ウェブインターフェースの両方に対する暗号化HTTPSTLSをサポートします",
"encryption_config_saved": "暗号化の設定を保存しました",
"encryption_server": "サーバ名",
"encryption_server_enter": "ドメイン名を入力してください",
"encryption_server_desc": "HTTPSを使用するには、SSL証明書と一致するサーバ名を入力する必要があります。",
"encryption_redirect": "HTTPSに自動的にリダイレクト",
"encryption_redirect_desc": "チェックすると、AdGuard Homeは自動的にHTTPからHTTPSアドレスへリダイレクトします。",
"encryption_https": "HTTPS ポート",
"encryption_https_desc": "HTTPSポートが設定されていると、AdGuard Home 管理インターフェースはHTTPS経由でアクセス可能になり、そして「/dns-query」の場所にDNS-over-HTTPSも提供されます。",
"encryption_dot": "DNS-over-TLS ポート",
"encryption_dot_desc": "このポートが設定されていると、AdGuard HomeはこのポートでDNS-over-TLSサーバを実行します。",
"encryption_certificates": "証明書",
"encryption_certificates_desc": "暗号化を使用するには、ドメインに有効なSSL証明書チェーンを提供する必要があります。無料の証明書は<0> {{link}} </0>で入手できます。または、信頼できる認証局のいずれかから購入することもできます。",
"encryption_certificates_input": "ここにPEM形式の証明書をコピーペーストしてください。",
"encryption_status": "ステータス",
"encryption_expire": "有効期限",
"encryption_key": "秘密鍵",
"encryption_key_input": "ここに証明書のためのPEM形式の秘密鍵をコピーペーストしてください。",
"encryption_enable": "暗号化を有効にするHTTPS、DNS-over-HTTPS、DNS-over-TLS",
"encryption_enable_desc": "暗号化が有効になっていると、AdGuard Home 管理インターフェースはHTTPS経由で動作し、DNSサーバはDNS-over-HTTPSおよびDNS-over-TLS経由で要求を待ち受けます。",
"encryption_chain_valid": "証明書チェーンは有効です",
"encryption_chain_invalid": "証明書チェーンは無効です",
"encryption_key_valid": "これは有効な{{type}}秘密鍵です",
"encryption_key_invalid": "これは無効な{{type}}秘密鍵です",
"encryption_subject": "件名",
"encryption_issuer": "発行者",
"encryption_hostnames": "ホスト名",
"encryption_reset": "暗号化設定をリセットして良いですか?",
"topline_expiring_certificate": "SSL証明書は期限切れになります。<0>暗号化設定</0>を更新します。",
"topline_expired_certificate": "SSL証明書は期限切れです。<0>暗号化設定</0>を更新します。",
"form_error_port_range": "80〜65535の範囲でポート番号を入力してください",
"form_error_port_unsafe": "これは危険なポートです",
"form_error_equal": "等しくないはずです",
"form_error_password": "パスワードが不一致です",
"reset_settings": "設定をリセットする",
"update_announcement": "AdGuard Home {{version}}がリリースされました。詳しくは<0>こちらをクリック</0>してください。",
"setup_guide": "セットアップガイド",
"dns_addresses": "DNSアドレス",
"down": "ダウン",
"fix": "改善",
"dns_providers": "こちらは、選択可能な<0>既知のDNSプロバイダの一覧</0>です。",
"update_now": "今すぐ更新する",
"update_failed": "自動更新に失敗しました。手動で更新するには、<a href='https://github.com/AdguardTeam/AdGuardHome/wiki/Getting-Started#update'>手順に従って</a>ください。",
"processing_update": "AdGuard Homeを更新しています。しばらくお待ちください",
"clients_title": "クライアント",
"clients_desc": "AdGuard Homeに接続されているデバイスを設定します",
"settings_global": "グローバル",
"settings_custom": "カスタム",
"table_client": "クライアント",
"table_name": "名前",
"save_btn": "保存する",
"client_add": "クライアントを追加する",
"client_new": "新規クライアント",
"client_edit": "クライアントの編集",
"client_identifier": "識別子",
"ip_address": "IPアドレス",
"client_identifier_desc": "クライアントはIPアドレスまたはMACアドレスで識別できます。AdGuard Homeが<0>DHCPサーバ</0>でもある場合にのみ、識別子としてMACを使用することが可能であることにご注意ください。",
"form_enter_ip": "IPアドレスを入力してください",
"form_enter_mac": "MACアドレスを入力してください",
"form_client_name": "クライアント名を入力してください",
"client_global_settings": "グローバル設定を使用する",
"client_deleted": "クライアント \"{{key}}\" の削除に成功しました",
"client_added": "クライアント \"{{key}}\" の追加に成功しました",
"client_updated": "クライアント \"{{key}}\" の更新に成功しました",
"table_statistics": "リクエスト数過去24時間",
"clients_not_found": "クライアント情報はありません",
"client_confirm_delete": "クライアント \"{{key}}\" を削除してもよろしいですか?",
"filter_confirm_delete": "フィルターを削除してもよろしいですか?",
"auto_clients_title": "クライアント(実行時)",
"auto_clients_desc": "AdGuard Homeで使用しているが設定に保存されていないクライアント上のデータ",
"access_title": "アクセス設定",
"access_desc": "ここで、AdGuard Home DNSサーバのアクセスルールを設定できます。",
"access_allowed_title": "許可されたクライアント",
"access_allowed_desc": "CIDRまたはIPアドレスのリスト。設定されると、AdGuard HomeはこれらのIPアドレスからのリクエストのみを許可します。",
"access_disallowed_title": "拒否するクライアント",
"access_disallowed_desc": "CIDRまたはIPアドレスのリスト。設定されると、AdGuard HomeはこれらのIPアドレスからのリクエストを破棄します。",
"access_blocked_title": "ブロックするドメイン",
"access_blocked_desc": "これをフィルタと混同しないでください。AdGuard Homeは、これらのドメインを含むDNSクエリを破棄します。",
"access_settings_saved": "アクセス設定の保存に成功しました",
"updates_checked": "アップデートの確認に成功しました",
"updates_version_equal": "AdGuard Homeは既に最新です",
"check_updates_now": "今すぐアップデートを確認する",
"dns_privacy": "DNSプライバシー",
"setup_dns_privacy_1": "<0>DNS-over-TLS:</0> <1>{{address}}</1>という文字列を使用してください。",
"setup_dns_privacy_2": "<0>DNS-over-HTTPS:</0> <1>{{address}}</1>という文字列を使用してください。",
"setup_dns_privacy_3": "<0>暗号化されたDNSプロトコルはAndroid 9でのみサポートされていることに注意してください。そのため、他のオペレーティングシステムでは追加のソフトウェアをインストールする必要があります。</0> <0>使用できるソフトウェアの一覧です。</0>",
"setup_dns_privacy_android_1": "Android 9はDNS-over-TLSをネイティブにサポートします。設定するには、設定 → ネットワークとインターネット → 詳細設定 → プライベートDNS へ遷移し、そこにドメイン名を入力してください。",
"setup_dns_privacy_android_2": "<0>AdGuard for Android</0>は、<1>DNS-over-HTTPS</1>と<1>DNS-over-TLS</1>をサポートしています。",
"setup_dns_privacy_android_3": "<0>Intra</0>は、Androidに<1>DNS-over-HTTPS</1>サポートを追加します。",
"setup_dns_privacy_ios_1": "<0>DNSCloak</0>は<1>DNS-over-HTTPS</1>をサポートしますが、自身のサーバで使用するように設定するには、<2>DNS Stamp</2>を生成する必要があります。",
"setup_dns_privacy_ios_2": "<0>AdGuard for iOS</0>は、<1>DNS-over-HTTPS</1>と<1>DNS-over-TLS</1>の設定をサポートしています。",
"setup_dns_privacy_other_title": "その他の機能",
"setup_dns_privacy_other_1": "AdGuard Home 自身は、どのプラットフォームでも安全なDNSクライアントになることができます。",
"setup_dns_privacy_other_2": "<0>dnsproxy</0>は、既知のすべてのセキュアDNSプロトコルをサポートしています。",
"setup_dns_privacy_other_3": "<0>dnscrypt-proxy</0>は<1>DNS-over-HTTPS</1>をサポートします。",
"setup_dns_privacy_other_4": "<0>Mozilla Firefox</0>は<1>DNS-over-HTTPS</1>をサポートしています。",
"setup_dns_privacy_other_5": "もっと多くの実装を<0>ここ</0>や<1>ここ</1>で見つけられます。",
"setup_dns_notice": "<1>DNS-over-HTTPS</1>または<1>DNS-over-TLS</1>を使用するには、AdGuard Home 設定の<0>暗号化設定</0>が必要です。",
"rewrite_added": "\"{{key}}\" のためのDNS書き換え情報を追加完了しました",
"rewrite_deleted": "\"{{key}}\" のためのDNS書き換え情報を削除完了しました",
"rewrite_add": "DNS書き換え情報を追加する",
"rewrite_not_found": "DNS書き換え情報はありません",
"rewrite_confirm_delete": "\"{{key}}\" のためのDNS書き換え情報を削除してもよろしいですか",
"rewrite_desc": "特定のドメイン名に対するDNS応答を簡単にカスタマイズすることを可能にします。",
"rewrite_applied": "書き換えルールを適用済み",
"dns_rewrites": "DNS書き換え",
"form_domain": "ドメイン名を入力",
"form_answer": "IPアドレスかドメイン名を入力",
"form_error_domain_format": "ドメイン名のフォーマットが間違っています",
"form_error_answer_format": "応答フォーマットが間違っています",
"configure": "保存",
"main_settings": "メイン設定",
"block_services": "特定のサービスをブロックする",
"blocked_services": "ブロックするサービス",
"blocked_services_desc": "人気のあるサイトやサービスを一気にブロック。",
"blocked_services_saved": "ブロックするサービスを保存完了しました。",
"blocked_services_global": "ブロックするサービスに対しグローバル設定を使用する",
"blocked_service": "ブロックするサービス",
"block_all": "すべてブロック",
"unblock_all": "すべてのブロックを解除"
}

View File

@@ -1,95 +1,113 @@
{
"example_upstream_reserved": "Voc\u00ea pode especificar um DNS upstream <0>para um dom\u00ednio(s) especifico<\/0>",
"upstream_parallel": "Usar consultas paralelas para acelerar a resolu\u00e7\u00e3o consultando simultaneamente todos os servidores upstream",
"bootstrap_dns": "Servidores DNS de inicializa\u00e7\u00e3o",
"bootstrap_dns_desc": "Servidores DNS de inicializa\u00e7\u00e3o s\u00e3o usados para resolver endere\u00e7os IP dos resolvedores DoH\/DoT que voc\u00ea especifica como upstreams.",
"client_settings": "Configurações do cliente",
"example_upstream_reserved": "Você pode especificar um DNS upstream <0>para um domínio(s) especifico</0>",
"upstream_parallel": "Usar consultas paralelas para acelerar a resolução consultando simultaneamente todos os servidores upstream",
"bootstrap_dns": "Servidores DNS de inicialização",
"bootstrap_dns_desc": "Servidores DNS de inicialização são usados para resolver endereços IP dos resolvedores DoH/DoT que você especifica como upstreams.",
"url_added_successfully": "URL adicionada com sucesso",
"check_dhcp_servers": "Verificar por servidores DHCP",
"save_config": "Salvar configura\u00e7\u00e3o",
"save_config": "Salvar configuração",
"enabled_dhcp": "Servidor DHCP ativado",
"disabled_dhcp": "Servidor DHCP desativado",
"dhcp_title": "Servidor DHCP (experimental)",
"dhcp_description": "Se o seu roteador n\u00e3o fornecer configura\u00e7\u00f5es de DHCP, voc\u00ea poder\u00e1 usar o servidor DHCP integrado do AdGuard.",
"dhcp_description": "Se o seu roteador não fornecer configurações de DHCP, você poderá usar o servidor DHCP integrado do AdGuard.",
"dhcp_enable": "Ativar servidor DHCP",
"dhcp_disable": "Desativar servidor DHCP",
"dhcp_not_found": "Nenhum servidor DHCP ativo foi encontrado na sua rede. \u00c9 seguro ativar o servidor DHCP integrado.",
"dhcp_found": "Foram encontrados servidores DHCP ativos na rede. N\u00e3o \u00e9 seguro ativar o servidor DHCP integrado.",
"dhcp_leases": "Concess\u00f5es DHCP",
"dhcp_leases_not_found": "Nenhuma concess\u00e3o DHCP encontrada",
"dhcp_config_saved": "Salvar configura\u00e7\u00f5es do servidor DHCP",
"form_error_required": "Campo obrigat\u00f3rio",
"form_error_ip_format": "formato de endere\u00e7o IPv4 inv\u00e1lido",
"dhcp_not_found": "É seguro ativar o servidor DHCP integrado - não encontramos nenhum servidor DHCP ativo na rede. No entanto, recomendamos que você faça manualmente uma nova verificação, pois nosso teste automático não oferece 100% de garantia.",
"dhcp_found": "Um servidor DHCP ativo foi encontrado na rede. Não é seguro ativar o servidor DHCP incorporado.",
"dhcp_leases": "Concessões DHCP",
"dhcp_static_leases": "Concessões de DHCP estático",
"dhcp_leases_not_found": "Nenhuma concessão DHCP encontrada",
"dhcp_config_saved": "Salvar configurações do servidor DHCP",
"form_error_required": "Campo obrigatório",
"form_error_ip_format": "formato de endereço IPv4 inválido",
"form_error_mac_format": "Formato do endereço MAC inválido",
"form_error_positive": "Deve ser maior que 0",
"dhcp_form_gateway_input": "IP do gateway",
"dhcp_form_subnet_input": "M\u00e1scara de sub-rede",
"dhcp_form_range_title": "Faixa de endere\u00e7os IP",
"dhcp_form_range_start": "In\u00edcio da faixa",
"dhcp_form_subnet_input": "Máscara de sub-rede",
"dhcp_form_range_title": "Faixa de endereços IP",
"dhcp_form_range_start": "Início da faixa",
"dhcp_form_range_end": "Final da faixa",
"dhcp_form_lease_title": "Tempo de concess\u00e3o do DHCP (em segundos)",
"dhcp_form_lease_input": "Dura\u00e7\u00e3o da concess\u00e3o",
"dhcp_form_lease_title": "Tempo de concessão do DHCP (em segundos)",
"dhcp_form_lease_input": "Duração da concessão",
"dhcp_interface_select": "Selecione a interface DHCP",
"dhcp_hardware_address": "Endere\u00e7o de hardware",
"dhcp_ip_addresses": "Endere\u00e7o de IP",
"dhcp_table_hostname": "Hostname",
"dhcp_hardware_address": "Endereço de hardware",
"dhcp_ip_addresses": "Endereço de IP",
"dhcp_table_hostname": "Nome do servidor",
"dhcp_table_expires": "Expira",
"dhcp_warning": "Se voc\u00ea quiser ativar o servidor DHCP interno, certifique-se que n\u00e3o h\u00e1 outro servidor DHCP ativo. Caso contr\u00e1rio, isso pode impedir que outros dispositivos conectem \u00e1 internet!",
"dhcp_warning": "Se você quiser ativar o servidor DHCP, verifique se não há outro servidor DHCP ativo na sua rede. Caso contrário, a internet pode parar de funcionar para outros dispositivos conectados!",
"dhcp_error": "Não foi possível determinar se existe outro servidor DHCP na rede.",
"dhcp_static_ip_error": "Para usar o servidor DHCP, você deve definir um endereço IP estático. Não conseguimos determinar se essa interface de rede está configurada usando o endereço de IP estático. Por favor, defina um endereço IP estático manualmente.",
"dhcp_dynamic_ip_found": "Seu sistema usa a configuração de endereço IP dinâmico para a interface <0>{{interfaceName}}</0>. Para usar o servidor DHCP, você deve definir um endereço de IP estático. Seu endereço IP atual é <0> {{ipAddress}} </ 0>. Vamos definir automaticamente este endereço IP como estático se você pressionar o botão Ativar DHCP.",
"dhcp_lease_added": "Concessão estática \"{{key}}\" adicionada com sucesso",
"dhcp_lease_deleted": "Concessão estática \"{{key}}\" excluída com sucesso",
"dhcp_new_static_lease": "Nova concessão estática",
"dhcp_static_leases_not_found": "Nenhuma concessão DHCP estática foi encontrada",
"dhcp_add_static_lease": "Adicionar nova concessão estática",
"delete_confirm": "Você tem certeza de que deseja excluir \"{{key}}\"?",
"form_enter_hostname": "Digite o hostname",
"error_details": "Detalhes do erro",
"back": "Voltar",
"dashboard": "Painel",
"settings": "Configura\u00e7\u00f5es",
"settings": "Configurações",
"filters": "Filtros",
"query_log": "Registro de consultas",
"faq": "FAQ",
"version": "vers\u00e3o",
"address": "endere\u00e7o",
"on": "ON",
"off": "OFF",
"version": "Versão",
"address": "endereço",
"on": "Ligado",
"off": "Desligado",
"copyright": "Copyright",
"homepage": "P\u00e1gina inicial",
"homepage": "Página inicial",
"report_an_issue": "Reportar um problema",
"enable_protection": "Ativar prote\u00e7\u00e3o",
"enabled_protection": "Prote\u00e7\u00e3o ativada",
"disable_protection": "Desativar prote\u00e7\u00e3o",
"disabled_protection": "Prote\u00e7\u00e3o desativada",
"refresh_statics": "Atualizar estat\u00edsticas",
"privacy_policy": "Política de privacidade",
"enable_protection": "Ativar proteção",
"enabled_protection": "Proteção ativada",
"disable_protection": "Desativar proteção",
"disabled_protection": "Proteção desativada",
"refresh_statics": "Atualizar estatísticas",
"dns_query": "Consultas de DNS",
"blocked_by": "Bloqueador por filtros",
"stats_malware_phishing": "Bloqueado malware\/phishing",
"stats_malware_phishing": "Bloqueado malware/phishing",
"stats_adult": "Bloqueado sites adultos",
"stats_query_domain": "Principais dom\u00ednios consultados",
"for_last_24_hours": "nas \u00faltimas 24 horas",
"no_domains_found": "Nenhum dom\u00ednio encontrado",
"requests_count": "Contagem de solicita\u00e7\u00f5es",
"top_blocked_domains": "Principais dom\u00ednios bloqueados",
"stats_query_domain": "Principais domínios consultados",
"for_last_24_hours": "nas últimas 24 horas",
"no_domains_found": "Nenhum domínio encontrado",
"requests_count": "Contagem de solicitações",
"top_blocked_domains": "Principais domínios bloqueados",
"top_clients": "Principais clientes",
"no_clients_found": "Nenhuma cliente encontrado",
"general_statistics": "Estat\u00edsticas gerais",
"number_of_dns_query_24_hours": "O n\u00famero de consultas DNS processadas nas \u00faltimas 24 horas",
"number_of_dns_query_blocked_24_hours": "V\u00e1rias solicita\u00e7\u00f5es DNS bloqueadas por filtros de bloqueio de an\u00fancios e listas de bloqueio de hosts",
"number_of_dns_query_blocked_24_hours_by_sec": "V\u00e1rias solicita\u00e7\u00f5es de DNS bloqueadas pelo m\u00f3dulo de seguran\u00e7a da navega\u00e7\u00e3o do AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "V\u00e1rios sites adultos bloqueados",
"enforced_save_search": "For\u00e7ar pesquisa segura",
"number_of_dns_query_to_safe_search": "V\u00e1rias solicita\u00e7\u00f5es de DNS para motores de busca para os quais a pesquisa segura foi aplicada",
"average_processing_time": "Tempo m\u00e9dio de processamento",
"average_processing_time_hint": "Tempo m\u00e9dio em milissegundos no processamento de uma solicita\u00e7\u00e3o DNS",
"block_domain_use_filters_and_hosts": "Bloquear dom\u00ednios usando arquivos de filtros e hosts",
"filters_block_toggle_hint": "Voc\u00ea pode configurar as regras de bloqueio nas configura\u00e7\u00f5es de <a href='#filters'>Filtros<\/a>.",
"use_adguard_browsing_sec": "Usar o servi\u00e7o de seguran\u00e7a da navega\u00e7\u00e3o do AdGuard",
"use_adguard_browsing_sec_hint": "O AdGuard Home ir\u00e1 verificar se o dom\u00ednio est\u00e1 na lista negra do servi\u00e7o de seguran\u00e7a da navega\u00e7\u00e3o. Ele usar\u00e1 a API de pesquisa de privacidade para executar a verifica\u00e7\u00e3o: apenas um prefixo curto do hash do nome de dom\u00ednio SHA256 \u00e9 enviado para o servidor.",
"use_adguard_parental": "Usar o servi\u00e7o de controle parental do AdGuard",
"use_adguard_parental_hint": "O AdGuard Home ir\u00e1 verificar se o dom\u00ednio cont\u00e9m conte\u00fado adulto. Ele usa a mesma API amig\u00e1vel de privacidade que o servi\u00e7o de seguran\u00e7a da navega\u00e7\u00e3o.",
"enforce_safe_search": "For\u00e7ar pesquisa segura",
"enforce_save_search_hint": "O AdGuard Home pode for\u00e7ar a pesquisa segura nos seguintes motores de busca: Google, Youtube, Bing e Yandex.",
"general_statistics": "Estatísticas gerais",
"number_of_dns_query_24_hours": "O número de consultas DNS processadas nas últimas 24 horas",
"number_of_dns_query_blocked_24_hours": "Várias solicitações DNS bloqueadas por filtros de bloqueio de anúncios e listas de bloqueio de hosts",
"number_of_dns_query_blocked_24_hours_by_sec": "Várias solicitações de DNS bloqueadas pelo módulo de segurança da navegação do AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "Vários sites adultos bloqueados",
"enforced_save_search": "Forçar pesquisa segura",
"number_of_dns_query_to_safe_search": "Várias solicitações de DNS para motores de busca para os quais a pesquisa segura foi aplicada",
"average_processing_time": "Tempo médio de processamento",
"average_processing_time_hint": "Tempo médio em milissegundos no processamento de uma solicitação DNS",
"block_domain_use_filters_and_hosts": "Bloquear domínios usando arquivos de filtros e hosts",
"filters_block_toggle_hint": "Você pode configurar as regras de bloqueio nas configurações de <a href='#filters'>Filtros</a>.",
"use_adguard_browsing_sec": "Usar o serviço de segurança da navegação do AdGuard",
"use_adguard_browsing_sec_hint": "O AdGuard Home irá verificar se o domínio está na lista negra do serviço de segurança da navegação. Ele usará a API de pesquisa de privacidade para executar a verificação: apenas um prefixo curto do hash do nome de domínio SHA256 é enviado para o servidor.",
"use_adguard_parental": "Usar o serviço de controle parental do AdGuard",
"use_adguard_parental_hint": "O AdGuard Home irá verificar se o domínio contém conteúdo adulto. Ele usa a mesma API amigável de privacidade que o serviço de segurança da navegação.",
"enforce_safe_search": "Forçar pesquisa segura",
"enforce_save_search_hint": "O AdGuard Home pode forçar a pesquisa segura nos seguintes motores de busca: Google, Youtube, Bing e Yandex.",
"no_servers_specified": "Nenhum servidor especificado",
"no_settings": "N\u00e3o configurado",
"general_settings": "Configura\u00e7\u00f5es gerais",
"no_settings": "Não configurado",
"general_settings": "Configurações gerais",
"dns_settings": "Configurações de DNS",
"encryption_settings": "Configurações de criptografia",
"dhcp_settings": "Configurações de DHCP",
"upstream_dns": "Servidores DNS upstream",
"upstream_dns_hint": "Se voc\u00ea deixar este campo vazio, o AdGuard Home ir\u00e1 usar o<a href='https:\/\/1.1.1.1\/' target='_blank'>DNS da Cloudflare<\/a> como upstream.",
"upstream_dns_hint": "Se você deixar este campo vazio, o AdGuard Home irá usar o<a href='https://1.1.1.1/' target='_blank'>DNS da Cloudflare</a> como upstream.",
"test_upstream_btn": "Testar upstreams",
"apply_btn": "Aplicar",
"disabled_filtering_toast": "Filtragem desativada",
"enabled_filtering_toast": "Filtragem ativada",
"disabled_safe_browsing_toast": "Navega\u00e7\u00e3o segura desativada",
"enabled_safe_browsing_toast": "Navega\u00e7\u00e3o segura ativada",
"disabled_safe_browsing_toast": "Navegação segura desativada",
"enabled_safe_browsing_toast": "Navegação segura ativada",
"disabled_parental_toast": "Controle parental desativado",
"enabled_parental_toast": "Controle parental ativado",
"disabled_safe_search_toast": "Pesquisa segura desativada",
@@ -98,42 +116,43 @@
"name_table_header": "Nome",
"filter_url_table_header": "URL do filtro",
"rules_count_table_header": "Quantidade de regras",
"last_time_updated_table_header": "\u00daltima atualiza\u00e7\u00e3o",
"actions_table_header": "A\u00e7\u00f5es",
"last_time_updated_table_header": "Última atualização",
"actions_table_header": "Ações",
"edit_table_action": "Editar",
"delete_table_action": "Excluir",
"filters_and_hosts": "Filtros e listas de bloqueio de hosts",
"filters_and_hosts_hint": "O AdGuard Home entende regras b\u00e1sicas de bloqueio de an\u00fancios e a sintaxe de arquivos de hosts.",
"filters_and_hosts_hint": "O AdGuard Home entende regras básicas de bloqueio de anúncios e a sintaxe de arquivos de hosts.",
"no_filters_added": "Nenhum filtro adicionado",
"add_filter_btn": "Adicionar filtro",
"cancel_btn": "Cancelar",
"enter_name_hint": "Digite o nome",
"enter_url_hint": "Digite a URL",
"check_updates_btn": "Verificar atualiza\u00e7\u00f5es",
"new_filter_btn": "Nova inscri\u00e7\u00e3o de filtro",
"enter_valid_filter_url": "Digite a URL v\u00e1lida para efetuar a inscri\u00e7\u00e3o de filtro ou um arquivo de hosts.",
"check_updates_btn": "Verificar atualizações",
"new_filter_btn": "Nova inscrição de filtro",
"enter_valid_filter_url": "Digite a URL válida para efetuar a inscrição de filtro ou um arquivo de hosts.",
"custom_filter_rules": "Regras de filtragem personalizadas",
"custom_filter_rules_hint": "Digite uma regra por linha. Voc\u00ea pode usar regras de bloqueio de an\u00fancios ou a sintaxe de arquivos de hosts.",
"custom_filter_rules_hint": "Digite uma regra por linha. Você pode usar regras de bloqueio de anúncios ou a sintaxe de arquivos de hosts.",
"examples_title": "Exemplos",
"example_meaning_filter_block": "bloqueia o acesso ao dom\u00ednio exemplo.org e a todos os seus subdom\u00ednios",
"example_meaning_filter_whitelist": "desbloqueia o acesso ao dom\u00ednio exemplo.org e a todos os seus subdom\u00ednios",
"example_meaning_host_block": "O AdGuard Home ir\u00e1 retornar o endere\u00e7o 127.0.0.1 para o dom\u00ednio exemplo.org (exceto seus subdom\u00ednios).",
"example_comment": "! Aqui vai um coment\u00e1rio",
"example_comment_meaning": "apenas um coment\u00e1rio",
"example_comment_hash": "# Tamb\u00e9m um coment\u00e1rio",
"example_regex_meaning": "bloqueia o acesso aos dom\u00ednios correspondentes \u00e0 express\u00e3o regular especificada",
"example_upstream_regular": "DNS regular (atrav\u00e9s do UDP)",
"example_upstream_dot": "<0>DNS-sobre-TLS<\/0> criptografado",
"example_upstream_doh": "<0>DNS-sobre-HTTPS<\/0> criptografado",
"example_upstream_sdns": "Voc\u00ea pode usar <0>DNS Stamps<\/0>para o <1>DNSCrypt<\/1>ou usar os resolvedores <2>DNS-sobre-HTTPS<\/2>",
"example_upstream_tcp": "DNS regular (atrav\u00e9s do TCP)",
"all_filters_up_to_date_toast": "Todos os filtros j\u00e1 est\u00e3o atualizados",
"example_meaning_filter_block": "bloqueia o acesso ao domínio exemplo.org e a todos os seus subdomínios",
"example_meaning_filter_whitelist": "desbloqueia o acesso ao domínio exemplo.org e a todos os seus subdomínios",
"example_meaning_host_block": "O AdGuard Home irá retornar o endereço 127.0.0.1 para o domínio exemplo.org (exceto seus subdomínios).",
"example_comment": "! Aqui vai um comentário",
"example_comment_meaning": "apenas um comentário",
"example_comment_hash": "# Também um comentário",
"example_regex_meaning": "bloqueia o acesso aos domínios que correspondem à <0>expressão regular especificada</0>",
"example_upstream_regular": "DNS regular (através do UDP)",
"example_upstream_dot": "<0>DNS-sobre-TLS</0> criptografado",
"example_upstream_doh": "<0>DNS-sobre-HTTPS</0> criptografado",
"example_upstream_sdns": "Você pode usar <0>DNS Stamps</0>para o <1>DNSCrypt</1>ou usar os resolvedores <2>DNS-sobre-HTTPS</2>",
"example_upstream_tcp": "DNS regular (através do TCP)",
"all_filters_up_to_date_toast": "Todos os filtros já estão atualizados",
"updated_upstream_dns_toast": "Atualizado os servidores DNS upstream",
"dns_test_ok_toast": "Os servidores DNS especificados est\u00e3o funcionando corretamente",
"dns_test_not_ok_toast": "O servidor \"{{key}}\": n\u00e3o p\u00f4de ser utilizado. Por favor, verifique se voc\u00ea escreveu corretamente",
"dns_test_ok_toast": "Os servidores DNS especificados estão funcionando corretamente",
"dns_test_not_ok_toast": "O servidor \"{{key}}\": não pôde ser utilizado. Por favor, verifique se você escreveu corretamente",
"unblock_btn": "Desbloquear",
"block_btn": "Bloquear",
"time_table_header": "Data",
"domain_name_table_header": "Nome de dom\u00ednio",
"domain_name_table_header": "Nome de domínio",
"type_table_header": "Tipo",
"response_table_header": "Resposta",
"client_table_header": "Cliente",
@@ -145,112 +164,194 @@
"download_log_file_btn": "Baixar arquivo de registros",
"refresh_btn": "Atualizar",
"enabled_log_btn": "Ativar registros",
"last_dns_queries": "\u00daltimas 5000 consultas DNS",
"last_dns_queries": "Últimas 5000 consultas DNS",
"previous_btn": "Anterior",
"next_btn": "Pr\u00f3ximo",
"next_btn": "Próximo",
"loading_table_status": "Carregando",
"page_table_footer_text": "P\u00e1gina",
"page_table_footer_text": "Página",
"of_table_footer_text": "de",
"rows_table_footer_text": "linhas",
"updated_custom_filtering_toast": "Regras de filtragem personalizadas atualizadas",
"rule_removed_from_custom_filtering_toast": "Regra removida das regras de filtragem personalizadas",
"rule_added_to_custom_filtering_toast": "Regra adicionada \u00e0s regras de filtragem personalizadas",
"rule_added_to_custom_filtering_toast": "Regra adicionada às regras de filtragem personalizadas",
"query_log_disabled_toast": "Registros de consultas desativado",
"query_log_enabled_toast": "Registros de consultas ativado",
"source_label": "Fonte",
"found_in_known_domain_db": "Encontrado no banco de dados de dom\u00ednios conhecidos.",
"found_in_known_domain_db": "Encontrado no banco de dados de domínios conhecidos.",
"category_label": "Categoria",
"rule_label": "Regra",
"filter_label": "Filtro",
"unknown_filter": "Filtro desconhecido {{filterId}}",
"install_welcome_title": "Bem-vindo(a) ao AdGuard Home!",
"install_welcome_desc": "O AdGuard Home \u00e9 um servidor de DNS para bloqueio de an\u00fancios e rastreamento em toda a rede. Sua finalidade \u00e9 permitir que voc\u00ea controle toda a sua rede e seus dispositivos sem precisar ter um programa instalado.",
"install_welcome_desc": "O AdGuard Home é um servidor de DNS para bloqueio de anúncios e rastreamento em toda a rede. Sua finalidade é permitir que você controle toda a sua rede e seus dispositivos sem precisar ter um programa instalado.",
"install_settings_title": "Interface web de administrador",
"install_settings_listen": "Interface de escuta",
"install_settings_port": "Porta",
"install_settings_interface_link": "A interface web de administrador do AdGuard estar\u00e1 dispon\u00edvel nos seguintes endere\u00e7os:",
"form_error_port": "Digite uma porta v\u00e1lida",
"install_settings_interface_link": "A interface web de administrador do AdGuard estará disponível nos seguintes endereços:",
"form_error_port": "Digite uma porta válida",
"install_settings_dns": "Servidor DNS",
"install_settings_dns_desc": "Voc\u00ea precisa configurar seu dispositivo ou roteador para usar o servidor DNS nos seguintes endere\u00e7os:",
"install_settings_dns_desc": "Você precisa configurar seu dispositivo ou roteador para usar o servidor DNS nos seguintes endereços:",
"install_settings_all_interfaces": "Todas interfaces",
"install_auth_title": "Autentica\u00e7\u00e3o",
"install_auth_desc": "\u00c9 altamente recomend\u00e1vel configurar uma senha de autentica\u00e7\u00e3o na interface web de administrador do AdGuard Home. Mesmo que seja acess\u00edvel apenas em sua rede local, ainda \u00e9 importante proteg\u00ea-lo contra o acesso irrestrito.",
"install_auth_username": "Nome de usu\u00e1rio",
"install_auth_title": "Autenticação",
"install_auth_desc": "É altamente recomendável configurar uma senha de autenticação na interface web de administrador do AdGuard Home. Mesmo que seja acessível apenas em sua rede local, ainda é importante protegê-lo contra o acesso irrestrito.",
"install_auth_username": "Nome de usuário",
"install_auth_password": "Senha",
"install_auth_confirm": "Confirmar senha",
"install_auth_username_enter": "Digite o nome de usu\u00e1rio",
"install_auth_username_enter": "Digite o nome de usuário",
"install_auth_password_enter": "Digite a senha",
"install_step": "Passo",
"install_devices_title": "Configure seus dispositivos",
"install_devices_desc": "Para que o AdGuard Home comece a funcionar, voc\u00ea precisa configurar seus dispositivos para us\u00e1-lo.",
"install_submit_title": "Parab\u00e9ns!",
"install_submit_desc": "O procedimento de configura\u00e7\u00e3o est\u00e1 conclu\u00eddo e voc\u00ea est\u00e1 pronto para come\u00e7ar a usar o AdGuard Home.",
"install_devices_desc": "Para que o AdGuard Home comece a funcionar, você precisa configurar seus dispositivos para usá-lo.",
"install_submit_title": "Parabéns!",
"install_submit_desc": "O procedimento de configuração está concluído e você está pronto para começar a usar o AdGuard Home.",
"install_devices_router": "Roteador",
"install_devices_router_desc": "Esta configura\u00e7\u00e3o cobrir\u00e1 automaticamente todos os dispositivos conectados ao seu roteador dom\u00e9stico e voc\u00ea n\u00e3o ir\u00e1 precisar configurar cada um deles manualmente.",
"install_devices_address": "O servidor de DNS do AdGuard Home est\u00e1 capturando os seguintes endere\u00e7os",
"install_devices_router_list_1": "Abra as configura\u00e7\u00f5es do seu roteador\nNo navegador digite o IP do roteador, o padr\u00e3o \u00e9 (http:\/\/192.168.0.1\/ ou http:\/\/192.168.1.1\/), e o login e senha \u00e9 admin\/admin; Se voc\u00ea n\u00e3o se lembra da senha, voc\u00ea pode redefinir a senha rapidamente pressionando um bot\u00e3o no pr\u00f3prio roteador. Alguns roteadores t\u00eam um aplicativo espec\u00edfico que j\u00e1 deve estar instalado em seu computador\/telefone.",
"install_devices_router_list_2": "Encontre as Configura\u00e7\u00f5es de DNS. Procure as letras DNS ao lado de um campo que permite dois ou tr\u00eas conjuntos de n\u00fameros, cada um dividido em quatro grupos de um a tr\u00eas n\u00fameros.",
"install_devices_router_desc": "Esta configuração cobrirá automaticamente todos os dispositivos conectados ao seu roteador doméstico e você não irá precisar configurar cada um deles manualmente.",
"install_devices_address": "O servidor de DNS do AdGuard Home está capturando os seguintes endereços",
"install_devices_router_list_1": "Abra as configurações do seu roteador\nNo navegador digite o IP do roteador, o padrão é (http://192.168.0.1/ ou http://192.168.1.1/), e o login e senha é admin/admin; Se você não se lembra da senha, você pode redefinir a senha rapidamente pressionando um botão no próprio roteador. Alguns roteadores têm um aplicativo específico que já deve estar instalado em seu computador/telefone.",
"install_devices_router_list_2": "Encontre as Configurações de DNS. Procure as letras DNS ao lado de um campo que permite dois ou três conjuntos de números, cada um dividido em quatro grupos de um a três números.",
"install_devices_router_list_3": "Digite aqui seu servidor do AdGuard Home.",
"install_devices_windows_list_1": "Abra o Painel de Controle pelo Menu Iniciar ou pela Pesquisa do Windows.",
"install_devices_windows_list_2": "Entre na categoria Rede e Internet e depois clique em Central de Rede e Compartilhamento.",
"install_devices_windows_list_3": "No lado esquerdo da janela clique em Alterar as configura\u00e7\u00f5es do adaptador.",
"install_devices_windows_list_4": "Selecione sua atual conex\u00e3o, clique nela com o bot\u00e3o direito do mouse e depois clique em Propriedades.",
"install_devices_windows_list_5": "Procure na lista por Internet Protocol Version 4 (TCP\/IP), selecione e clique em Propriedades novamente.",
"install_devices_windows_list_6": "Marque usar os seguintes endere\u00e7os de servidor DNS e digite os endere\u00e7os do servidores do AdGuard Home.",
"install_devices_macos_list_1": "Clique na \u00edcone da Apple e depois em Prefer\u00eancias do Sistema.",
"install_devices_windows_list_3": "No lado esquerdo da janela clique em Alterar as configurações do adaptador.",
"install_devices_windows_list_4": "Selecione sua atual conexão, clique nela com o botão direito do mouse e depois clique em Propriedades.",
"install_devices_windows_list_5": "Procure na lista por Internet Protocol Version 4 (TCP/IP), selecione e clique em Propriedades novamente.",
"install_devices_windows_list_6": "Marque usar os seguintes endereços de servidor DNS e digite os endereços do servidores do AdGuard Home.",
"install_devices_macos_list_1": "Clique na ícone da Apple e depois em Preferências do Sistema.",
"install_devices_macos_list_2": "Clique em Rede.",
"install_devices_macos_list_3": "Selecione a primeira conex\u00e3o da lista e clique em Avan\u00e7ado.",
"install_devices_macos_list_4": "Selecione a guia DNS e digite os endere\u00e7os dos servidores do AdGuard Home.",
"install_devices_android_list_1": "Na tela inicial do menu Android, toque em Configura\u00e7\u00f5es.",
"install_devices_android_list_2": "Toque em Wi-Fi. A tela listando todas as redes ser\u00e1 exibida (n\u00e3o \u00e9 poss\u00edvel configurar DNS personalizado para uma conex\u00e3o de dados m\u00f3veis)",
"install_devices_android_list_3": "Pressione prolongadamente a rede para a qual voc\u00ea est\u00e1 conectado e toque em Modificar rede",
"install_devices_android_list_4": "Em alguns dispositivos, talvez seja necess\u00e1rio marcar a caixa Avan\u00e7ado para ver as outras configura\u00e7\u00f5es. Para ajustar suas configura\u00e7\u00f5es de DNS do Android, voc\u00ea precisar\u00e1 alternar as configura\u00e7\u00f5es de IP de DHCP para Est\u00e1tico.",
"install_devices_android_list_5": "Altere o conjunto dos valores DNS 1 e DNS 2 para os endere\u00e7os de servidores do AdGuard Home.",
"install_devices_macos_list_3": "Selecione a primeira conexão da lista e clique em Avançado.",
"install_devices_macos_list_4": "Selecione a guia DNS e digite os endereços dos servidores do AdGuard Home.",
"install_devices_android_list_1": "Na tela inicial do menu Android, toque em Configurações.",
"install_devices_android_list_2": "Toque em Wi-Fi. A tela listando todas as redes será exibida (não é possível configurar DNS personalizado para uma conexão de dados móveis)",
"install_devices_android_list_3": "Pressione prolongadamente a rede para a qual você está conectado e toque em Modificar rede",
"install_devices_android_list_4": "Em alguns dispositivos, talvez seja necessário marcar a caixa Avançado para ver as outras configurações. Para ajustar suas configurações de DNS do Android, você precisará alternar as configurações de IP de DHCP para Estático.",
"install_devices_android_list_5": "Altere o conjunto dos valores DNS 1 e DNS 2 para os endereços de servidores do AdGuard Home.",
"install_devices_ios_list_1": "Na tela incial, toque em Ajustes.",
"install_devices_ios_list_2": "Selecione Wi-Fi no menu esquerdo (n\u00e3o \u00e9 poss\u00edvel configurar o DNS em conex\u00f5es de dados m\u00f3veis).",
"install_devices_ios_list_2": "Selecione Wi-Fi no menu esquerdo (não é possível configurar o DNS em conexões de dados móveis).",
"install_devices_ios_list_3": "Toque no nome da rede atualmente ativa.",
"install_devices_ios_list_4": "No campo DNS, digite os endere\u00e7os dos servidores do AdGuard Home.",
"get_started": "Come\u00e7ar",
"next": "Pr\u00f3ximo",
"install_devices_ios_list_4": "No campo DNS, digite os endereços dos servidores do AdGuard Home.",
"get_started": "Começar",
"next": "Próximo",
"open_dashboard": "Abrir painel",
"install_saved": "Salvo com sucesso",
"encryption_title": "Criptografia",
"encryption_desc": "Suporte a criptografia (HTTPS\/TLS) para DNS e interface de administra\u00e7\u00e3o web",
"encryption_config_saved": "Configura\u00e7\u00e3o de criptografia salva",
"encryption_desc": "Suporte a criptografia (HTTPS/TLS) para DNS e interface de administração web",
"encryption_config_saved": "Configuração de criptografia salva",
"encryption_server": "Nome do servidor",
"encryption_server_enter": "Digite seu nome de dom\u00ednio",
"encryption_server_desc": "Para usar o protocolo HTTPS, voc\u00ea precisa digitar o nome do servidor que corresponde ao seu certificado SSL.",
"encryption_server_enter": "Digite seu nome de domínio",
"encryption_server_desc": "Para usar o protocolo HTTPS, você precisa digitar o nome do servidor que corresponde ao seu certificado SSL.",
"encryption_redirect": "Redirecionar automaticamente para HTTPS",
"encryption_redirect_desc": "Se marcado, o AdGuard Home ir\u00e1 redirecionar automaticamente os endere\u00e7os HTTP para HTTPS.",
"encryption_redirect_desc": "Se marcado, o AdGuard Home irá redirecionar automaticamente os endereços HTTP para HTTPS.",
"encryption_https": "Porta HTTPS",
"encryption_https_desc": "Se a porta HTTPS estiver configurada, a interface administrativa do AdGuard Home ser\u00e1 acess\u00edvel via HTTPS e tamb\u00e9m fornecer\u00e1 o DNS-sobre-HTTPS no local '\/dns-query'.",
"encryption_https_desc": "Se a porta HTTPS estiver configurada, a interface administrativa do AdGuard Home será acessível via HTTPS e também fornecerá o DNS-sobre-HTTPS no local '/dns-query'.",
"encryption_dot": "Porta DNS-sobre-TLS",
"encryption_dot_desc": "Se essa porta estiver configurada, o AdGuard Home ir\u00e1 executar o servidor DNS-sobre- TSL nesta porta.",
"encryption_dot_desc": "Se essa porta estiver configurada, o AdGuard Home irá executar o servidor DNS-sobre- TSL nesta porta.",
"encryption_certificates": "Certificados",
"encryption_certificates_desc": "Para usar criptografia, voc\u00ea precisa fornecer uma cadeia de certificados SSL v\u00e1lida para seu dom\u00ednio. Voc\u00ea pode obter um certificado gratuito em <0> {{link}}<\/0> ou pode compr\u00e1-lo de uma das autoridades de certifica\u00e7\u00e3o confi\u00e1veis.",
"encryption_certificates_input": "Copie\/cole aqui seu certificado codificado em PEM.",
"encryption_certificates_desc": "Para usar criptografia, você precisa fornecer uma cadeia de certificados SSL válida para seu domínio. Você pode obter um certificado gratuito em <0> {{link}}</0> ou pode comprá-lo de uma das autoridades de certificação confiáveis.",
"encryption_certificates_input": "Copie/cole aqui seu certificado codificado em PEM.",
"encryption_status": "Status",
"encryption_expire": "Expira",
"encryption_key": "Chave privada",
"encryption_key_input": "Copie\/cole aqui a chave privada codificada em PEM para seu certificado.",
"encryption_key_input": "Copie/cole aqui a chave privada codificada em PEM para seu certificado.",
"encryption_enable": "Ativar criptografia (HTTPS, DNS-sobre-HTTPS e DNS-sobre-TLS)",
"encryption_enable_desc": "Se a criptografia estiver ativada, a interface administrativa do AdGuard Home funcionar\u00e1 em HTTPS, o servidor DNS ir\u00e1 capturar as solicita\u00e7\u00f5es por meio do DNS-sobre-HTTPS e DNS-sobre-TLS.",
"encryption_chain_valid": "Cadeia de chave v\u00e1lida.",
"encryption_chain_invalid": "A cadeia de certificado \u00e9 inv\u00e1lida",
"encryption_key_valid": "Esta \u00e9 uma chave privada {{type}} v\u00e1lida",
"encryption_key_invalid": "Esta \u00e9 uma chave privada {{type}} inv\u00e1lida",
"encryption_enable_desc": "Se a criptografia estiver ativada, a interface administrativa do AdGuard Home funcionará em HTTPS, o servidor DNS irá capturar as solicitações por meio do DNS-sobre-HTTPS e DNS-sobre-TLS.",
"encryption_chain_valid": "Cadeia de chave válida.",
"encryption_chain_invalid": "A cadeia de certificado é inválida",
"encryption_key_valid": "Esta é uma chave privada {{type}} válida",
"encryption_key_invalid": "Esta é uma chave privada {{type}} inválida",
"encryption_subject": "Assunto",
"encryption_issuer": "Emissor",
"encryption_hostnames": "Hostnames",
"encryption_reset": "Voc\u00ea tem certeza de que deseja redefinir a configura\u00e7\u00e3o de criptografia?",
"topline_expiring_certificate": "Seu certificado SSL est\u00e1 prestes a expirar. Atualize suas <0>configura\u00e7\u00f5es de criptografia<\/]0>",
"topline_expired_certificate": "Seu certificado SSL est\u00e1 expirado. Atualize suas <0>configura\u00e7\u00f5es de criptografia<\/0>",
"encryption_hostnames": "Nomes dos servidores",
"encryption_reset": "Você tem certeza de que deseja redefinir a configuração de criptografia?",
"topline_expiring_certificate": "Seu certificado SSL está prestes a expirar. Atualize suas <0>configurações de criptografia</]0>",
"topline_expired_certificate": "Seu certificado SSL está expirado. Atualize suas <0>configurações de criptografia</0>",
"form_error_port_range": "Digite um porta entre 80 e 65535",
"form_error_port_unsafe": "Esta porta n\u00e3o \u00e9 segura",
"form_error_equal": "N\u00e3o deve ser igual",
"form_error_password": "Senhas n\u00e3o coincidem",
"reset_settings": "Redefinir configura\u00e7\u00f5es",
"update_announcement": "AdGuard Home {{version}} est\u00e1 dispon\u00edvel!<0>Clique aqui<\/0> para mais informa\u00e7\u00f5es.",
"setup_guide": "Guia de configura\u00e7\u00e3o",
"dns_addresses": "Endere\u00e7os DNS"
"form_error_port_unsafe": "Esta porta não é segura",
"form_error_equal": "Não deve ser igual",
"form_error_password": "Senhas não coincidem",
"reset_settings": "Redefinir configurações",
"update_announcement": "AdGuard Home {{version}} está disponível!<0>Clique aqui</0> para mais informações.",
"setup_guide": "Guia de configuração",
"dns_addresses": "Endereços DNS",
"down": "Caiu",
"fix": "Corrigido",
"dns_providers": "Aqui está uma <0>lista de provedores de DNS conhecidos</0> para escolher.",
"update_now": "Atualizar agora",
"update_failed": "A atualização automática falhou. Por favor, <a href='https://github.com/AdguardTeam/AdGuardHome/wiki/Getting-Started#update'>siga estes passos</a> para atualizar manualmente.",
"processing_update": "Por favor, aguarde enquanto o AdGuard Home está sendo atualizado",
"clients_title": "Clientes",
"clients_desc": "Configure dispositivos conectados ao AdGuard",
"settings_global": "Global",
"settings_custom": "Personalizado",
"table_client": "Cliente",
"table_name": "Nome",
"save_btn": "Salvar",
"client_add": "Adicionar cliente",
"client_new": "Novo cliente",
"client_edit": "Editar cliente",
"client_identifier": "Identificador",
"ip_address": "Endereço de IP",
"client_identifier_desc": "Os clientes podem ser identificados pelo endereço de IP ou pelo endereço MAC. Observe que o uso do endereço MAC como identificador só é possível se o AdGuard Home também for um <0>servidor DHCP</0>",
"form_enter_ip": "Digite o endereço de IP",
"form_enter_mac": "Digite o endereço MAC",
"form_client_name": "Digite o nome do cliente",
"client_global_settings": "Usar configurações global",
"client_deleted": "Cliente \"{{key}}\" excluído com sucesso",
"client_added": "Cliente \"{{key}}\" adicionado com sucesso",
"client_updated": "Cliente \"{{key}}\" atualizado com sucesso",
"table_statistics": "Contagem de solicitações (últimas 24 horas)",
"clients_not_found": "Nenhum cliente foi encontrado",
"client_confirm_delete": "Você tem certeza de que deseja excluir o cliente \"{{key}}\"?",
"filter_confirm_delete": "Você tem certeza de que deseja excluir o filtro?",
"auto_clients_title": "Clientes (tempo de execução)",
"auto_clients_desc": "Dados dos clientes que usam o AdGuard Home, que não são armazenados na configuração",
"access_title": "Configurações de acessos",
"access_desc": "Aqui você pode configurar as regras de acesso para o servidores de DNS do AdGuard Home.",
"access_allowed_title": "Clientes permitidos",
"access_allowed_desc": "Uma lista de endereços IP ou CIDR. Ao configurar, o AdGuard Home irá permitir solicitações apenas desses endereços de IP.",
"access_disallowed_title": "Clientes não permitidos",
"access_disallowed_desc": "Uma lista de endereços IP ou CIDR. Ao configurar, o AdGuard Home irá descartar as solicitações desses endereços de IP.",
"access_blocked_title": "Domínios bloqueados",
"access_blocked_desc": "Não confunda isso com os filtros. O AdGuard Home irá descartar as consultas DNS com esses domínios.",
"access_settings_saved": "Configurações de acesso foram salvas com sucesso",
"updates_checked": "Atualizações verificadas com sucesso",
"updates_version_equal": "O AdGuard Home está atualizado.",
"check_updates_now": "Verificar atualizações",
"dns_privacy": "Privacidade de DNS",
"setup_dns_privacy_1": "<0>DNS-sobre-TLS:</0> Use <1>{{address}}</1> string.",
"setup_dns_privacy_2": "<0>DNS-sobre-HTTPS:</0> Use <1>{{address}}</1> string.",
"setup_dns_privacy_3": "<0>Por favor, note que os protocolos de DNS criptografados são suportados apenas no Android 9. Então, você irá precisa instalar um software adicional em outros sistemas operacionais.</0><0>Aqui está a lista de softwares que você pode usar.</0>",
"setup_dns_privacy_android_1": "O Android 9 suporta o DNS-sobre-TLS de forma nativa. Para configurá-lo, vá para Configurações → Rede e internet → Avançado → DNS privado e digite seu nome de domínio lá.",
"setup_dns_privacy_android_2": "O <0>AdGuard para Android</0> suporta <1>DNS-sobre-HTTPS</1> e <1>DNS-sobre-TLS</1>.",
"setup_dns_privacy_android_3": "<0>Intra</0> adiciona o suporte <1>DNS-sobre-HTTPS</1> para o Android.",
"setup_dns_privacy_ios_1": "<0>DNSCloak</0> suporta <1>DNS-sobre-HTTPS</1>, mas para configurá-lo para usar seu próprio servidor, você precisará gerar um <2>DNS Stamp</2>.",
"setup_dns_privacy_ios_2": "O <0>AdGuard para iOS</0> suporta a configuração do <1>DNS-sobre-HTTPS</1> e <1>DNS-sobre-TLS</1>.",
"setup_dns_privacy_other_title": "Outras implementações",
"setup_dns_privacy_other_1": "O próprio AdGuard Home pode ser usado como um cliente DNS seguro em qualquer plataforma.",
"setup_dns_privacy_other_2": "<0>dnsproxy</0> suporta todos os protocolos de DNS seguros conhecidos.",
"setup_dns_privacy_other_3": "<0>dnscrypt-proxy</0> suporta <1>DNS-sobre-HTTPS</1>",
"setup_dns_privacy_other_4": "<0>Mozilla Firefox</0> suporta <1>DNS-sobre-HTTPS</1>.",
"setup_dns_privacy_other_5": "Você encontrará mais implementações <0>aqui</0> e <1>aqui</1>.",
"setup_dns_notice": "Para usar o <1>DNS-sobre-HTTPS</1> ou <1>DNS-sobre-TLS</1>, você precisa <0>configurar a criptografia</0> nas configurações do AdGuard Home.",
"rewrite_added": "Reescrita de DNS para \"{{key}}\" adicionada com sucesso",
"rewrite_deleted": "Reescrita de DNS para \"{{key}}\" excluída com sucesso",
"rewrite_add": "Adicionar reescrita de DNS",
"rewrite_not_found": "Nenhuma reescrita de DNS foi encontrada",
"rewrite_confirm_delete": "Você tem certeza de que deseja excluir a reescrita de DNS para \"{{key}}\"?",
"rewrite_desc": "Permite configurar uma resposta personalizada do DNS para um nome de domínio específico.",
"rewrite_applied": "Regra de reescrita aplicada",
"dns_rewrites": "Reescritas de DNS",
"form_domain": "Digite o domínio",
"form_answer": "Digite o endereço de IP ou nome de domínio",
"form_error_domain_format": "Formato de domínio inválido",
"form_error_answer_format": "Formato de resposta inválido",
"configure": "Configurar",
"main_settings": "Configurações principais",
"block_services": "Bloquear serviços específicos",
"blocked_services": "Serviços bloqueados",
"blocked_services_desc": "Permite o bloqueio rápido de sites e serviços populares.",
"blocked_services_saved": "Serviços bloqueados salvos com sucesso",
"blocked_services_global": "Usar serviços bloqueados globais",
"blocked_service": "Serviço bloqueado",
"block_all": "Bloquear tudo",
"unblock_all": "Desbloquear todos"
}

View File

@@ -1,159 +1,357 @@
{
"check_dhcp_servers": "\u041f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c DHCP-\u0441\u0435\u0440\u0432\u0435\u0440\u044b",
"save_config": "\u0421\u043e\u0445\u0440\u0430\u043d\u0438\u0442\u044c \u043a\u043e\u043d\u0444\u0438\u0433\u0443\u0440\u0430\u0446\u0438\u044e",
"enabled_dhcp": "DHCP-\u0441\u0435\u0440\u0432\u0435\u0440 \u0432\u043a\u043b\u044e\u0447\u0435\u043d",
"disabled_dhcp": "DHCP-\u0441\u0435\u0440\u0432\u0435\u0440 \u043e\u0442\u043a\u043b\u044e\u0447\u0435\u043d",
"dhcp_title": "DHCP-\u0441\u0435\u0440\u0432\u0435\u0440 (\u044d\u043a\u0441\u043f\u0435\u0440\u0438\u043c\u0435\u043d\u0442\u0430\u043b\u044c\u043d\u044b\u0439!)",
"dhcp_description": "\u0415\u0441\u043b\u0438 \u0432\u0430\u0448 \u0440\u043e\u0443\u0442\u0435\u0440 \u043d\u0435 \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438 DHCP, \u0432\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u044b\u0439 \u0432\u0441\u0442\u0440\u043e\u0435\u043d\u043d\u044b\u0439 DHCP-\u0441\u0435\u0440\u0432\u0435\u0440 AdGuard.",
"dhcp_enable": "\u0412\u043a\u043b\u044e\u0447\u0438\u0442\u044c DHCP-\u0441\u0435\u0440\u0432\u0435\u0440",
"dhcp_disable": "\u041e\u0442\u043a\u043b\u044e\u0447\u0438\u0442\u044c DHCP-\u0441\u0435\u0440\u0432\u0435\u0440",
"dhcp_not_found": "\u0410\u043a\u0442\u0438\u0432\u043d\u044b\u0435 DHCP-\u0441\u0435\u0440\u0432\u0435\u0440\u044b \u0432 \u0441\u0435\u0442\u0438 \u043d\u0435 \u043d\u0430\u0439\u0434\u0435\u043d\u044b. \u0412\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e \u0432\u043a\u043b\u044e\u0447\u0438\u0442\u044c \u0432\u0441\u0442\u0440\u043e\u0435\u043d\u043d\u044b\u0439 \u0441\u0435\u0440\u0432\u0435\u0440 DHCP.",
"dhcp_found": "\u041d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0430\u043a\u0442\u0438\u0432\u043d\u044b\u0435 DHCP-\u0441\u0435\u0440\u0432\u0435\u0440\u044b \u043d\u0430\u0439\u0434\u0435\u043d\u044b \u0432 \u0441\u0435\u0442\u0438. \u0412\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0435 \u0432\u0441\u0442\u0440\u043e\u0435\u043d\u043d\u043e\u0433\u043e DHCP-\u0441\u0435\u0440\u0432\u0435\u0440\u0430 \u043d\u0435\u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e.",
"dhcp_leases": "\u0410\u0440\u0435\u043d\u0434\u0430 DHCP",
"dhcp_leases_not_found": "\u0410\u0440\u0435\u043d\u0434\u0430 DHCP \u043d\u0435 \u043e\u0431\u043d\u0430\u0440\u0443\u0436\u0435\u043d\u0430",
"dhcp_config_saved": "\u0421\u043e\u0445\u0440\u0430\u043d\u0435\u043d\u043d\u0430\u044f \u043a\u043e\u043d\u0444\u0438\u0433\u0443\u0440\u0430\u0446\u0438\u044f DHCP-\u0441\u0435\u0440\u0432\u0435\u0440\u0430",
"form_error_required": "\u041e\u0431\u044f\u0437\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0435 \u043f\u043e\u043b\u0435",
"form_error_ip_format": "\u041d\u0435\u0432\u0435\u0440\u043d\u044b\u0439 \u0444\u043e\u0440\u043c\u0430\u0442 IPv4",
"form_error_positive": "\u0414\u043e\u043b\u0436\u043d\u043e \u0431\u044b\u0442\u044c \u0431\u043e\u043b\u044c\u0448\u0435 0",
"dhcp_form_gateway_input": "IP-\u0430\u0434\u0440\u0435\u0441 \u0448\u043b\u044e\u0437\u0430",
"dhcp_form_subnet_input": "\u041c\u0430\u0441\u043a\u0430 \u043f\u043e\u0434\u0441\u0435\u0442\u0438",
"dhcp_form_range_title": "\u0414\u0438\u0430\u043f\u0430\u0437\u043e\u043d IP-\u0430\u0434\u0440\u0435\u0441\u043e\u0432",
"dhcp_form_range_start": "\u041d\u0430\u0447\u0430\u043b\u043e \u0434\u0438\u0430\u043f\u0430\u0437\u043e\u043d\u0430",
"dhcp_form_range_end": "\u041a\u043e\u043d\u0435\u0446 \u0434\u0438\u0430\u043f\u0430\u0437\u043e\u043d\u0430",
"dhcp_form_lease_title": "\u0412\u0440\u0435\u043c\u044f \u0430\u0440\u0435\u043d\u0434\u044b DHCP (\u0432 \u0441\u0435\u043a\u0443\u043d\u0434\u0430\u0445)",
"dhcp_form_lease_input": "\u0421\u0440\u043e\u043a \u0430\u0440\u0435\u043d\u0434\u044b",
"dhcp_interface_select": "\u0412\u044b\u0431\u0440\u0430\u0442\u044c \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 DHCP",
"dhcp_hardware_address": "\u0410\u043f\u043f\u0430\u0440\u0430\u0442\u043d\u044b\u0439 \u0430\u0434\u0440\u0435\u0441",
"dhcp_ip_addresses": "IP-\u0430\u0434\u0440\u0435\u0441\u0430",
"dhcp_table_hostname": "\u0418\u043c\u044f \u0445\u043e\u0441\u0442\u0430",
"dhcp_table_expires": "\u0418\u0441\u0442\u0435\u043a\u0430\u0435\u0442",
"back": "\u041d\u0430\u0437\u0430\u0434",
"dashboard": "\u041f\u0430\u043d\u0435\u043b\u044c \u0443\u043f\u0440\u0430\u0432\u043b\u0435\u043d\u0438\u044f",
"settings": "\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438",
"filters": "\u0424\u0438\u043b\u044c\u0442\u0440\u044b",
"query_log": "\u0416\u0443\u0440\u043d\u0430\u043b",
"client_settings": "Настройки клиентов",
"example_upstream_reserved": "вы можете указать DNS-сервер <0>для конкретного домена(ов)</0>",
"upstream_parallel": "Использовать одновременные запроссы ко всем серверам для ускорения обработки запроса",
"bootstrap_dns": "Bootstrap DNS-серверы",
"bootstrap_dns_desc": "Bootstrap DNS-серверы используются для поиска IP-адресов DoH/DoT серверов, которые вы указали.",
"url_added_successfully": "URL успешно добавлен",
"check_dhcp_servers": "Проверить DHCP-серверы",
"save_config": "Сохранить конфигурацию",
"enabled_dhcp": "DHCP-сервер включен",
"disabled_dhcp": "DHCP-сервер отключен",
"dhcp_title": "DHCP-сервер (экспериментальный!)",
"dhcp_description": "Если ваш роутер не предоставляет настройки DHCP, вы можете использовать собственный встроенный DHCP-сервер AdGuard.",
"dhcp_enable": "Включить DHCP-сервер",
"dhcp_disable": "Отключить DHCP-сервер",
"dhcp_not_found": "Активные DHCP-серверы в сети не найдены. Вы можете безопасно включить встроенный сервер DHCP.",
"dhcp_found": "Некоторые активные DHCP-серверы найдены в сети. Включение встроенного DHCP-сервера небезопасно.",
"dhcp_leases": "Аренда DHCP",
"dhcp_static_leases": "Статические аренды DHCP",
"dhcp_leases_not_found": "Аренда DHCP не обнаружена",
"dhcp_config_saved": "Сохраненная конфигурация DHCP-сервера",
"form_error_required": "Обязательное поле",
"form_error_ip_format": "Неверный формат IPv4",
"form_error_mac_format": "Некорректный формат MAC",
"form_error_positive": "Должно быть больше 0",
"dhcp_form_gateway_input": "IP-адрес шлюза",
"dhcp_form_subnet_input": "Маска подсети",
"dhcp_form_range_title": "Диапазон IP-адресов",
"dhcp_form_range_start": "Начало диапазона",
"dhcp_form_range_end": "Конец диапазона",
"dhcp_form_lease_title": "Время аренды DHCP (в секундах)",
"dhcp_form_lease_input": "Срок аренды",
"dhcp_interface_select": "Выбрать интерфейс DHCP",
"dhcp_hardware_address": "Аппаратный адрес",
"dhcp_ip_addresses": "IP-адреса",
"dhcp_table_hostname": "Имя хоста",
"dhcp_table_expires": "Истекает",
"dhcp_warning": "Если вы все равно хотите включить DHCP-сервер, убедитесь, что в сети больше нет активных DHCP-серверов. Иначе это может сломать доступ в сеть для подключенных устройств!",
"dhcp_error": "Мы не смогли определить присутствие других DHCP-серверов в сети.",
"dhcp_static_ip_error": "Для того, чтобы использовать DHCP-сервер, должен быть установлен статический IP-адрес. Мы не смогли определить, использует ли этот сетевой интерфейс статический IP-адрес. Пожалуйста, установите его вручную.",
"dhcp_dynamic_ip_found": "Ваша система использует динамический IP-адрес для интерфейса <0>{{interfaceName}}</0>. Чтобы использовать DHCP-сервер необходимо установить статический IP-адрес. Ваш текущий IP-адрес - <0>{{ipAddress}}</0>. Мы автоматически установим его как статический ессли вы нажмете кнопку Включить DHCP.",
"dhcp_lease_added": "Статическая аренда \"{{key}}\" успешно добавлена",
"dhcp_lease_deleted": "Статическая аренда \"{{key}}\" успешно удалена",
"dhcp_new_static_lease": "Новая статическая аренда",
"dhcp_static_leases_not_found": "Не найдено статических аренд DHCP",
"dhcp_add_static_lease": "Добавить статическую аренду",
"delete_confirm": "Are you sure you want to delete \"{{key}}\"?",
"form_enter_hostname": "Введите имя хоста",
"error_details": "Детализация ошибки",
"back": "Назад",
"dashboard": "Панель управления",
"settings": "Настройки",
"filters": "Фильтры",
"query_log": "Журнал",
"faq": "FAQ",
"version": "\u0432\u0435\u0440\u0441\u0438\u044f",
"address": "\u0430\u0434\u0440\u0435\u0441",
"on": "\u0412\u043a\u043b",
"off": "\u0412\u044b\u043a\u043b",
"copyright": "\u0412\u0441\u0435 \u043f\u0440\u0430\u0432\u0430 \u0437\u0430\u0449\u0438\u0449\u0435\u043d\u044b",
"homepage": "\u0413\u043b\u0430\u0432\u043d\u0430\u044f",
"report_an_issue": "\u0421\u043e\u043e\u0431\u0449\u0438\u0442\u044c \u043e \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u0435",
"enable_protection": "\u0412\u043a\u043b\u044e\u0447\u0438\u0442\u044c \u0437\u0430\u0449\u0438\u0442\u0443",
"enabled_protection": "\u0417\u0430\u0449\u0438\u0442\u0430 \u0432\u043a\u043b.",
"disable_protection": "\u041e\u0442\u043a\u043b\u044e\u0447\u0438\u0442\u044c \u0437\u0430\u0449\u0438\u0442\u0443",
"disabled_protection": "\u0417\u0430\u0449\u0438\u0442\u0430 \u0432\u044b\u043a\u043b.",
"refresh_statics": "\u041e\u0431\u043d\u043e\u0432\u0438\u0442\u044c \u0441\u0442\u0430\u0442\u0438\u0441\u0442\u0438\u043a\u0443",
"dns_query": "DNS-\u0437\u0430\u043f\u0440\u043e\u0441\u044b",
"blocked_by": "\u0417\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u043d\u043e \u0444\u0438\u043b\u044c\u0442\u0440\u0430\u043c\u0438",
"stats_malware_phishing": "\u0417\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \u0432\u0440\u0435\u0434\u043e\u043d\u043e\u0441\u043d\u044b\u0435 \u0438 \u0444\u0438\u0448\u0438\u043d\u0433\u043e\u0432\u044b\u0435 \u0441\u0430\u0439\u0442\u044b",
"stats_adult": "\u0417\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \"\u0432\u0437\u0440\u043e\u0441\u043b\u044b\u0435\" \u0441\u0430\u0439\u0442\u044b",
"stats_query_domain": "\u0427\u0430\u0441\u0442\u043e \u0437\u0430\u043f\u0440\u0430\u0448\u0438\u0432\u0430\u0435\u043c\u044b\u0435 \u0434\u043e\u043c\u0435\u043d\u044b",
"for_last_24_hours": "\u0437\u0430 24 \u0447\u0430\u0441\u0430",
"no_domains_found": "\u0414\u043e\u043c\u0435\u043d\u044b \u043d\u0435 \u043d\u0430\u0439\u0434\u0435\u043d\u044b",
"requests_count": "\u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432",
"top_blocked_domains": "\u0427\u0430\u0441\u0442\u043e \u0431\u043b\u043e\u043a\u0438\u0440\u0443\u0435\u043c\u044b\u0435 \u0434\u043e\u043c\u0435\u043d\u044b",
"top_clients": "\u0427\u0430\u0441\u0442\u044b\u0435 \u043a\u043b\u0438\u0435\u043d\u0442\u044b",
"no_clients_found": "\u041a\u043b\u0438\u0435\u043d\u0442\u043e\u0432 \u043d\u0435 \u043d\u0430\u0439\u0434\u0435\u043d\u043e",
"general_statistics": "\u041e\u0431\u0449\u0430\u044f \u0441\u0442\u0430\u0442\u0438\u0441\u0442\u0438\u043a\u0430",
"number_of_dns_query_24_hours": "\u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e DNS-\u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432 \u0437\u0430 24 \u0447\u0430\u0441\u0430",
"number_of_dns_query_blocked_24_hours": "\u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e DNS-\u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432, \u0437\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u0444\u0438\u043b\u044c\u0442\u0440\u0430\u043c\u0438 \u0438 \u0431\u043b\u043e\u043a-\u0441\u043f\u0438\u0441\u043a\u0430\u043c\u0438",
"number_of_dns_query_blocked_24_hours_by_sec": "\u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e DNS-\u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432, \u0437\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u043c\u043e\u0434\u0443\u043b\u0435\u043c \u0410\u043d\u0442\u0438\u0444\u0438\u0448\u0438\u043d\u0433\u0430 AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "\u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0437\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \"\u0441\u0430\u0439\u0442\u043e\u0432 \u0434\u043b\u044f \u0432\u0437\u0440\u043e\u0441\u043b\u044b\u0445\"",
"enforced_save_search": "\u041f\u0440\u0438\u043c\u0435\u043d\u0435\u043d \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0439 \u043f\u043e\u0438\u0441\u043a",
"number_of_dns_query_to_safe_search": "\u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432 DNS \u0434\u043b\u044f \u043f\u043e\u0438\u0441\u043a\u043e\u0432\u044b\u0445 \u0441\u0438\u0441\u0442\u0435\u043c, \u0434\u043b\u044f \u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u0431\u044b\u043b \u043f\u0440\u0438\u043c\u0435\u043d\u0435\u043d \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0439 \u043f\u043e\u0438\u0441\u043a",
"average_processing_time": "\u0421\u0440\u0435\u0434\u043d\u0435\u0435 \u0432\u0440\u0435\u043c\u044f \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0438 \u0437\u0430\u043f\u0440\u043e\u0441\u0430",
"average_processing_time_hint": "\u0421\u0440\u0435\u0434\u043d\u0435\u0435 \u0432\u0440\u0435\u043c\u044f \u0434\u043b\u044f \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0438 \u0437\u0430\u043f\u0440\u043e\u0441\u0430 DNS \u0432 \u043c\u0438\u043b\u043b\u0438\u0441\u0435\u043a\u0443\u043d\u0434\u0430\u0445",
"block_domain_use_filters_and_hosts": "\u0411\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0434\u043e\u043c\u0435\u043d\u044b \u0441 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u0435\u043c \u0444\u0438\u043b\u044c\u0442\u0440\u043e\u0432 \u0438 \u0444\u0430\u0439\u043b\u043e\u0432 \u0445\u043e\u0441\u0442\u043e\u0432",
"filters_block_toggle_hint": "\u0412\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u043d\u0430\u0441\u0442\u0440\u043e\u0438\u0442\u044c \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u043a\u0438 \u0432 <a href='#filters'> \"\u0424\u0438\u043b\u044c\u0442\u0440\u0430\u0445\"<\/a>.",
"use_adguard_browsing_sec": "\u0418\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u0443\u044e \u043d\u0430\u0432\u0438\u0433\u0430\u0446\u0438\u044e AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442, \u0432\u043a\u043b\u044e\u0447\u0435\u043d \u043b\u0438 \u0434\u043e\u043c\u0435\u043d \u0432 \u0432\u0435\u0431-\u0441\u043b\u0443\u0436\u0431\u0443 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0441\u0442\u0438 \u0431\u0440\u0430\u0443\u0437\u0435\u0440\u0430. \u041e\u043d \u0431\u0443\u0434\u0435\u0442 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c API, \u0447\u0442\u043e\u0431\u044b \u0432\u044b\u043f\u043e\u043b\u043d\u0438\u0442\u044c \u043f\u0440\u043e\u0432\u0435\u0440\u043a\u0443: \u043d\u0430 \u0441\u0435\u0440\u0432\u0435\u0440 \u043e\u0442\u043f\u0440\u0430\u0432\u043b\u044f\u0435\u0442\u0441\u044f \u0442\u043e\u043b\u044c\u043a\u043e \u043a\u043e\u0440\u043e\u0442\u043a\u0438\u0439 \u043f\u0440\u0435\u0444\u0438\u043a\u0441 \u0438\u043c\u0435\u043d\u0438 \u0434\u043e\u043c\u0435\u043d\u0430 SHA256.",
"use_adguard_parental": "\u0418\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0439\u0442\u0435 \u043c\u043e\u0434\u0443\u043b\u044c \u0420\u043e\u0434\u0438\u0442\u0435\u043b\u044c\u0441\u043a\u043e\u0433\u043e \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u044f AdGuard ",
"use_adguard_parental_hint": "AdGuard Home \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442, \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442 \u043b\u0438 \u0434\u043e\u043c\u0435\u043d \u043c\u0430\u0442\u0435\u0440\u0438\u0430\u043b\u044b 18+. \u041e\u043d \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u0442\u043e\u0442 \u0436\u0435 API \u0434\u043b\u044f \u043e\u0431\u0435\u0441\u043f\u0435\u0447\u0435\u043d\u0438\u044f \u043a\u043e\u043d\u0444\u0438\u0434\u0435\u043d\u0446\u0438\u0430\u043b\u044c\u043d\u043e\u0441\u0442\u0438, \u0447\u0442\u043e \u0438 \u0432\u0435\u0431-\u0441\u043b\u0443\u0436\u0431\u0430 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0441\u0442\u0438 \u0431\u0440\u0430\u0443\u0437\u0435\u0440\u0430.",
"enforce_safe_search": "\u0423\u0441\u0438\u043b\u0438\u0442\u044c \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0439 \u043f\u043e\u0438\u0441\u043a",
"enforce_save_search_hint": "AdGuard Home \u043c\u043e\u0436\u0435\u0442 \u043e\u0431\u0435\u0441\u043f\u0435\u0447\u0438\u0442\u044c \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0439 \u043f\u043e\u0438\u0441\u043a \u0432 \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u0445 \u0441\u0438\u0441\u0442\u0435\u043c\u0430\u0445: Google, Youtube, Bing \u0438 Yandex.",
"no_servers_specified": "\u041d\u0435\u0442 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u044b\u0445 \u0441\u0435\u0440\u0432\u0435\u0440\u043e\u0432",
"no_settings": "\u041d\u0435\u0442 \u043d\u0430\u0441\u0442\u0440\u043e\u0435\u043a",
"general_settings": "\u041e\u0441\u043d\u043e\u0432\u043d\u044b\u0435 \u043d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0438",
"upstream_dns": "Upstream DNS-\u0441\u0435\u0440\u0432\u0435\u0440\u044b",
"upstream_dns_hint": "\u0415\u0441\u043b\u0438 \u0432\u044b \u043e\u0441\u0442\u0430\u0432\u0438\u0442\u0435 \u044d\u0442\u043e \u043f\u043e\u043b\u0435 \u043f\u0443\u0441\u0442\u044b\u043c, \u0442\u043e AdGuard Home \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> \u0432 \u043a\u0430\u0447\u0435\u0441\u0442\u0432\u0435 upstream. \u0418\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0439\u0442\u0435 tls:\/\/ \u0434\u043b\u044f DNS \u0447\u0435\u0440\u0435\u0437 \u0441\u0435\u0440\u0432\u0435\u0440\u044b TLS.",
"test_upstream_btn": "\u0422\u0435\u0441\u0442 upstream \u0441\u0435\u0440\u0432\u0435\u0440\u043e\u0432",
"apply_btn": "\u041f\u0440\u0438\u043c\u0435\u043d\u0438\u0442\u044c",
"disabled_filtering_toast": "\u0424\u0438\u043b\u044c\u0442\u0440\u0430\u0446\u0438\u044f \u0432\u044b\u043a\u043b.",
"enabled_filtering_toast": "\u0424\u0438\u043b\u044c\u0442\u0440\u0430\u0446\u0438\u044f \u0432\u043a\u043b.",
"disabled_safe_browsing_toast": "\u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u0430\u044f \u043d\u0430\u0432\u0438\u0433\u0430\u0446\u0438\u044f \u0432\u044b\u043a\u043b.",
"enabled_safe_browsing_toast": "\u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u0430\u044f \u043d\u0430\u0432\u0438\u0433\u0430\u0446\u0438\u044f \u0432\u043a\u043b.",
"disabled_parental_toast": "\u0420\u043e\u0434\u0438\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u0439 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u044c \u0432\u044b\u043a\u043b.",
"enabled_parental_toast": "\u0420\u043e\u0434\u0438\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u0439 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u044c \u0432\u043a\u043b.",
"disabled_safe_search_toast": "\u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0439 \u043f\u043e\u0438\u0441\u043a \u0432\u044b\u043a\u043b.",
"enabled_save_search_toast": "\u0411\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0439 \u043f\u043e\u0438\u0441\u043a \u0432\u043a\u043b.",
"enabled_table_header": "\u0412\u043a\u043b.",
"name_table_header": "\u0418\u043c\u044f",
"filter_url_table_header": "URL \u0444\u0438\u043b\u044c\u0442\u0440\u0430",
"rules_count_table_header": "\u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u043f\u0440\u0430\u0432\u0438\u043b:",
"last_time_updated_table_header": "\u041f\u043e\u0441\u043b\u0435\u0434\u043d\u0435\u0435 \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u0435",
"actions_table_header": "\u0414\u0435\u0439\u0441\u0442\u0432\u0438\u044f",
"delete_table_action": "\u0423\u0434\u0430\u043b\u0438\u0442\u044c",
"filters_and_hosts": "\u0424\u0438\u043b\u044c\u0442\u0440\u044b \u0438 \u0447\u0435\u0440\u043d\u044b\u0435 \u0441\u043f\u0438\u0441\u043a\u0438 hosts",
"filters_and_hosts_hint": "AdGuard Home \u0440\u0430\u0441\u043f\u043e\u0437\u043d\u0430\u0435\u0442 \u0431\u0430\u0437\u043e\u0432\u044b\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u043a\u0438 \u0438 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0441 \u0444\u0430\u0439\u043b\u043e\u0432 hosts.",
"no_filters_added": "\u0424\u0438\u043b\u044c\u0442\u0440\u044b \u043d\u0435 \u0434\u043e\u0431\u0430\u0432\u043b\u0435\u043d\u044b",
"add_filter_btn": "\u0414\u043e\u0431\u0430\u0432\u0438\u0442\u044c \u0444\u0438\u043b\u044c\u0442\u0440",
"cancel_btn": "\u041e\u0442\u043c\u0435\u043d\u0430",
"enter_name_hint": "\u0412\u0432\u0435\u0434\u0438\u0442\u0435 \u0438\u043c\u044f",
"enter_url_hint": "\u0412\u0432\u0435\u0434\u0438\u0442\u0435 URL",
"check_updates_btn": "\u041f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u044f",
"new_filter_btn": "\u0414\u043e\u0431\u0430\u0432\u043b\u0435\u043d\u0438\u0435 \u043d\u043e\u0432\u043e\u0433\u043e \u0444\u0438\u043b\u044c\u0442\u0440\u0430",
"enter_valid_filter_url": "\u0412\u0432\u0435\u0434\u0438\u0442\u0435 \u0434\u0435\u0439\u0441\u0442\u0432\u0443\u044e\u0449\u0438\u0439 URL \u0434\u043b\u044f \u043f\u043e\u0434\u043f\u0438\u0441\u043a\u0438 \u043d\u0430 \u0444\u0438\u043b\u044c\u0442\u0440 \u0438\u043b\u0438 \u0444\u0430\u0439\u043b hosts.",
"custom_filter_rules": "\u041f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0444\u0438\u043b\u044c\u0442\u0440\u0430\u0446\u0438\u0438",
"custom_filter_rules_hint": "\u0412\u0432\u043e\u0434\u0438\u0442\u0435 \u043f\u043e \u043e\u0434\u043d\u043e\u043c\u0443 \u043f\u0440\u0430\u0432\u0438\u043b\u0443 \u043d\u0430 \u0441\u0442\u0440\u043e\u0447\u043a\u0443. \u0412\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u043a\u0438 \u0438\u043b\u0438 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0441 \u0444\u0430\u0439\u043b\u043e\u0432 hosts.",
"examples_title": "\u041f\u0440\u0438\u043c\u0435\u0440\u044b",
"example_meaning_filter_block": "\u0437\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0434\u043e\u0441\u0442\u0443\u043f \u043a \u0434\u043e\u043c\u0435\u043d\u0443 example.org \u0438 \u0432\u0441\u0435\u043c \u0435\u0433\u043e \u043f\u043e\u0434\u0434\u043e\u043c\u0435\u043d\u0430\u043c",
"example_meaning_filter_whitelist": "\u0440\u0430\u0437\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0434\u043e\u0441\u0442\u0443\u043f \u043a \u0434\u043e\u043c\u0435\u043d\u0443 example.org \u0438 \u0432\u0441\u0435\u043c \u0435\u0433\u043e \u043f\u043e\u0434\u0434\u043e\u043c\u0435\u043d\u0430\u043c",
"example_meaning_host_block": "\u0422\u0435\u043f\u0435\u0440\u044c AdGuard Home \u0432\u0435\u0440\u043d\u0435\u0442 127.0.0.1 \u0434\u043b\u044f \u0434\u043e\u043c\u0435\u043d\u0430 example.org (\u043d\u043e \u043d\u0435 \u0434\u043b\u044f \u0435\u0433\u043e \u043f\u043e\u0434\u0434\u043e\u043c\u0435\u043d\u043e\u0432).",
"example_comment": "! \u0422\u0430\u043a \u043c\u043e\u0436\u043d\u043e \u0434\u043e\u0431\u0430\u0432\u043b\u044f\u0442\u044c \u043e\u043f\u0438\u0441\u0430\u043d\u0438\u0435",
"example_comment_meaning": "\u043a\u043e\u043c\u043c\u0435\u043d\u0442\u0430\u0440\u0438\u0439",
"example_comment_hash": "# \u0418 \u0432\u043e\u0442 \u0442\u0430\u043a \u0442\u043e\u0436\u0435",
"example_upstream_regular": "\u043e\u0431\u044b\u0447\u043d\u044b\u0439 DNS (\u043f\u043e\u0432\u0435\u0440\u0445 UDP)",
"example_upstream_dot": "\u0437\u0430\u0448\u0438\u0444\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0439 <0>DNS-\u043f\u043e\u0432\u0435\u0440\u0445-TLS<\/0>",
"example_upstream_doh": "\u0437\u0430\u0448\u0438\u0444\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0439 <0>DNS-\u043f\u043e\u0432\u0435\u0440\u0445-HTTPS<\/0>",
"example_upstream_sdns": "\u0432\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c <0>DNS Stamps<\/0> \u0434\u043b\u044f <1>DNSCrypt<\/1> \u0438\u043b\u0438 <2>DNS-over-HTTPS<\/2> \u0440\u0435\u0437\u043e\u043b\u0432\u0435\u0440\u043e\u0432",
"example_upstream_tcp": "\u043e\u0431\u044b\u0447\u043d\u044b\u0439 DNS (\u043f\u043e\u0432\u0435\u0440\u0445 TCP)",
"all_filters_up_to_date_toast": "\u0412\u0441\u0435 \u0444\u0438\u043b\u044c\u0442\u0440\u044b \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u044b",
"updated_upstream_dns_toast": "Upstream DNS-\u0441\u0435\u0440\u0432\u0435\u0440\u044b \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u044b",
"dns_test_ok_toast": "\u0423\u043a\u0430\u0437\u0430\u043d\u043d\u044b\u0435 \u0441\u0435\u0440\u0432\u0435\u0440\u044b DNS \u0440\u0430\u0431\u043e\u0442\u0430\u044e\u0442 \u043a\u043e\u0440\u0440\u0435\u043a\u0442\u043d\u043e",
"dns_test_not_ok_toast": "\u0421\u0435\u0440\u0432\u0435\u0440 \"{{key}}\": \u043d\u0435\u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c, \u043f\u0440\u043e\u0432\u0435\u0440\u044c\u0442\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u043e\u0441\u0442\u044c \u043d\u0430\u043f\u0438\u0441\u0430\u043d\u0438\u044f",
"unblock_btn": "\u0420\u0430\u0437\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u0442\u044c",
"block_btn": "\u0417\u0430\u0431\u043b\u043e\u043a\u0438\u0440\u043e\u0432\u0430\u0442\u044c",
"time_table_header": "\u0412\u0440\u0435\u043c\u044f",
"domain_name_table_header": "\u0414\u043e\u043c\u0435\u043d",
"type_table_header": "\u0422\u0438\u043f",
"response_table_header": "\u041e\u0442\u0432\u0435\u0442",
"client_table_header": "\u041a\u043b\u0438\u0435\u043d\u0442",
"empty_response_status": "\u041f\u0443\u0441\u0442\u043e",
"show_all_filter_type": "\u041f\u043e\u043a\u0430\u0437\u0430\u0442\u044c \u0432\u0441\u0435",
"show_filtered_type": "\u041f\u043e\u043a\u0430\u0437\u0430\u0442\u044c \u043e\u0442\u0444\u0438\u043b\u044c\u0442\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0435",
"no_logs_found": "\u041b\u043e\u0433\u0438 \u043d\u0435 \u043d\u0430\u0439\u0434\u0435\u043d\u044b",
"disabled_log_btn": "\u0416\u0443\u0440\u043d\u0430\u043b \u0444\u0438\u043b\u044c\u0442\u0440\u0430\u0446\u0438\u0438 \u0432\u044b\u043a\u043b.",
"download_log_file_btn": "\u0417\u0430\u0433\u0440\u0443\u0437\u0438\u0442\u044c \u043e\u0442\u0447\u0451\u0442",
"refresh_btn": "\u041e\u0431\u043d\u043e\u0432\u0438\u0442\u044c",
"enabled_log_btn": "\u0416\u0443\u0440\u043d\u0430\u043b \u0444\u0438\u043b\u044c\u0442\u0440\u0430\u0446\u0438\u0438 \u0432\u043a\u043b.",
"last_dns_queries": "\u041f\u043e\u0441\u043b\u0435\u0434\u043d\u0438\u0435 5000 DNS-\u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432",
"previous_btn": "\u041d\u0430\u0437\u0430\u0434",
"next_btn": "\u0412\u043f\u0435\u0440\u0451\u0434",
"loading_table_status": "\u0417\u0430\u0433\u0440\u0443\u0437\u043a\u0430...",
"page_table_footer_text": "\u0421\u0442\u0440\u0430\u043d\u0438\u0446\u0430",
"of_table_footer_text": "\u0438\u0437",
"rows_table_footer_text": "\u0441\u0442\u0440\u043e\u043a",
"updated_custom_filtering_toast": "\u0412\u043d\u0435\u0441\u0435\u043d\u044b \u0438\u0437\u043c\u0435\u043d\u0435\u043d\u0438\u044f \u0432 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u0430",
"rule_removed_from_custom_filtering_toast": "\u041f\u0440\u0430\u0432\u0438\u043b\u043e \u0443\u0434\u0430\u043b\u0435\u043d\u043e \u0438\u0437 \u0430\u0432\u0442\u043e\u0440\u0441\u043a\u043e\u0433\u043e \u0441\u043f\u0438\u0441\u043a\u0430 \u043f\u0440\u0430\u0432\u0438\u043b \u0444\u0438\u043b\u044c\u0442\u0440\u0430\u0446\u0438\u0438",
"rule_added_to_custom_filtering_toast": "\u041f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0434\u043e\u0431\u0430\u0432\u043b\u0435\u043d\u043e",
"query_log_disabled_toast": "\u0416\u0443\u0440\u043d\u0430\u043b \u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432 \u0432\u044b\u043a\u043b.",
"query_log_enabled_toast": "\u0416\u0443\u0440\u043d\u0430\u043b \u0437\u0430\u043f\u0440\u043e\u0441\u043e\u0432 \u0432\u043a\u043b.",
"source_label": "\u0418\u0441\u0442\u043e\u0447\u043d\u0438\u043a",
"found_in_known_domain_db": "\u041d\u0430\u0439\u0434\u0435\u043d \u0432 \u0431\u0430\u0437\u0435 \u0438\u0437\u0432\u0435\u0441\u0442\u043d\u044b\u0445 \u0434\u043e\u043c\u0435\u043d\u043e\u0432.",
"category_label": "\u041a\u0430\u0442\u0435\u0433\u043e\u0440\u0438\u044f",
"rule_label": "\u041f\u0440\u0430\u0432\u0438\u043b\u043e",
"filter_label": "\u0424\u0438\u043b\u044c\u0442\u0440",
"unknown_filter": "\u041d\u0435\u0438\u0437\u0432\u0435\u0441\u0442\u043d\u044b\u0439 \u0444\u0438\u043b\u044c\u0442\u0440 {{filterId}}"
"version": "версия",
"address": "адрес",
"on": "Вкл",
"off": "Выкл",
"copyright": "Все права защищены",
"homepage": "Главная",
"report_an_issue": "Сообщить о проблеме",
"privacy_policy": "Политика конфиденциальности",
"enable_protection": "Включить защиту",
"enabled_protection": "Защита вкл.",
"disable_protection": "Отключить защиту",
"disabled_protection": "Защита выкл.",
"refresh_statics": "Обновить статистику",
"dns_query": "DNS-запросы",
"blocked_by": "Заблокировано фильтрами",
"stats_malware_phishing": "Заблокированные вредоносные и фишинговые сайты",
"stats_adult": "Заблокированные \"взрослые\" сайты",
"stats_query_domain": "Часто запрашиваемые домены",
"for_last_24_hours": "за 24 часа",
"no_domains_found": "Домены не найдены",
"requests_count": "Количество запросов",
"top_blocked_domains": "Часто блокируемые домены",
"top_clients": "Частые клиенты",
"no_clients_found": "Клиентов не найдено",
"general_statistics": "Общая статистика",
"number_of_dns_query_24_hours": "Количество DNS-запросов за 24 часа",
"number_of_dns_query_blocked_24_hours": "Количество DNS-запросов, заблокированных фильтрами и блок-списками",
"number_of_dns_query_blocked_24_hours_by_sec": "Количество DNS-запросов, заблокированных модулем Антифишинга AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "Количество заблокированных \"сайтов для взрослых\"",
"enforced_save_search": "Применен безопасный поиск",
"number_of_dns_query_to_safe_search": "Количество запросов DNS для поисковых систем, для которых был применен Безопасный поиск",
"average_processing_time": "Среднее время обработки запроса",
"average_processing_time_hint": "Среднее время для обработки запроса DNS в миллисекундах",
"block_domain_use_filters_and_hosts": "Блокировать домены с использованием фильтров и файлов хостов",
"filters_block_toggle_hint": "Вы можете настроить правила блокировки в <a href='#filters'> \"Фильтрах\"</a>.",
"use_adguard_browsing_sec": "Использовать Безопасную навигацию AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home проверит, включен ли домен в веб-службу безопасности браузера. Он будет использовать API, чтобы выполнить проверку: на сервер отправляется только короткий префикс имени домена SHA256.",
"use_adguard_parental": "Используйте модуль Родительского контроля AdGuard ",
"use_adguard_parental_hint": "AdGuard Home проверит, содержит ли домен материалы 18+. Он использует тот же API для обеспечения конфиденциальности, что и веб-служба безопасности браузера.",
"enforce_safe_search": "Усилить безопасный поиск",
"enforce_save_search_hint": "AdGuard Home может обеспечить безопасный поиск в следующих системах: Google, Youtube, Bing и Yandex.",
"no_servers_specified": "Нет указанных серверов",
"no_settings": "Нет настроек",
"general_settings": "Основные настройки",
"dns_settings": "Настройки DNS",
"encryption_settings": "Настройки шифрования",
"dhcp_settings": "Настройки DHCP",
"upstream_dns": "Upstream DNS-серверы",
"upstream_dns_hint": "Если вы оставите это поле пустым, то AdGuard Home использует <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> в качестве upstream. Используйте tls:// для DNS через серверы TLS.",
"test_upstream_btn": "Тест upstream серверов",
"apply_btn": "Применить",
"disabled_filtering_toast": "Фильтрация выкл.",
"enabled_filtering_toast": "Фильтрация вкл.",
"disabled_safe_browsing_toast": "Безопасная навигация выкл.",
"enabled_safe_browsing_toast": "Безопасная навигация вкл.",
"disabled_parental_toast": "Родительский контроль выкл.",
"enabled_parental_toast": "Родительский контроль вкл.",
"disabled_safe_search_toast": "Безопасный поиск выкл.",
"enabled_save_search_toast": "Безопасный поиск вкл.",
"enabled_table_header": "Вкл.",
"name_table_header": "Имя",
"filter_url_table_header": "URL фильтра",
"rules_count_table_header": "Количество правил:",
"last_time_updated_table_header": "Последнее обновление",
"actions_table_header": "Действия",
"edit_table_action": "Редактировать",
"delete_table_action": "Удалить",
"filters_and_hosts": "Фильтры и черные списки hosts",
"filters_and_hosts_hint": "AdGuard Home распознает базовые правила блокировки и синтаксис файлов hosts.",
"no_filters_added": "Фильтры не добавлены",
"add_filter_btn": "Добавить фильтр",
"cancel_btn": "Отмена",
"enter_name_hint": "Введите имя",
"enter_url_hint": "Введите URL",
"check_updates_btn": "Проверить обновления",
"new_filter_btn": "Добавление нового фильтра",
"enter_valid_filter_url": "Введите действующий URL для подписки на фильтр или файл hosts.",
"custom_filter_rules": "Пользовательское правило фильтрации",
"custom_filter_rules_hint": "Вводите по одному правилу на строчку. Вы можете использовать правила блокировки или синтаксис файлов hosts.",
"examples_title": "Примеры",
"example_meaning_filter_block": "заблокировать доступ к домену example.org и всем его поддоменам",
"example_meaning_filter_whitelist": "разблокировать доступ к домену example.org и всем его поддоменам",
"example_meaning_host_block": "Теперь AdGuard Home вернет 127.0.0.1 для домена example.org (но не для его поддоменов).",
"example_comment": "! Так можно добавлять описание",
"example_comment_meaning": "комментарий",
"example_comment_hash": "# И вот так тоже",
"example_regex_meaning": "блокирует доступ к доменам, соответствующим <0>заданному регулярному выражению</0>",
"example_upstream_regular": "обычный DNS (поверх UDP)",
"example_upstream_dot": "зашифрованный <a href='https://en.wikipedia.org/wiki/DNS_over_TLS' target='_blank'>DNS-поверх-TLS</a>",
"example_upstream_doh": "зашифрованный <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-поверх-HTTPS</a>",
"example_upstream_sdns": "вы можете использовать <a href='https://dnscrypt.info/stamps/' target='_blank'>DNS Stamps</a> для <a href='https://dnscrypt.info/' target='_blank'>DNSCrypt</a> или <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a> резолверов",
"example_upstream_tcp": "обычный DNS (поверх TCP)",
"all_filters_up_to_date_toast": "Все фильтры обновлены",
"updated_upstream_dns_toast": "Upstream DNS-серверы обновлены",
"dns_test_ok_toast": "Указанные серверы DNS работают корректно",
"dns_test_not_ok_toast": "Сервер \"{{key}}\": невозможно использовать, проверьте правильность написания",
"unblock_btn": "Разблокировать",
"block_btn": "Заблокировать",
"time_table_header": "Время",
"domain_name_table_header": "Домен",
"type_table_header": "Тип",
"response_table_header": "Ответ",
"client_table_header": "Клиент",
"empty_response_status": "Пусто",
"show_all_filter_type": "Показать все",
"show_filtered_type": "Показать отфильтрованные",
"no_logs_found": "Логи не найдены",
"disabled_log_btn": "Журнал фильтрации выкл.",
"download_log_file_btn": "Загрузить отчёт",
"refresh_btn": "Обновить",
"enabled_log_btn": "Журнал фильтрации вкл.",
"last_dns_queries": "Последние 5000 DNS-запросов",
"previous_btn": "Назад",
"next_btn": "Вперёд",
"loading_table_status": "Загрузка...",
"page_table_footer_text": "Страница",
"of_table_footer_text": "из",
"rows_table_footer_text": "строк",
"updated_custom_filtering_toast": "Внесены изменения в пользовательские правила",
"rule_removed_from_custom_filtering_toast": "Правило удалено из авторского списка правил фильтрации",
"rule_added_to_custom_filtering_toast": "Пользовательское правило добавлено",
"query_log_disabled_toast": "Журнал запросов выкл.",
"query_log_enabled_toast": "Журнал запросов вкл.",
"source_label": "Источник",
"found_in_known_domain_db": "Найден в базе известных доменов.",
"category_label": "Категория",
"rule_label": "Правило",
"filter_label": "Фильтр",
"unknown_filter": "Неизвестный фильтр {{filterId}}",
"install_welcome_title": "Добро пожаловать в AdGuard Home!",
"install_welcome_desc": "AdGuard Home - это DNS-сервер, блокирующий рекламу и трекинг. Его цель - дать вам возможность контролировать всю вашу сеть и все подключенные устройства. Он не требует установки клиентских программ.",
"install_settings_title": "Веб-интерфейс администрирования",
"install_settings_listen": "Сетевой интерфейс",
"install_settings_port": "Порт",
"install_settings_interface_link": "Ваш веб-интерфейс администрирования AdGuard Home будет доступен по следующим адресам:",
"form_error_port": "Введите корректный порт",
"install_settings_dns": "DNS-сервер",
"install_settings_dns_desc": "Вам будет нужно настроить свои устройства или роутер на использование DNS-сервера на одном из следующих адресов:",
"install_settings_all_interfaces": "Все интерфейсы",
"install_auth_title": "Авторизация",
"install_auth_desc": "Рекомендуется настроить авторизацию по паролю для вашего веб-интерфейса администрирования AdGuard Home. Важно ограничить доступ к нему даже если он доступен только в вашей локальной сети.",
"install_auth_username": "Имя пользователя",
"install_auth_password": "Пароль",
"install_auth_confirm": "Подтвердить пароль",
"install_auth_username_enter": "Введите имя пользователя",
"install_auth_password_enter": "Введите пароль",
"install_step": "Шаг",
"install_devices_title": "Настройте ваши устройства",
"install_devices_desc": "Для того, чтобы использовать AdGuard Home, вам нужно настроить ваши устройства на его использование.",
"install_submit_title": "Поздравляем!",
"install_submit_desc": "Процедура настройки завершена и вы готовы начать использование AdGuard Home.",
"install_devices_router": "Роутер",
"install_devices_router_desc": "Такая настройка автоматически покроет все устройства, использующие ваш домашний роутер, и вам не нужно будет настраивать каждое из них в отдельности.",
"install_devices_address": "DNS-сервер AdGuard Home доступен по следующим адресам",
"install_devices_router_list_1": "Откройте настройки вашего роутера. Обычно вы можете открыть их в вашем браузере (например, http://192.168.0.1/ или http://192.168.1.1/). Вас могут попросить ввести пароль. Если вы не помните его, пароль часто можно сбросить, нажав на кнопку на самом роутере. Некоторые роутеры требуют специального приложения, которое в этом случае должно быть уже установлено на ваш компьютер или телефон.",
"install_devices_router_list_2": "Найдите настройки DHCP или DNS. Найдите буквы \"DNS\" рядом с текстовым полем, в которое можно ввести два или три ряда цифр, разделенных на 4 группы от одной до трёх цифр.",
"install_devices_router_list_3": "Введите туда адрес вашего AdGuard Home.",
"install_devices_windows_list_1": "Откройте Панель управления через меню \"Пуск\" или через поиск Windows.",
"install_devices_windows_list_2": "Откройте Панель управления через меню \"Пуск\" или через поиск Windows.",
"install_devices_windows_list_3": "В левой стороне экрана найдите \"Изменение параметров адаптера\" и кликните по нему.",
"install_devices_windows_list_4": "Выделите ваше активное подключение, затем кликните по нему правой клавишей мыши и выберите \"Свойства\".",
"install_devices_windows_list_5": "Найдите в списке пункт \"IP версии 4 (TCP/IP)\", выделите его и затем снова нажмите \"Свойства\".",
"install_devices_windows_list_6": "Выберите \"Использовать следующие адреса DNS-серверов\" и введите адрес AdGuard Home.",
"install_devices_macos_list_1": "Кликните по иконке Apple и перейдите в «Системные настройки».",
"install_devices_macos_list_2": "Кликните по иконке «Сеть».",
"install_devices_macos_list_3": "Выберите первое подключение в списке и нажмите кнопку «Дополнительно».",
"install_devices_macos_list_4": "Выберите вкладку «DNS» и добавьте адреса AdGuard Home.",
"install_devices_android_list_1": "В меню управления нажмите иконку «Настройки».",
"install_devices_android_list_2": "Выберите пункт «Wi-Fi». Появится экран со списком доступных сетей (настройка DNS недоступна для мобильных сетей).",
"install_devices_android_list_3": "Долгим нажатием по текущей сети вызовите меню, в котором нажмите «Изменить сеть».",
"install_devices_android_list_4": "На некоторых устройствах может потребоваться нажать «Расширенные настройки». Чтобы получить возможность изменять настройки DNS, вам потребуется переключить «Настройки IP» на «Пользовательские».",
"install_devices_android_list_5": "Теперь можно изменить поля «DNS 1» и «DNS 2». Введите в них адреса AdGuard Home.",
"install_devices_ios_list_1": "Войдите в меню настроек устройства.",
"install_devices_ios_list_2": "Выберите пункт «Wi-Fi» (для мобильных сетей ручная настройка DNS невозможна).",
"install_devices_ios_list_3": "Нажмите на название сети, к которой устройство подключено в данный момент.",
"install_devices_ios_list_4": "В поле «DNS» введите введите адреса AdGuard Home.",
"get_started": "Поехали",
"next": "Дальше",
"open_dashboard": "Открыть Панель управления",
"install_saved": "Успешно сохранено",
"encryption_title": "Шифрование",
"encryption_desc": "Поддержка шифрования (HTTPS/TLS) для DNS и веб-интерфейса администрирования",
"encryption_config_saved": "Настройки шифрования сохранены",
"encryption_server": "Имя сервера",
"encryption_server_enter": "Введите ваше доменное имя",
"encryption_server_desc": "Для использования HTTPS вам необходимо ввести имя сервера, которое подходит вашему SSL-сертификату.",
"encryption_redirect": "Автоматически перенаправлять на HTTPS",
"encryption_redirect_desc": "Если включено, AdGuard Home будет автоматически перенаправлять вас с HTTP на HTTPS адрес.",
"encryption_https": "Порт HTTPS",
"encryption_https_desc": "Если порт HTTPS настроен, веб-интерфейс администрирования AdGuard Home будет доступен через HTTPS, а также DNS-over-HTTPS сервер будет доступен по пути '/dns-query'.",
"encryption_dot": "Порт DNS-over-TLS",
"encryption_dot_desc": "Если этот порт настроен, AdGuard Home запустит DNS-over-TLS-сервер на этому порту.",
"encryption_certificates": "Сертификаты",
"encryption_certificates_desc": "Для использования шифрования вам необходимо предоставить валидную цепочку SSL-сертификатов для вашего домена. Вы можете получить бесплатный сертификат на <0>{{link}}</0> или вы можете купить его у одного из доверенных Центров Сертификации.",
"encryption_certificates_input": "Скопируйте сюда сертификаты в PEM-кодировке.",
"encryption_status": "Статус",
"encryption_expire": "Истекает",
"encryption_key": "Приватный ключ",
"encryption_key_input": "Скопируйте сюда приватный ключ в PEM-кодировке.",
"encryption_enable": "Включить шифрование (HTTPS, DNS-over-HTTPS и DNS-over-TLS)",
"encryption_enable_desc": "Если шифрование включено, веб-интерфейс AdGuard Home будет работать по HTTPS, а DNS-сервер будет также работать по DNS-over-HTTPS и DNS-over-TLS.",
"encryption_chain_valid": "Цепочка сертификатов валидна",
"encryption_chain_invalid": "Цепочка сертификатов не валидна",
"encryption_key_valid": "Валидный {{type}} приватный ключ",
"encryption_key_invalid": "Невалидный {{type}} приватный ключ",
"encryption_subject": "Субъект",
"encryption_issuer": "Издатель",
"encryption_hostnames": "Имена хостов",
"encryption_reset": "Вы уверены, что хотите сбросить настройки шифрования?",
"topline_expiring_certificate": "Ваш SSL-сертификат скоро истекает. Обновите <0>Настройки шифрования</0>.",
"topline_expired_certificate": "Ваш SSL-сертификат истек. Обновите <0>Настройки шифрования</0>.",
"form_error_port_range": "Введите значение порта из интервала 80-65535",
"form_error_port_unsafe": "Это - небезопасный порт",
"form_error_equal": "Не должны быть равны",
"form_error_password": "Пароли не совпадают",
"reset_settings": "Сбросить настройки",
"update_announcement": "AdGuard Home {{version}} уже доступна! <0>Нажмите сюда</0>, чтобы узнать больше.",
"setup_guide": "Инструкция по настройке",
"dns_addresses": "Адреса DNS",
"down": "Вниз",
"fix": "Исправить",
"dns_providers": "<0>Список известных DNS-провайдеров</0> на выбор.",
"update_now": "Обновить сейчас",
"update_failed": "Ошибка авто-обновления. Пожалуйста, <a href='https://github.com/AdguardTeam/AdGuardHome/wiki/Getting-Started#update'>следуйте инструкции</a> для обновления вручную.",
"processing_update": "Пожалуйста, подождите, AdGuard Home обновляется",
"clients_title": "Клиенты",
"clients_desc": "Настройте устройства, использующие AdGuard Home",
"settings_global": "Глобальные",
"settings_custom": "Свои",
"table_client": "Клиент",
"table_name": "Имя",
"save_btn": "Сохранить",
"client_add": "Добавить клиента",
"client_new": "Новый клиент",
"client_edit": "Редактировать клиента",
"client_identifier": "Идентификатор",
"ip_address": "IP-адрес",
"client_identifier_desc": "Клиенты могут быть идентифицированы по IP-адресу или MAC-адресу. Обратите внимание, что использование MAC как идентификатора, возможно только если AdGuard Home также является и <0>DHCP-сервером</0>",
"form_enter_ip": "Введите IP",
"form_enter_mac": "Введите MAC",
"form_client_name": "Введите имя клиента",
"client_global_settings": "Использовать глобальные настройки",
"client_deleted": "Клиент \"{{key}}\" успешно удален",
"client_added": "Клиент \"{{key}}\" успешно добавлен",
"client_updated": "Клиент \"{{key}}\" успешно обновлен",
"table_statistics": "Количество запросов (последние 24 часа)",
"clients_not_found": "Клиентов не найдено",
"client_confirm_delete": "Вы уверены, что хотите удалить клиента \"{{key}}\"?",
"filter_confirm_delete": "Вы уверены, что хотите удалить фильтр?",
"auto_clients_title": "Клиенты (runtime)",
"auto_clients_desc": "Данные о клиентах, которые используют AdGuard Home, но не хранятся в настройках",
"access_title": "Настройки доступа",
"access_desc": "Здесь вы можете настроить правила доступа к DNS-серверу AdGuard Home.",
"access_allowed_title": "Разрешенные клиенты",
"access_allowed_desc": "Список CIDR- или IP-адресов. Если он настроен, AdGuard Home будет принимать запросы только с этих IP-адресов.",
"access_disallowed_title": "Запрещенные клиенты",
"access_disallowed_desc": "Список CIDR- или IP-адресов. Если он настроек, AdGuard Home будет игнорировать запросы с этих IP-адресов.",
"access_blocked_title": "Заблокированные домены",
"access_blocked_desc": "Не путайте это с фильтрами. AdGuard Home будет игнорировать DNS-запросы с этими доменами.",
"access_settings_saved": "Настройки доступа успешно сохранены",
"updates_checked": "Проверка обновлений прошла успешно",
"updates_version_equal": "Версия AdGuard Home актуальна",
"check_updates_now": "Проверить обновления",
"dns_privacy": "Зашифрованный DNS",
"setup_dns_privacy_1": "<0>DNS-over-TLS:</0> Используйте строку <1>{{address}}</1>.",
"setup_dns_privacy_2": "<0>DNS-over-HTTPS:</0> Используйте строку <1>{{address}}</1>.",
"setup_dns_privacy_3": "<0>Обратите внимание, что зашифрованный DNS-протокол поддерживается только на Android 9. Для других операционных систем вам нужно будет установить дополнительное ПО.</0><0>Вот список ПО, которое вы можете использовать.</0>",
"setup_dns_privacy_android_1": "Android 9 нативно поддерживает DNS-over-TLS. Для настройки, перейдите в Настройки → Сеть и Интернет → Дополнительно → Персональный DNS сервер, и введите туда ваше доменное имя.",
"setup_dns_privacy_android_2": "<0>AdGuard для Android</0> поддерживает <1>DNS-over-HTTPS</1> и <1>DNS-over-TLS</1>.",
"setup_dns_privacy_android_3": "<0>Intra</0> добавляет поддержка <1>DNS-over-HTTPS</1> на Android.",
"setup_dns_privacy_ios_1": "<0>DNSCloak</0> поддерживает <1>DNS-over-HTTPS</1>, но для настройки его, вам будет нужно сгенерировать для него <2>DNS-отпечаток</2>.",
"setup_dns_privacy_ios_2": "<0>AdGuard для iOS</0> поддерживает <1>DNS-over-HTTPS</1> и <1>DNS-over-TLS</1>.",
"setup_dns_privacy_other_title": "Другие решения",
"setup_dns_privacy_other_1": "AdGuard Home сам может быть клиентом зашифрованного DNS на любой платформе.",
"setup_dns_privacy_other_2": "<0>dnsproxy</0> поддерживает все известные зашифрованные DNS-протоколы.",
"setup_dns_privacy_other_3": "<0>dnscrypt-proxy</0> поддерживает <1>DNS-over-HTTPS</1>.",
"setup_dns_privacy_other_4": "<0>Mozilla Firefox</0> поддерживает <1>DNS-over-HTTPS</1>.",
"setup_dns_privacy_other_5": "Вы можете найти еще варианты <0>тут</0> и <1>тут</1>.",
"setup_dns_notice": "Чтобы использовать <1>DNS-over-HTTPS</1> или <1>DNS-over-TLS</1>, вам нужно <0>настроить шифрование</0> в настройках AdGuard Home.",
"rewrite_added": "Правило перенаправления DNS для \"{{key}}\" успешно добавлено",
"rewrite_deleted": "Правило перенаправления DNS для \"{{key}}\" успешно удалено",
"rewrite_add": "Добавить правило перенаправления DNS",
"rewrite_not_found": "Не найдено правил перенаправления DNS",
"rewrite_confirm_delete": "Вы уверены, что хотите удалить правило перенаправления DNS для \"{{key}}\"?",
"rewrite_desc": "Позволяет легко настроить пользовательский DNS-ответ для определеннного домена.",
"rewrite_applied": "Применено правило перенаправления",
"dns_rewrites": "Перенаправления DNS",
"form_domain": "Введите домен",
"form_answer": "Введите IP адрес или домен",
"form_error_domain_format": "Неверный формат домена",
"form_error_answer_format": "Неверный формат ответа",
"configure": "Настроить",
"main_settings": "Основные настройки",
"block_services": "Выбрать заблокированные сервисы",
"blocked_services": "Заблокированные сервисы",
"blocked_services_desc": "Позволяет быстро заблокировать популярные сайты и сервисы.",
"blocked_services_saved": "Заблокированные сервисы успешно сохранены",
"blocked_services_global": "Использовать глобальные заблокированные сервисы",
"blocked_service": "Заблокированный сервис",
"block_all": "Заблокировать все",
"unblock_all": "Разблокировать все"
}

View File

@@ -1,135 +1,141 @@
{
"example_upstream_reserved": "du kan specificera DNS-uppström <0>för en specifik domän</0>",
"upstream_parallel": "Använd parallella förfrågningar för att snabba upp dessa på uppströmsservrar.",
"bootstrap_dns": "Bootstrap-DNS-servrar",
"bootstrap_dns_desc": "Bootstrap-DNS-servrar används för att slå upp DoH/DoT-resolvrarnas IP-adresser som du specificerat som uppström.",
"url_added_successfully": "URL tillagd utan fel",
"check_dhcp_servers": "Letar efter DHCP-servrar",
"save_config": "Spara inst\u00e4llningar",
"save_config": "Spara inställningar",
"enabled_dhcp": "DHCP-server aktiverad",
"disabled_dhcp": "Dhcp-server avaktiverad",
"dhcp_title": "DHCP-server (experimentell)",
"dhcp_description": "Om din router inte har inst\u00e4llningar f\u00f6r DHCP kan du anv\u00e4nda AdGuards inbyggda server.",
"dhcp_description": "Om din router inte har inställningar för DHCP kan du använda AdGuards inbyggda server.",
"dhcp_enable": "Aktivera DHCP.-server",
"dhcp_disable": "Avaktivera DHCP-server",
"dhcp_not_found": "Ingen aktiv DHCP-server hittades i n\u00e4tverkat.",
"dhcp_found": "N\u00e5gra aktiva DHCP-servar uppt\u00e4cktes. Det \u00e4r inte s\u00e4kert att aktivera inbyggda DHCP-servrar.",
"dhcp_not_found": "Ingen aktiv DHCP-server hittades i nätverkat.",
"dhcp_found": "Några aktiva DHCP-servar upptäcktes. Det är inte säkert att aktivera inbyggda DHCP-servrar.",
"dhcp_leases": "DHCP-lease",
"dhcp_leases_not_found": "Ingen DHCP-lease hittad",
"dhcp_config_saved": "Sparade inst\u00e4llningar f\u00f6r DHCP-servern",
"form_error_required": "Obligatoriskt f\u00e4lt",
"dhcp_config_saved": "Sparade inställningar för DHCP-servern",
"form_error_required": "Obligatoriskt fält",
"form_error_ip_format": "Ogiltigt IPv4-format",
"form_error_positive": "M\u00e5ste vara st\u00f6rre \u00e4n noll",
"form_error_positive": "Måste vara större än noll",
"dhcp_form_gateway_input": "Gateway-IP",
"dhcp_form_subnet_input": "Subnetmask",
"dhcp_form_range_title": "IP-adressgr\u00e4nser",
"dhcp_form_range_start": "Startgr\u00e4ns",
"dhcp_form_range_end": "Gr\u00e4nsslut",
"dhcp_form_range_title": "IP-adressgränser",
"dhcp_form_range_start": "Startgräns",
"dhcp_form_range_end": "Gränsslut",
"dhcp_form_lease_title": "DHCP-leasetid (i sekunder)",
"dhcp_form_lease_input": "Leasetid",
"dhcp_interface_select": "V\u00e4lj DHCP-gr\u00e4nssnitt",
"dhcp_hardware_address": "H\u00e5rdvaruadress",
"dhcp_interface_select": "Välj DHCP-gränssnitt",
"dhcp_hardware_address": "Hårdvaruadress",
"dhcp_ip_addresses": "IP-adresser",
"dhcp_table_hostname": "V\u00e4rdnamn",
"dhcp_table_expires": "Utg\u00e5r",
"dhcp_warning": "Om du vill koppla in den inbyggda DHCP-servern m\u00e5ste du f\u00f6rs\u00e4kra dig om att det finns n\u00e5gra andra DHCP-servar som i s\u00e5 fall riskerar att orsaka avbrott p\u00e5 internet!",
"dhcp_table_hostname": "Värdnamn",
"dhcp_table_expires": "Utgår",
"dhcp_warning": "Om du vill använda den inbyggda DHCP-servern ändå, se till att det inte finns några andra aktiva DHCP-servrar. Annars kan den störa internetanslutningen för anslutna enheter!",
"dhcp_error": "Vi kunde inte avgöra om det finns en till DHCP-server på nätverket.",
"dhcp_static_ip_error": "För att kunna använda en DHCP-server måste det finnas en statisk IP-adress. Vi kunde inte avgöra om nätverksgränssnittet är konfigurerat med en statisk IP-adress. Ställ in en statistik IP-adress manuellt.",
"dhcp_dynamic_ip_found": "Din enhet använder en dynamisk IP-adress för gränssnittet <0>{{interfaceName}}</0>. För att kunna använda DHCP-servern behövs en statisk IP-adress. Din nuvarande IP-adress är <0>{{ipAddress}}</0>. Vi kommer att göra denna IP-adress statisk automatiskt om du trycker på knappen \"Aktivera DHCP\".",
"error_details": "Felinformation",
"back": "Tiilbaka",
"dashboard": "Kontrollpanel",
"settings": "Inst\u00e4llningar",
"settings": "Inställningar",
"filters": "Filter",
"query_log": "F\u00f6rfr\u00e5gningslogg",
"faq": "FAQ",
"query_log": "Förfrågningslogg",
"version": "version",
"address": "adress",
"on": "P\u00c5",
"on": "PÅ",
"off": "AV",
"copyright": "Copyright",
"homepage": "Hemsida",
"report_an_issue": "Rapportera ett problem",
"enable_protection": "Koppla p\u00e5 skydd",
"enabled_protection": "Kopplade p\u00e5 skydd",
"privacy_policy": "Integritetspolicy",
"enable_protection": "Koppla skydd",
"enabled_protection": "Kopplade på skydd",
"disable_protection": "Koppla bort skydd",
"disabled_protection": "Kopplade bort skydd",
"refresh_statics": "Uppdatera statistik",
"dns_query": "DNS-f\u00f6rfr\u00e5gningar",
"dns_query": "DNS-förfrågningar",
"blocked_by": "Blockerat av filter",
"stats_malware_phishing": "Blockerad skadekod\/phising",
"stats_malware_phishing": "Blockerad skadekod/phising",
"stats_adult": "Blockerade vuxensajter",
"stats_query_domain": "Mest efters\u00f6kta dom\u00e4ner",
"stats_query_domain": "Mest eftersökta domäner",
"for_last_24_hours": "under de senaste 24 timamrna",
"no_domains_found": "Inga dom\u00e4ner hittade",
"requests_count": "F\u00f6rfr\u00e5gningsantal",
"top_blocked_domains": "Flest blockerade dom\u00e4ner",
"no_domains_found": "Inga domäner hittade",
"requests_count": "Förfrågningsantal",
"top_blocked_domains": "Flest blockerade domäner",
"top_clients": "Toppklienter",
"no_clients_found": "Inga hitatde klienter",
"general_statistics": "Allm\u00e4n statistik",
"number_of_dns_query_24_hours": "Ett antal DNS-f\u00f6rfr\u00e5gningar utf\u00f6rdes under de senaste 244 timamrna",
"number_of_dns_query_blocked_24_hours": "Ett antal DNS-f\u00f6rfr\u00e5gningar blockerades av annonsfilter och v\u00e4rdens bloceringsklistor",
"number_of_dns_query_blocked_24_hours_by_sec": "Ett antal DNS-f\u00f6rfr\u00e5gningar blockerades av AdGuards modul f\u00f6r surfs\u00e4kerhet",
"general_statistics": "Allmän statistik",
"number_of_dns_query_24_hours": "Ett antal DNS-förfrågningar utfördes under de senaste 244 timamrna",
"number_of_dns_query_blocked_24_hours": "Ett antal DNS-förfrågningar blockerades av annonsfilter och värdens bloceringsklistor",
"number_of_dns_query_blocked_24_hours_by_sec": "Ett antal DNS-förfrågningar blockerades av AdGuards modul för surfsäkerhet",
"number_of_dns_query_blocked_24_hours_adult": "Ett anta vuxensajter blockerades",
"enforced_save_search": "Aktivering av S\u00e4ker surf",
"number_of_dns_query_to_safe_search": "Ett antal DNS-f\u00f6rfr\u00e5gningar genomf\u00f6rdes p\u00e5 s\u00f6kmotorer med S\u00e4ker surf aktiverat",
"enforced_save_search": "Aktivering av Säker surf",
"number_of_dns_query_to_safe_search": "Ett antal DNS-förfrågningar genomfördes på sökmotorer med Säker surf aktiverat",
"average_processing_time": "Genomsnittlig processtid",
"average_processing_time_hint": "Genomsnittlig processtid i millisekunder f\u00f6r DNS-f\u00f6rfr\u00e5gning",
"block_domain_use_filters_and_hosts": "Blockera dom\u00e4ner med filter- och v\u00e4rdfiler",
"filters_block_toggle_hint": "Du kan st\u00e4lla in egna blockerings regler i <a href='#filters'>Filterinst\u00e4llningar<\/a>.",
"use_adguard_browsing_sec": "Amv\u00e4nd AdGuards webbservice f\u00f6r surfs\u00e4kerhet",
"use_adguard_browsing_sec_hint": "AdGuard Home kommer att kontrollera om en dom\u00e4n \u00e4r svartlistad i webbservicens surfs\u00e4kerhet. Med en integritetsv\u00e4nlig metod g\u00f6rs en API-lookup f\u00f6r att kontrollera : endast en kort prefix i dom\u00e4nnamnet SHA256 hash skickas till servern.",
"use_adguard_parental": "Anv\u00e4nda AdGuards webbservice f\u00f6r f\u00e4r\u00e4ldrakontroll",
"use_adguard_parental_hint": "AdGuard Home kommer att kontrollera dom\u00e4ner f\u00f6r inneh\u00e5ll av vuxenmaterial . Samma integritetsv\u00e4nliga metod f\u00f6r API-lookup som till\u00e4mpas i webbservicens surfs\u00e4kerhet anv\u00e4nds.",
"enforce_safe_search": "Till\u00e4mpa S\u00e4ker surf",
"enforce_save_search_hint": "AdGuard Home kan framtvinga s\u00e4ker surf i f\u00f6ljande s\u00f6kmoterer: Google, Youtube, Bing, och Yandex.",
"average_processing_time_hint": "Genomsnittlig processtid i millisekunder för DNS-förfrågning",
"block_domain_use_filters_and_hosts": "Blockera domäner med filter- och värdfiler",
"filters_block_toggle_hint": "Du kan ställa in egna blockerings regler i <a href='#filters'>Filterinställningar</a>.",
"use_adguard_browsing_sec": "Amvänd AdGuards webbservice för surfsäkerhet",
"use_adguard_browsing_sec_hint": "AdGuard Home kommer att kontrollera om en domän är svartlistad i webbservicens surfsäkerhet. Med en integritetsvänlig metod görs en API-lookup för att kontrollera : endast en kort prefix i domännamnet SHA256 hash skickas till servern.",
"use_adguard_parental": "Använda AdGuards webbservice för färäldrakontroll",
"use_adguard_parental_hint": "AdGuard Home kommer att kontrollera domäner för innehåll av vuxenmaterial . Samma integritetsvänliga metod för API-lookup som tillämpas i webbservicens surfsäkerhet används.",
"enforce_safe_search": "Tillämpa Säker surf",
"enforce_save_search_hint": "AdGuard Home kan framtvinga säker surf i följande sökmoterer: Google, Youtube, Bing, och Yandex.",
"no_servers_specified": "Inga servrar angivna",
"no_settings": "Inga inst\u00e4llningar",
"general_settings": "Allm\u00e4nna inst\u00e4llningar",
"no_settings": "Inga inställningar",
"general_settings": "Allmänna inställningar",
"upstream_dns": "Upstream DNS-servrar",
"upstream_dns_hint": "Om du l\u00e5ter f\u00e4ltet vara tomt kommer AdGuard Home att anv\u00e4nda <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> f\u00f6r upstream. Anv\u00e4nd tls:\/\/ prefix f\u00f6r DNS \u00f6ver TLS-servrar.",
"test_upstream_btn": "Testa uppstr\u00f6mmar",
"apply_btn": "Till\u00e4mpa",
"upstream_dns_hint": "Om du låter fältet vara tomt kommer AdGuard Home att använda <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> för uppström.",
"test_upstream_btn": "Testa uppströmmar",
"apply_btn": "Tillämpa",
"disabled_filtering_toast": "Filtrering bortkopplad",
"enabled_filtering_toast": "Filtrering inkopplad",
"disabled_safe_browsing_toast": "S\u00e4ker surfning bortkopplat",
"enabled_safe_browsing_toast": "S\u00e4ker surfning inkopplat",
"disabled_parental_toast": "F\u00f6r\u00e4ldrakontroll bortkopplat",
"enabled_parental_toast": "F\u00f6r\u00e4ldrakontroll inkopplat",
"disabled_safe_search_toast": "S\u00e4ker webbs\u00f6kning bortkopplat",
"enabled_save_search_toast": "S\u00e4ker webbs\u00f6kning inkopplat",
"disabled_safe_browsing_toast": "Säker surfning bortkopplat",
"enabled_safe_browsing_toast": "Säker surfning inkopplat",
"disabled_parental_toast": "Föräldrakontroll bortkopplat",
"enabled_parental_toast": "Föräldrakontroll inkopplat",
"disabled_safe_search_toast": "Säker webbsökning bortkopplat",
"enabled_save_search_toast": "Säker webbsökning inkopplat",
"enabled_table_header": "Inkopplat",
"name_table_header": "Namn",
"filter_url_table_header": "Filtrerar URL",
"rules_count_table_header": "Regelantal",
"last_time_updated_table_header": "Uppdaterades senast",
"actions_table_header": "\u00c5tg\u00e4rder",
"actions_table_header": "Åtgärder",
"delete_table_action": "Ta bort",
"filters_and_hosts": "Filtrerings- och v\u00e4rdlistor f\u00f6r blockering",
"filters_and_hosts_hint": "AdGuard till\u00e4mpar grundl\u00e4ggande annonsblockeringsregler och v\u00e4rdfiltersyntaxer",
"filters_and_hosts": "Filtrerings- och värdlistor för blockering",
"filters_and_hosts_hint": "AdGuard tillämpar grundläggande annonsblockeringsregler och värdfiltersyntaxer",
"no_filters_added": "Inga filter tillagda",
"add_filter_btn": "L\u00e4gg till filter",
"add_filter_btn": "Lägg till filter",
"cancel_btn": "Avbryt",
"enter_name_hint": "Skriv in namn",
"enter_url_hint": "Skriv in URL",
"check_updates_btn": "S\u00f6k efter uppdateringar",
"check_updates_btn": "Sök efter uppdateringar",
"new_filter_btn": "Nytt filterabonemang",
"enter_valid_filter_url": "Skriv in en giltigt URL till ett filterabonnemang eller v\u00e4rdfil.",
"enter_valid_filter_url": "Skriv in en giltigt URL till ett filterabonnemang eller värdfil.",
"custom_filter_rules": "Egna filterregler",
"custom_filter_rules_hint": "Skriv en regel per rad. Du kan anv\u00e4nda antingen annonsblockeringsregler eller v\u00e4rdfilssyntax.",
"custom_filter_rules_hint": "Skriv en regel per rad. Du kan använda antingen annonsblockeringsregler eller värdfilssyntax.",
"examples_title": "Exempel",
"example_meaning_filter_block": "blockera \u00e5tkomst till dom\u00e4n example.org domain och alla dess subdom\u00e4ner",
"example_meaning_filter_whitelist": "avblockera \u00e5tkomst till dom\u00e4n example.org domain och alla dess subdom\u00e4ner",
"example_meaning_host_block": "AdGuard Home kommer nu att returnera adress 127.0.0.1 f\u00f6r dom\u00e4nexemplet example.org (dock utan dess subdom\u00e4ner).",
"example_comment": "! H\u00e4r kommer en kommentar",
"example_meaning_filter_block": "blockera åtkomst till domän example.org domain och alla dess subdomäner",
"example_meaning_filter_whitelist": "avblockera åtkomst till domän example.org domain och alla dess subdomäner",
"example_meaning_host_block": "AdGuard Home kommer nu att returnera adress 127.0.0.1 för domänexemplet example.org (dock utan dess subdomäner).",
"example_comment": "! Här kommer en kommentar",
"example_comment_meaning": "Endast en kommentar",
"example_comment_hash": "# Ocks\u00e5 en kommentar",
"example_regex_meaning": "blockera \u00e5tkomst till en dom\u00e4n som matchar det angivna uttrycket",
"example_upstream_regular": "vanlig DNS (\u00f6ver UDP)",
"example_upstream_dot": "krypterat <0>DNS-over-TLS<\/0>",
"example_upstream_doh": "krypterat <0>DNS-over-HTTPS<\/0>",
"example_upstream_sdns": "Du kan anv\u00e4nda <0>DNS-stamps<\/0> f\u00f6r <1>DNSCrypt<\/1> eller <2>DNS-\u00f6ver-HTTPS<\/2>\n-resolvers",
"example_upstream_tcp": "vanlig DNS (\u00f6ver UDP)",
"all_filters_up_to_date_toast": "Alla filter \u00e4r redan aktuella",
"updated_upstream_dns_toast": "Uppdaterade uppstr\u00f6ms-dns-servrar",
"example_comment_hash": "# Också en kommentar",
"example_upstream_regular": "vanlig DNS (över UDP)",
"example_upstream_dot": "krypterat <a href='https://en.wikipedia.org/wiki/DNS_over_TLS' target='_blank'>DNS-over-TLS</a>",
"example_upstream_doh": "krypterat <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a>",
"example_upstream_sdns": "Du kan använda <a href='https://dnscrypt.info/stamps/' target='_blank'>DNS-stamps</a> för <a href='https://dnscrypt.info/' target='_blank'>DNSCrypt</a> eller <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-över-HTTPS</a>\n-resolvers",
"example_upstream_tcp": "vanlig DNS (över UDP)",
"all_filters_up_to_date_toast": "Alla filter är redan aktuella",
"updated_upstream_dns_toast": "Uppdaterade uppströms-dns-servrar",
"dns_test_ok_toast": "Angivna DNS servrar fungerar korrekt",
"dns_test_not_ok_toast": "Server \"{{key}}\": kunde inte anv\u00e4ndas. Var sn\u00e4ll och kolla att du skrivit in r\u00e4tt",
"dns_test_not_ok_toast": "Server \"{{key}}\": kunde inte användas. Var snäll och kolla att du skrivit in rätt",
"unblock_btn": "Avblockera",
"block_btn": "Blockera",
"time_table_header": "Tid",
"domain_name_table_header": "Dom\u00e4nnamn",
"domain_name_table_header": "Domännamn",
"type_table_header": "Typ",
"response_table_header": "Svar",
"client_table_header": "Klient",
@@ -139,112 +145,110 @@
"no_logs_found": "Inga logga funna",
"disabled_log_btn": "Koppla bort logg",
"download_log_file_btn": "Ladda ner loggfil",
"refresh_btn": "L\u00e4s in igen",
"refresh_btn": "Läs in igen",
"enabled_log_btn": "Koppla in logg",
"last_dns_queries": "De senaste 5000 DNS-anropen",
"previous_btn": "F\u00f6reg\u00e5ende",
"next_btn": "N\u00e4sta",
"loading_table_status": "L\u00e4ser in...",
"previous_btn": "Föregående",
"next_btn": "Nästa",
"loading_table_status": "Läser in...",
"page_table_footer_text": "Sida",
"of_table_footer_text": "av",
"rows_table_footer_text": "rader",
"updated_custom_filtering_toast": "Uppdaterade de egna filterreglerna",
"rule_removed_from_custom_filtering_toast": "Regel borttagen fr\u00e5n de egna filterreglerna",
"rule_removed_from_custom_filtering_toast": "Regel borttagen från de egna filterreglerna",
"rule_added_to_custom_filtering_toast": "Regel tillagd till de egna filterreglerna",
"query_log_disabled_toast": "F\u00f6rfr\u00e5gningsloggen bortkopplad",
"query_log_enabled_toast": "F\u00f6rfr\u00e5gningsloggen inkopplad",
"source_label": "K\u00e4lla",
"found_in_known_domain_db": "Hittad i dom\u00e4ndatabas.",
"query_log_disabled_toast": "Förfrågningsloggen bortkopplad",
"query_log_enabled_toast": "Förfrågningsloggen inkopplad",
"source_label": "Källa",
"found_in_known_domain_db": "Hittad i domändatabas.",
"category_label": "Kategori",
"rule_label": "Regel",
"filter_label": "Filter",
"unknown_filter": "Ok\u00e4nt filter {{filterId}}",
"install_welcome_title": "V\u00e4lkommen till AdGuard Home!",
"install_welcome_desc": "AdGuard Home \u00e4r en DNS-server f\u00f6r n\u00e4tverkst\u00e4ckande annons- och sp\u00e5rningsblockering. Dess syfte \u00e4r att de dig kontroll \u00f6ver hela n\u00e4tverket och alla dina enheter, utan behov av att anv\u00e4nda klientbaserade program.",
"install_settings_title": "Administrat\u00f6rens webbgr\u00e4nssnitt",
"install_settings_listen": "\u00d6vervakningsgr\u00e4nssnitt",
"install_settings_port": "Port",
"install_settings_interface_link": "Din administrat\u00f6rssida f\u00f6r AdGuard Home finns p\u00e5 f\u00f6ljande adresser:",
"unknown_filter": "Okänt filter {{filterId}}",
"install_welcome_title": "Välkommen till AdGuard Home!",
"install_welcome_desc": "AdGuard Home är en DNS-server för nätverkstäckande annons- och spårningsblockering. Dess syfte är att de dig kontroll över hela nätverket och alla dina enheter, utan behov av att använda klientbaserade program.",
"install_settings_title": "Administratörens webbgränssnitt",
"install_settings_listen": "Övervakningsgränssnitt",
"install_settings_interface_link": "Din administratörssida för AdGuard Home finns på följande adresser:",
"form_error_port": "Skriv in ett giltigt portnummer",
"install_settings_dns": "DNS-server",
"install_settings_dns_desc": "Du beh\u00f6ver st\u00e4lla in dina enheter eller din router f\u00f6r att anv\u00e4nda DNS-server p\u00e5 f\u00f6ljande adresser.",
"install_settings_all_interfaces": "Alla gr\u00e4nssnitt",
"install_settings_dns_desc": "Du behöver ställa in dina enheter eller din router för att använda DNS-server på följande adresser.",
"install_settings_all_interfaces": "Alla gränssnitt",
"install_auth_title": "Autentisering",
"install_auth_desc": "Det rekommenderas starkt att st\u00e4lla in l\u00f6senordsskydd till webbgr\u00e4nssnittets administrativa del i ditt AdGuard Home. \u00c4ven om den endast \u00e4r \u00e5tkomlig p\u00e5 ditt lokala n\u00e4tverk rekommenderas det \u00e4nd\u00e5 att skydda det mot o\u00f6nskad \u00e5tkomst.",
"install_auth_username": "Anv\u00e4ndarnamn",
"install_auth_password": "L\u00f6senord",
"install_auth_confirm": "Bekr\u00e4fta l\u00f6senord",
"install_auth_username_enter": "Skriv in anv\u00e4ndarnamn",
"install_auth_password_enter": "Skriv in l\u00f6senord",
"install_auth_desc": "Det rekommenderas starkt att ställa in lösenordsskydd till webbgränssnittets administrativa del i ditt AdGuard Home. Även om den endast är åtkomlig på ditt lokala nätverk rekommenderas det ändå att skydda det mot oönskad åtkomst.",
"install_auth_username": "Användarnamn",
"install_auth_password": "Lösenord",
"install_auth_confirm": "Bekräfta lösenord",
"install_auth_username_enter": "Skriv in användarnamn",
"install_auth_password_enter": "Skriv in lösenord",
"install_step": "Steg",
"install_devices_title": "St\u00e4ll in dina enheter",
"install_devices_desc": "F\u00f6r att kunna anv\u00e4nda AdGuard Home m\u00e5ste du s\u00e4lla in dina enheter f\u00f6r att utnyttja den.",
"install_devices_title": "Ställ in dina enheter",
"install_devices_desc": "För att kunna använda AdGuard Home måste du sälla in dina enheter för att utnyttja den.",
"install_submit_title": "Grattis!",
"install_submit_desc": "Inst\u00e4llningsproceduren \u00e4r klar och du kan b\u00f6rja anv\u00e4nda AdGuard Home.",
"install_devices_router": "Router",
"install_devices_router_desc": "Den h\u00e4r anpassningen kommer att automatiskt t\u00e4cka in alla de enheter som \u00e4r anslutna till din hemmarouter och du beh\u00f6ver d\u00e4rf\u00f6r inte konfigurera var och en individuellt.",
"install_devices_address": "AdGuard Home DNS-server t\u00e4cker f\u00f6ljande adresser",
"install_devices_router_list_1": "\u00d6ppna routern Inst\u00e4llningar. Vanligtvis f\u00e5r man \u00e5tkomst via en URL (http:\/\/192.168.0.1 eller 192.168.1.1)- Du kommer att bli ombes att ange ett l\u00f6senord. L\u00f6senordet kan st\u00e5 angivet p\u00e5 routerns bak- eller undersida. Om l\u00f6senordet \u00e4ndrats och du inte k\u00e4nner till det kan du \u00e5terst\u00e4lla med Reset-knappen. En del routrar kr\u00e4ver en s\u00e4rskild applikation som skall finnas p\u00e5 antingen din dator eller i din mobil.",
"install_devices_router_list_2": "Leta upp DHCP\/DNS-inst\u00e4llningarna. Titta efter DNS-tecken intill ett f\u00e4lt med tv\u00e5 eller tre upps\u00e4ttningar siffror, var och en uppdelade i grupper om fyra med en eller tre siffror.",
"install_submit_desc": "Inställningsproceduren är klar och du kan börja använda AdGuard Home.",
"install_devices_router_desc": "Den här anpassningen kommer att automatiskt täcka in alla de enheter som är anslutna till din hemmarouter och du behöver därför inte konfigurera var och en individuellt.",
"install_devices_address": "AdGuard Home DNS-server täcker följande adresser",
"install_devices_router_list_1": "Öppna routern Inställningar. Vanligtvis får man åtkomst via en URL (http://192.168.0.1 eller 192.168.1.1)- Du kommer att bli ombes att ange ett lösenord. Lösenordet kan stå angivet på routerns bak- eller undersida. Om lösenordet ändrats och du inte känner till det kan du återställa med Reset-knappen. En del routrar kräver en särskild applikation som skall finnas på antingen din dator eller i din mobil.",
"install_devices_router_list_2": "Leta upp DHCP/DNS-inställningarna. Titta efter DNS-tecken intill ett fält med två eller tre uppsättningar siffror, var och en uppdelade i grupper om fyra med en eller tre siffror.",
"install_devices_router_list_3": "Ange serveradressen till ditt AdGuard Home.",
"install_devices_windows_list_1": "\u00d6ppna Kontrollpanelen via Start eller Windows S\u00f6k.",
"install_devices_windows_list_2": "V\u00e4lj N\u00e4tverks och delningscenter, N\u00e4tverk och Internet.",
"install_devices_windows_list_3": "Leta upp \u00c4ndra n\u00e4tverkskortsalternativ",
"install_devices_windows_list_4": "Markera din aktiva anslutning. H\u00f6gerklicka p\u00e5 den och v\u00e4lj Egenskaper.",
"install_devices_windows_list_5": "Markera Internet Protocol Version 4 (TCP\/IP) och klicka p\u00e5 knappen Egenskaper.",
"install_devices_windows_list_6": "Markera Anv\u00e4nd f\u00f6ljande DNS-serveradresser och skriv in adresserna till ditt AdGuard Home.",
"install_devices_macos_list_1": "Klicka p\u00e5 Apple-ikonen och v\u00e4lj Systemalternativ.",
"install_devices_macos_list_2": "Klicka p\u00e5 N\u00e4tverk.",
"install_devices_macos_list_3": "V\u00e4lj den f\u00f6rsta anslutningen i listan och klicka p\u00e5 Avancerat.",
"install_devices_macos_list_4": "Klicka p\u00e5 DNS-fliken och skriv in AdGuard Homes serveradresser",
"install_devices_android_list_1": "V\u00e4lj Inst\u00e4llningar fr\u00e5n Androids hemknapp",
"install_devices_android_list_2": "Tryck p\u00e5 N\u00e4tverk och Internet, Wi-Fi. Alla tillg\u00e4ngliga n\u00e4tverk visas i en lista (det g\u00e5r inte all v\u00e4lja egen DNS p\u00e5 mobiln\u00e4tverk.",
"install_devices_android_list_3": "H\u00e5ll ner p\u00e5 n\u00e4tverksnamnet som du \u00e4r ansluten till och v\u00e4lj \u00c4ndra n\u00e4tverk.",
"install_devices_android_list_4": "P\u00e5 en del enheter kan du beh\u00f6va v\u00e4lja Avancerat f\u00f6r att komma \u00e5t ytterligare inst\u00e4llningar. F\u00f6r att \u00e4ndra p\u00e5 DNS-inst\u00e4llningar m\u00e5ste du byta IP-inst\u00e4llning fr\u00e5n DHCP till Statisk. P\u00e5 Android Pie v\u00e4ljs Privat DNS p\u00e5 N\u00e4tverk och internet.",
"install_devices_android_list_5": "\u00c4ndra DNS 1 och DNS 2 till serveradresserna f\u00f6r AdGuard Home.",
"install_devices_ios_list_1": "Tryck Inst\u00e4llningar fr\u00e5n hemsk\u00e4rmen.",
"install_devices_ios_list_2": "V\u00e4lj Wi_Fi p\u00e5 den v\u00e4nstra menyn (det g\u00e5r inte att st\u00e4lla in egen DNS f\u00f6r mobila n\u00e4tverk).",
"install_devices_ios_list_3": "Tryck p\u00e5 namnet p\u00e5 den aktiva anslutningen.",
"install_devices_ios_list_4": "Skriv in AdGuard Homes serveradresser i DNS-f\u00e4lten.",
"get_started": "Kom ig\u00e5ng",
"next": "N\u00e4sta",
"open_dashboard": "\u00d6ppna Kontrollbordet",
"install_devices_windows_list_1": "Öppna Kontrollpanelen via Start eller Windows Sök.",
"install_devices_windows_list_2": "Välj Nätverks och delningscenter, Nätverk och Internet.",
"install_devices_windows_list_3": "Leta upp Ändra nätverkskortsalternativ",
"install_devices_windows_list_4": "Markera din aktiva anslutning. Högerklicka på den och välj Egenskaper.",
"install_devices_windows_list_5": "Markera Internet Protocol Version 4 (TCP/IP) och klicka på knappen Egenskaper.",
"install_devices_windows_list_6": "Markera Använd följande DNS-serveradresser och skriv in adresserna till ditt AdGuard Home.",
"install_devices_macos_list_1": "Klicka på Apple-ikonen och välj Systemalternativ.",
"install_devices_macos_list_2": "Klicka på Nätverk.",
"install_devices_macos_list_3": "Välj den första anslutningen i listan och klicka på Avancerat.",
"install_devices_macos_list_4": "Klicka på DNS-fliken och skriv in AdGuard Homes serveradresser",
"install_devices_android_list_1": "Välj Inställningar från Androids hemknapp",
"install_devices_android_list_2": "Tryck på Nätverk och Internet, Wi-Fi. Alla tillgängliga nätverk visas i en lista (det går inte all välja egen DNS på mobilnätverk.",
"install_devices_android_list_3": "Håll ner på nätverksnamnet som du är ansluten till och välj Ändra nätverk.",
"install_devices_android_list_4": "På en del enheter kan du behöva välja Avancerat för att komma åt ytterligare inställningar. För att ändra på DNS-inställningar måste du byta IP-inställning från DHCP till Statisk. På Android Pie väljs Privat DNS på Nätverk och internet.",
"install_devices_android_list_5": "Ändra DNS 1 och DNS 2 till serveradresserna för AdGuard Home.",
"install_devices_ios_list_1": "Tryck Inställningar från hemskärmen.",
"install_devices_ios_list_2": "Välj Wi_Fi på den vänstra menyn (det går inte att ställa in egen DNS för mobila nätverk).",
"install_devices_ios_list_3": "Tryck på namnet på den aktiva anslutningen.",
"install_devices_ios_list_4": "Skriv in AdGuard Homes serveradresser i DNS-fälten.",
"get_started": "Kom igång",
"next": "Nästa",
"open_dashboard": "Öppna Kontrollbordet",
"install_saved": "Sparat utan fel",
"encryption_title": "Encryption",
"encryption_desc": "Encryption (HTTPS\/TLS) support for both DNS and admin web interface",
"encryption_config_saved": "Encryption config saved",
"encryption_server": "Server name",
"encryption_server_enter": "Enter your domain name",
"encryption_server_desc": "In order to use HTTPS, you need to enter the server name that matches your SSL certificate.",
"encryption_redirect": "Redirect to HTTPS automatically",
"encryption_redirect_desc": "If checked, AdGuard Home will automatically redirect you from HTTP to HTTPS addresses.",
"encryption_https": "HTTPS port",
"encryption_https_desc": "If HTTPS port is configured, AdGuard Home admin interface will be accessible via HTTPS, and it will also provide DNS-over-HTTPS on '\/dns-query' location.",
"encryption_dot": "DNS-over-TLS port",
"encryption_dot_desc": "If this port is configured, AdGuard Home will run a DNS-over-TLS server on this port.",
"encryption_certificates": "Certificates",
"encryption_certificates_desc": "In order to use encryption, you need to provide a valid SSL certificates chain for your domain. You can get a free certificate on <0>{{link}}<\/0> or you can buy it from one of the trusted Certificate Authorities.",
"encryption_certificates_input": "Copy\/paste your PEM-encoded certificates here.",
"encryption_status": "Status",
"encryption_expire": "Expires",
"encryption_key": "Private key",
"encryption_key_input": "Copy\/paste your PEM-encoded private key for your certificate here.",
"encryption_enable": "Enable Encryption (HTTPS, DNS-over-HTTPS, and DNS-over-TLS)",
"encryption_enable_desc": "If encryption is enabled, AdGuard Home admin interface will work over HTTPS, and the DNS server will listen for requests over DNS-over-HTTPS and DNS-over-TLS.",
"encryption_chain_valid": "Certificate chain is valid",
"encryption_chain_invalid": "Certificate chain is invalid",
"encryption_key_valid": "This is a valid {{type}} private key",
"encryption_key_invalid": "This is an invalid {{type}} private key",
"encryption_subject": "Subject",
"encryption_issuer": "Issuer",
"encryption_hostnames": "Hostnames",
"encryption_reset": "Are you sure you want to reset encryption settings?",
"topline_expiring_certificate": "Your SSL certificate is about to expire. Update <0>Encryption settings<\/0>.",
"topline_expired_certificate": "Your SSL certificate is expired. Update <0>Encryption settings<\/0>.",
"form_error_port_range": "Enter port value in the range of 80-65535",
"form_error_port_unsafe": "This is an unsafe port",
"form_error_equal": "Shouldn't be equal",
"form_error_password": "L\u00f6senorden \u00f6verensst\u00e4mmer inte",
"reset_settings": "Reset settings",
"update_announcement": "AdGuard Home {{version}} is now available! <0>Click here<\/0> for more info."
"encryption_title": "Kryptering",
"encryption_desc": "Krypteringsstöd (HTTPS/TLS) för både DNS och adminwebbgränssnitt.",
"encryption_config_saved": "Krypteringsinställningar sparade",
"encryption_server": "Servernamn",
"encryption_server_enter": "Skriv in ditt domännamn",
"encryption_server_desc": "För att använda HTTPS behöver du skriva in servernamnet som stämmer överens med ditt SSL-certifikat.",
"encryption_redirect": "Omdirigera till HTTPS automatiskt",
"encryption_redirect_desc": "Om bockad kommer AdGuard Home automatiskt att omdirigera dig från HTTP till HTTPS-adresser.",
"encryption_https": "HTTPS-port",
"encryption_https_desc": "Om en HTTPS-port är inställd kommer gränssnittet till AdGuard Home administrering att kunna nås via HTTPS och kommer också att erbjuda DNS-over-HTTPS '/dns-query' plats.",
"encryption_dot": "DNS-över-TLS port",
"encryption_dot_desc": "Om den här porten ställs in kommer AdGuard Home att använda DNS-over-TLS-server porten.",
"encryption_certificates": "Certifikat",
"encryption_certificates_desc": "För att använda kryptering måste du ange ett giltigt SSL-certifikat för din domän. Du kan skaffa ett certifikat gratis på <0>{{link}}</0> eller köpa ett från någon av de godkända certifikatutfärdare.",
"encryption_certificates_input": "Kopiera/klistra in dina PEM-kodade certifikat här.",
"encryption_expire": "Utgår",
"encryption_key": "Privat nyckel",
"encryption_key_input": "Kopiera/klistra in din PEM-kodade privata nyckel för ditt certifikat här.",
"encryption_enable": "Aktivera kryptering (HTTPS, DNS-över-HTTPS och DNS-över-TLS)",
"encryption_enable_desc": "Om kryptering är aktiverat kommer administratörsgränssnittet till AdGuard Home att köras över HTTPS och DNS-servern kommer att lyssna på förfrågningar över DNS-over-HTTPS och DNS-over-TLS.",
"encryption_chain_valid": "Certifikatkedjan är giltig",
"encryption_chain_invalid": "Certifikatkedjan är ogiltig",
"encryption_key_valid": "Det här är en giltig {{type}} privat nyckel",
"encryption_key_invalid": "Det här är en ogiltig {{type}} privat nyckel",
"encryption_subject": "Subjekt",
"encryption_issuer": "Utgivare",
"encryption_hostnames": "Värdnamn",
"encryption_reset": "Är du säker på att du vill återställa krypteringsinställningarna?",
"topline_expiring_certificate": "Ditt SSL-certifikat håller på att gå ut. <0>Krypteringsinställningar</0>.",
"topline_expired_certificate": "Ditt SSL-certifikat har gått ut. Uppdatera <0>Krypteringsinställningar</0>-",
"form_error_port_range": "Ange ett portnummer inom värdena 80-65535",
"form_error_port_unsafe": "Det här är en osäker port",
"form_error_equal": "Skall inte vara lika",
"form_error_password": "Lösenorden överensstämmer inte",
"reset_settings": "Återställ inställningar",
"update_announcement": "AdGuard Home {{version}} är nu tillgänglig! <0>Klicka här</0> för mer information.",
"setup_guide": "Inställningsguide",
"dns_addresses": "DNS-adresser"
}

View File

@@ -1,158 +1,144 @@
{
"check_dhcp_servers": "Ki\u1ec3m tra m\u00e1y ch\u1ee7 DHCP",
"save_config": "L\u01b0u thi\u1ebft l\u1eadp",
"enabled_dhcp": "M\u00e1y ch\u1ee7 DHCP \u0111\u00e3 k\u00edch ho\u1ea1t",
"disabled_dhcp": "M\u00e1y ch\u1ee7 DHCP \u0111\u00e3 t\u1eaft",
"dhcp_title": "M\u00e1y ch\u1ee7 DHCP (th\u1eed nghi\u1ec7m!)",
"dhcp_description": "N\u1ebfu b\u1ed9 \u0111\u1ecbnh tuy\u1ebfn kh\u00f4ng tr\u1ee3 c\u00e0i \u0111\u1eb7t DHCP, b\u1ea1n c\u00f3 th\u1ec3 d\u00f9ng m\u00e1y ch\u1ee7 DHCP d\u1ef1ng s\u1eb5n c\u1ee7a AdGuard",
"dhcp_enable": "B\u1eadt m\u00e1y ch\u1ee7 DHCP",
"dhcp_disable": "T\u1eaft m\u00e1y ch\u1ee7 DHCP",
"dhcp_not_found": "Kh\u00f4ng c\u00f3 m\u00e1y ch\u1ee7 DHCP n\u00e0o \u0111\u01b0\u1ee3c t\u00ecm th\u1ea5y trong m\u1ea1ng. C\u00f3 th\u1ec3 b\u1eadt m\u00e1y ch\u1ee7 DHCP m\u1ed9t c\u00e1ch an to\u00e0n",
"dhcp_found": "\u0110\u00e3 t\u00ecm th\u1ea5y m\u00e1y ch\u1ee7 DHCP trong m\u1ea1ng. C\u00f3 th\u1ec3 c\u00f3 r\u1ee7i ro n\u1ebfu k\u00edch ho\u1ea1t m\u00e1y ch\u1ee7 DHCP d\u1ef1ng s\u1eb5n",
"dhcp_leases": "DHCP leases",
"dhcp_leases_not_found": "No DHCP leases found",
"dhcp_config_saved": "Saved DHCP server config",
"form_error_required": "Required field",
"form_error_ip_format": "Invalid IPv4 format",
"form_error_positive": "Ph\u1ea3i l\u1edbn h\u01a1n 0",
"dhcp_form_gateway_input": "Gateway IP",
"dhcp_form_subnet_input": "Subnet mask",
"dhcp_form_range_title": "Range of IP addresses",
"dhcp_form_range_start": "Range start",
"dhcp_form_range_end": "IP k\u1ebft th\u00fac",
"dhcp_form_lease_title": "DHCP lease time (in seconds)",
"dhcp_form_lease_input": "Lease duration",
"dhcp_interface_select": "Ch\u1ecdn m\u1ed9t card m\u1ea1ng",
"dhcp_hardware_address": "Hardware address",
"dhcp_ip_addresses": "IP addresses",
"back": "Quay l\u1ea1i",
"dashboard": "T\u1ed5ng quan",
"settings": "C\u00e0i \u0111\u1eb7t",
"filters": "B\u1ed9 l\u1ecdc",
"query_log": "L\u1ecbch s\u1eed truy v\u1ea5n",
"faq": "H\u1ecfi \u0111\u00e1p",
"version": "phi\u00ean b\u1ea3n",
"address": "\u0111\u1ecba ch\u1ec9",
"on": "\u0110ang b\u1eadt",
"off": "\u0110ang t\u1eaft",
"copyright": "B\u1ea3n quy\u1ec1n",
"homepage": "Trang ch\u1ee7",
"report_an_issue": "B\u00e1o l\u1ed7i",
"enable_protection": "B\u1eadt b\u1ea3o v\u1ec7",
"enabled_protection": "\u0110\u00e3 b\u1eadt b\u1ea3o v\u1ec7",
"disable_protection": "T\u1eaft b\u1ea3o v\u1ec7",
"disabled_protection": "\u0110\u00e3 t\u1eaft b\u1ea3o v\u1ec7",
"refresh_statics": "L\u00e0m m\u1edbi th\u1ed1ng k\u00ea",
"dns_query": "Truy v\u1ea5n DNS",
"blocked_by": "Ch\u1eb7n b\u1edfi b\u1ed9 l\u1ecdc",
"stats_malware_phishing": "M\u00e3 \u0111\u1ed9c\/l\u1eeba \u0111\u1ea3o \u0111\u00e3 ch\u1eb7n",
"stats_adult": "Website ng\u01b0\u1eddi l\u1edbn \u0111\u00e3 ch\u1eb7n",
"stats_query_domain": "T\u00ean mi\u1ec1n truy v\u1ea5n nhi\u1ec1u",
"for_last_24_hours": "trong 24 gi\u1edd qua",
"no_domains_found": "Kh\u00f4ng c\u00f3 t\u00ean mi\u1ec1n n\u00e0o",
"requests_count": "S\u1ed1 l\u1ea7n y\u00eau c\u1ea7u",
"top_blocked_domains": "T\u00ean mi\u1ec1n ch\u1eb7n nhi\u1ec1u",
"top_clients": "Client d\u00f9ng nhi\u1ec1u",
"no_clients_found": "Kh\u00f4ng c\u00f3 client n\u00e0o",
"general_statistics": "Th\u1ed1ng k\u00ea chung",
"number_of_dns_query_24_hours": "S\u1ed1 y\u00eau c\u1ea7u DNS \u0111\u00e3 x\u1eed l\u00fd trong 24 gi\u1edd qua",
"number_of_dns_query_blocked_24_hours": "S\u1ed1 y\u00eau c\u1ea7u DNS b\u1ecb ch\u1eb7n b\u1edfi b\u1ed9 l\u1ecdc qu\u1ea3ng c\u00e1o v\u00e0 danh s\u00e1ch ch\u1eb7n host",
"number_of_dns_query_blocked_24_hours_by_sec": "S\u1ed1 y\u00eau c\u1ea7u DNS b\u1ecb ch\u1eb7n b\u1edfi ch\u1ebf \u0111\u1ed9 b\u1ea3o v\u1ec7 duy\u1ec7t web AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "S\u1ed1 website ng\u01b0\u1eddi l\u1edbn \u0111\u00e3 ch\u1eb7n",
"enforced_save_search": "T\u00ecm ki\u1ebfm an to\u00e0n",
"number_of_dns_query_to_safe_search": "S\u1ed1 y\u00eau c\u1ea7u DNS t\u1edbi c\u00f4ng c\u1ee5 t\u00ecm ki\u1ebfm \u0111\u00e3 chuy\u1ec3n th\u00e0nh t\u00ecm ki\u1ebfm an to\u00e0n",
"average_processing_time": "Th\u1eddi gian x\u1eed l\u00fd trung b\u00ecnh",
"average_processing_time_hint": "Th\u1eddi gian trung b\u00ecnh cho m\u1ed9t y\u00eau c\u1ea7u DNS t\u00ednh b\u1eb1ng mili gi\u00e2y",
"block_domain_use_filters_and_hosts": "Ch\u1eb7n t\u00ean mi\u1ec1n s\u1eed d\u1ee5ng c\u00e1c b\u1ed9 l\u1ecdc v\u00e0 file hosts",
"filters_block_toggle_hint": "B\u1ea1n c\u00f3 th\u1ec3 thi\u1ebft l\u1eadp quy t\u1eafc ch\u1eb7n t\u1ea1i c\u00e0i \u0111\u1eb7t <a href='#filters'>B\u1ed9 l\u1ecdc<\/a>.",
"use_adguard_browsing_sec": "S\u1eed d\u1ee5ng d\u1ecbch v\u1ee5 b\u1ea3o v\u1ec7 duy\u1ec7t web AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home s\u1ebd ki\u1ec3m tra t\u00ean mi\u1ec1n v\u1edbi d\u1ecbch v\u1ee5 b\u1ea3o v\u1ec7 duy\u1ec7t web. T\u00ednh n\u0103ng s\u1eed d\u1ee5ng m\u1ed9t API th\u00e2n thi\u1ec7n v\u1edbi quy\u1ec1n ri\u00eang t\u01b0: ch\u1ec9 m\u1ed9t ph\u1ea7n ng\u1eafn ti\u1ec1n t\u1ed1 m\u00e3 b\u0103m SHA256 \u0111\u01b0\u1ee3c g\u1eedi \u0111\u1ebfn m\u00e1y ch\u1ee7",
"use_adguard_parental": "S\u1eed d\u1ee5ng d\u1ecbch v\u1ee5 qu\u1ea3n l\u00fd c\u1ee7a ph\u1ee5 huynh AdGuard",
"use_adguard_parental_hint": "AdGuard Home s\u1ebd ki\u1ec3m tra n\u1ebfu t\u00ean mi\u1ec1n ch\u1ee9a t\u1eeb kho\u00e1 ng\u01b0\u1eddi l\u1edbn. T\u00ednh n\u0103ng s\u1eed d\u1ee5ng API th\u00e2n thi\u1ec7n v\u1edbi quy\u1ec1n ri\u00eang t\u01b0 t\u01b0\u01a1ng t\u1ef1 v\u1edbi d\u1ecbch v\u1ee5 b\u1ea3o v\u1ec7 duy\u1ec7t web",
"enforce_safe_search": "B\u1eaft bu\u1ed9c t\u00ecm ki\u1ebfm an to\u00e0n",
"enforce_save_search_hint": "AdGuard Home c\u00f3 th\u1ec3 b\u1eaft bu\u1ed9c t\u00ecm ki\u1ebfm an to\u00e0n v\u1edbi c\u00e1c d\u1ecbch v\u1ee5 t\u00ecm ki\u1ebfm: Google, Youtube, Bing, Yandex.",
"no_servers_specified": "Kh\u00f4ng c\u00f3 m\u00e1y ch\u1ee7 n\u00e0o \u0111\u01b0\u1ee3c li\u1ec7t k\u00ea",
"no_settings": "Kh\u00f4ng c\u00f3 c\u00e0i \u0111\u1eb7t n\u00e0o",
"general_settings": "C\u00e0i \u0111\u1eb7t chung",
"upstream_dns": "M\u00e1y ch\u1ee7 DNS t\u00ecm ki\u1ebfm",
"upstream_dns_hint": "N\u1ebfu b\u1ea1n \u0111\u1ec3 tr\u1ed1ng m\u1ee5c n\u00e0y, AdGuard Home s\u1ebd s\u1eed d\u1ee5ng <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> \u0111\u1ec3 t\u00ecm ki\u1ebfm. S\u1eed d\u1ee5ng ti\u1ec1n t\u1ed1 tls:\/\/ cho c\u00e1c m\u00e1y ch\u1ee7 DNS d\u1ef1a tr\u00ean TLS.",
"test_upstream_btn": "Ki\u1ec3m tra",
"apply_btn": "\u00c1p d\u1ee5ng",
"disabled_filtering_toast": "\u0110\u00e3 t\u1eaft ch\u1eb7n qu\u1ea3ng c\u00e1o",
"enabled_filtering_toast": "\u0110\u00e3 b\u1eadt ch\u1eb7n qu\u1ea3ng c\u00e1o",
"disabled_safe_browsing_toast": "\u0110\u00e3 t\u1eaft b\u1ea3o v\u1ec7 duy\u1ec7t web",
"enabled_safe_browsing_toast": "\u0110\u00e3 b\u1eadt b\u1ea3o v\u1ec7 duy\u1ec7t web",
"disabled_parental_toast": "\u0110\u00e3 t\u1eaft qu\u1ea3n l\u00fd c\u1ee7a ph\u1ee5 huynh",
"enabled_parental_toast": "\u0110\u00e3 b\u1eadt qu\u1ea3n l\u00fd c\u1ee7a ph\u1ee5 huynh",
"disabled_safe_search_toast": "\u0110\u00e3 t\u1eaft t\u00ecm ki\u1ebfm an to\u00e0n",
"enabled_save_search_toast": "\u0110\u00e3 b\u1eadt t\u00ecm ki\u1ebfm an to\u00e0n",
"enabled_table_header": "K\u00edch ho\u1ea1t",
"name_table_header": "T\u00ean",
"filter_url_table_header": "URL b\u1ed9 l\u1ecdc",
"rules_count_table_header": "S\u1ed1 quy t\u1eafc",
"last_time_updated_table_header": "C\u1eadp nh\u1eadt cu\u1ed1i",
"actions_table_header": "Thao t\u00e1c",
"delete_table_action": "Xo\u00e1",
"filters_and_hosts": "Danh s\u00e1ch b\u1ed9 l\u1ecdc v\u00e0 hosts",
"filters_and_hosts_hint": "AdGuard home hi\u1ec3u c\u00e1c quy t\u1eafc ch\u1eb7n qu\u1ea3ng c\u00e1o \u0111\u01a1n gi\u1ea3n v\u00e0 c\u00fa ph\u00e1p file hosts",
"no_filters_added": "Kh\u00f4ng c\u00f3 b\u1ed9 l\u1ecdc n\u00e0o \u0111\u01b0\u1ee3c th\u00eam",
"add_filter_btn": "Th\u00eam b\u1ed9 l\u1ecdc",
"cancel_btn": "Hu\u1ef7",
"enter_name_hint": "Nh\u1eadp t\u00ean",
"enter_url_hint": "Nh\u1eadp URL",
"check_updates_btn": "Ki\u1ec3m tra c\u1eadp nh\u1eadt",
"new_filter_btn": "\u0110\u0103ng k\u00fd b\u1ed9 l\u1ecdc m\u1edbi",
"enter_valid_filter_url": "Nh\u1eadp URL h\u1ee3p l\u1ec7 c\u1ee7a b\u1ed9 l\u1ecdc ho\u1eb7c file hosts",
"custom_filter_rules": "Quy t\u1eafc l\u1ecdc tu\u1ef3 ch\u1ec9nh",
"custom_filter_rules_hint": "Nh\u1eadp m\u1ed7i quy t\u1eafc 1 d\u00f2ng. C\u00f3 th\u1ec3 s\u1eed d\u1ee5ng quy t\u1eafc ch\u1eb7n qu\u1ea3ng c\u00e1o ho\u1eb7c c\u00fa ph\u00e1p file host",
"examples_title": "V\u00ed d\u1ee5",
"example_meaning_filter_block": "Ch\u1eb7n truy c\u1eadp t\u1edbi t\u00ean mi\u1ec1n example.org v\u00e0 t\u1ea5t c\u1ea3 t\u00ean mi\u1ec1n con",
"example_meaning_filter_whitelist": "Kh\u00f4ng ch\u1eb7n truy c\u1eadp t\u1edbi t\u00ean mi\u1ec1n example.org v\u00e0 t\u1ea5t c\u1ea3 t\u00ean mi\u1ec1n con",
"example_meaning_host_block": "AdGuard Home s\u1ebd ph\u1ea3n h\u1ed3i \u0111\u1ecba ch\u1ec9 IP 127.0.0.1 cho t\u00ean mi\u1ec1n example.org (kh\u00f4ng \u00e1p d\u1ee5ng t\u00ean mi\u1ec1n con)",
"example_comment": "! \u0110\u00e2y l\u00e0 m\u1ed9t ch\u00fa th\u00edch",
"example_comment_meaning": "Ch\u1ec9 l\u00e0 m\u1ed9t ch\u00fa th\u00edch",
"example_comment_hash": "# C\u0169ng l\u00e0 m\u1ed9t ch\u00fa th\u00edch",
"example_upstream_regular": "DNS th\u00f4ng th\u01b0\u1eddng (d\u00f9ng UDP)",
"example_upstream_dot": "\u0111\u01b0\u1ee3c m\u00e3 ho\u00e1 <0>DNS-over-TLS<\/0>",
"example_upstream_doh": "\u0111\u01b0\u1ee3c m\u00e3 ho\u00e1 <0>DNS-over-HTTPS<\/0>",
"example_upstream_sdns": "b\u1ea1n c\u00f3 th\u1ec3 s\u1eed d\u1ee5ng <0>DNS Stamps<\/0> for <1>DNSCrypt<\/1> ho\u1eb7c <2>DNS-over-HTTPS<\/2> ",
"example_upstream_tcp": "DNS th\u00f4ng th\u01b0\u1eddng(d\u00f9ng TCP)",
"all_filters_up_to_date_toast": "T\u1ea5t c\u1ea3 b\u1ed9 l\u1ecdc \u0111\u00e3 \u0111\u01b0\u1ee3c c\u1eadp nh\u1eadt",
"updated_upstream_dns_toast": "\u0110\u00e3 c\u1eadp nh\u1eadt m\u00e1y ch\u1ee7 DNS t\u00ecm ki\u1ebfm",
"dns_test_ok_toast": "M\u00e1y ch\u1ee7 DNS c\u00f3 th\u1ec3 s\u1eed d\u1ee5ng",
"dns_test_not_ok_toast": "M\u00e1y ch\u1ee7 '{{key}}': kh\u00f4ng th\u1ec3 s\u1eed d\u1ee5ng, vui l\u00f2ng ki\u1ec3m tra b\u1ea1n \u0111\u00e3 \u0111i\u1ec1n ch\u00ednh x\u00e1c",
"unblock_btn": "B\u1ecf ch\u1eb7n",
"block_btn": "Ch\u1eb7n",
"time_table_header": "Th\u1eddi gian",
"domain_name_table_header": "T\u00ean mi\u1ec1n",
"type_table_header": "Lo\u1ea1i",
"response_table_header": "Ph\u1ea3n h\u1ed3i",
"client_table_header": "Ng\u01b0\u1eddi d\u00f9ng cu\u1ed1i",
"empty_response_status": "R\u1ed7ng",
"show_all_filter_type": "Hi\u1ec7n t\u1ea5t c\u1ea3",
"show_filtered_type": "Ch\u1ec9 hi\u1ec7n \u0111\u00e3 l\u1ecdc",
"no_logs_found": "Kh\u00f4ng c\u00f3 l\u1ecbch s\u1eed truy v\u1ea5n",
"disabled_log_btn": "T\u1eaft l\u1ecbch s\u1eed truy v\u1ea5n",
"download_log_file_btn": "T\u1ea3i t\u1eadp tin l\u1ecbch s\u1eed truy v\u1ea5n",
"refresh_btn": "L\u00e0m m\u1edbi",
"enabled_log_btn": "B\u1eadt l\u1ecbch s\u1eed truy v\u1ea5n",
"last_dns_queries": "5000 truy v\u1ea5n DNS g\u1ea7n nh\u1ea5t",
"previous_btn": "Trang tr\u01b0\u1edbc",
"check_dhcp_servers": "Kim tra máy chủ DHCP",
"save_config": "Lưu thiết lập",
"enabled_dhcp": "Máy chủ DHCP đã kích hoạt",
"disabled_dhcp": "Máy chủ DHCP đã tắt",
"dhcp_title": "Máy chủ DHCP (thử nghiệm!)",
"dhcp_description": "Nếu bộ định tuyến không trợ cài đặt DHCP, bạn có thể dùng máy chủ DHCP dựng sẵn của AdGuard",
"dhcp_enable": "Bật máy chủ DHCP",
"dhcp_disable": "Tắt máy chủ DHCP",
"dhcp_not_found": "Không có máy chủ DHCP nào được tìm thấy trong mạng. Có thể bật máy chủ DHCP một cách an toàn",
"dhcp_found": "Đã tìm thấy máy chủ DHCP trong mạng. Có thể có rủi ro nếu kích hoạt máy chủ DHCP dựng sẵn",
"form_error_positive": "Phải lớn hơn 0",
"dhcp_form_range_end": "IP kết thúc",
"dhcp_interface_select": "Chọn một card mạng",
"back": "Quay lại",
"dashboard": "Tổng quan",
"settings": "Cài đặt",
"filters": "Bộ lọc",
"query_log": "Lịch sử truy vấn",
"faq": "Hỏi đáp",
"version": "phiên bản",
"address": "địa chỉ",
"on": "Đang bật",
"off": "Đang tắt",
"copyright": "Bản quyền",
"homepage": "Trang chủ",
"report_an_issue": "Báo lỗi",
"enable_protection": "Bật bảo vệ",
"enabled_protection": "Đã bật bảo vệ",
"disable_protection": "Tắt bảo vệ",
"disabled_protection": "Đã tắt bảo vệ",
"refresh_statics": "Làm mới thống kê",
"dns_query": "Truy vấn DNS",
"blocked_by": "Chặn bởi bộ lọc",
"stats_malware_phishing": "Mã độc/lừa đảo đã chặn",
"stats_adult": "Website người lớn đã chặn",
"stats_query_domain": "Tên miền truy vấn nhiều",
"for_last_24_hours": "trong 24 giờ qua",
"no_domains_found": "Không có tên miền nào",
"requests_count": "Số lần yêu cầu",
"top_blocked_domains": "Tên miền chặn nhiều",
"top_clients": "Client dùng nhiều",
"no_clients_found": "Không có client nào",
"general_statistics": "Thống kê chung",
"number_of_dns_query_24_hours": "Số yêu cầu DNS đã xử lý trong 24 giờ qua",
"number_of_dns_query_blocked_24_hours": "Số yêu cầu DNS bị chặn bởi bộ lọc quảng cáo và danh sách chặn host",
"number_of_dns_query_blocked_24_hours_by_sec": "Số yêu cầu DNS bị chặn bởi chế độ bảo vệ duyệt web AdGuard",
"number_of_dns_query_blocked_24_hours_adult": "Số website người lớn đã chặn",
"enforced_save_search": "Tìm kiếm an toàn",
"number_of_dns_query_to_safe_search": "Số yêu cầu DNS tới công cụ tìm kiếm đã chuyển thành tìm kiếm an toàn",
"average_processing_time": "Thời gian xử lý trung bình",
"average_processing_time_hint": "Thời gian trung bình cho một yêu cầu DNS tính bằng mili giây",
"block_domain_use_filters_and_hosts": "Chặn tên miền sử dụng các bộ lọc và file hosts",
"filters_block_toggle_hint": "Bạn có thể thiết lập quy tắc chặn tại cài đặt <a href='#filters'>Bộ lọc</a>.",
"use_adguard_browsing_sec": "Sử dụng dịch vụ bảo vệ duyệt web AdGuard",
"use_adguard_browsing_sec_hint": "AdGuard Home sẽ kiểm tra tên miền với dịch vụ bảo vệ duyệt web. Tính năng sử dụng một API thân thiện với quyền riêng tư: chỉ một phần ngắn tiền tố mã băm SHA256 được gửi đến máy chủ",
"use_adguard_parental": "Sử dụng dịch vụ quản lý của phụ huynh AdGuard",
"use_adguard_parental_hint": "AdGuard Home sẽ kiểm tra nếu tên miền chứa từ khoá người lớn. Tính năng sử dụng API thân thiện với quyền riêng tư tương tự với dịch vụ bảo vệ duyệt web",
"enforce_safe_search": "Bắt buộc tìm kiếm an toàn",
"enforce_save_search_hint": "AdGuard Home có thể bắt buộc tìm kiếm an toàn với các dịch vụ tìm kiếm: Google, Youtube, Bing, Yandex.",
"no_servers_specified": "Không có máy chủ nào được liệt kê",
"no_settings": "Không có cài đặt nào",
"general_settings": "Cài đặt chung",
"upstream_dns": "Máy chủ DNS tìm kiếm",
"upstream_dns_hint": "Nếu bạn để trng mục này, AdGuard Home sẽ sử dụng <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> để tìm kiếm. Sử dụng tiền tố tls:// cho các máy chủ DNS dựa trên TLS.",
"test_upstream_btn": "Kiểm tra",
"apply_btn": "Áp dụng",
"disabled_filtering_toast": "Đã tắt chặn quảng cáo",
"enabled_filtering_toast": "Đã bật chặn quảng cáo",
"disabled_safe_browsing_toast": "Đã tắt bảo vệ duyệt web",
"enabled_safe_browsing_toast": "Đã bật bảo vệ duyệt web",
"disabled_parental_toast": "Đã tắt quản lý của phụ huynh",
"enabled_parental_toast": "Đã bật quản lý của phụ huynh",
"disabled_safe_search_toast": "Đã tắt tìm kiếm an toàn",
"enabled_save_search_toast": "Đã bật tìm kiếm an toàn",
"enabled_table_header": "Kích hoạt",
"name_table_header": "Tên",
"filter_url_table_header": "URL bộ lọc",
"rules_count_table_header": "Số quy tắc",
"last_time_updated_table_header": "Cập nhật cuối",
"actions_table_header": "Thao tác",
"delete_table_action": "Xoá",
"filters_and_hosts": "Danh sách bộ lọc và hosts",
"filters_and_hosts_hint": "AdGuard home hiểu các quy tắc chặn quảng cáo đơn giản và cú pháp file hosts",
"no_filters_added": "Không có bộ lọc nào được thêm",
"add_filter_btn": "Thêm bộ lọc",
"cancel_btn": "Huỷ",
"enter_name_hint": "Nhập tên",
"enter_url_hint": "Nhập URL",
"check_updates_btn": "Kiểm tra cập nhật",
"new_filter_btn": "Đăng ký bộ lọc mới",
"enter_valid_filter_url": "Nhập URL hợp lệ của bộ lọc hoặc file hosts",
"custom_filter_rules": "Quy tắc lọc tuỳ chỉnh",
"custom_filter_rules_hint": "Nhập mỗi quy tắc 1 dòng. Có thể sử dụng quy tắc chặn quảng cáo hoặc cú pháp file host",
"examples_title": "Ví dụ",
"example_meaning_filter_block": "Chặn truy cập tới tên miền example.org và tất cả tên miền con",
"example_meaning_filter_whitelist": "Không chặn truy cập tới tên miền example.org và tất cả tên miền con",
"example_meaning_host_block": "AdGuard Home sẽ phản hồi địa chỉ IP 127.0.0.1 cho tên miền example.org (không áp dụng tên miền con)",
"example_comment": "! Đây là một chú thích",
"example_comment_meaning": "Chỉ là một chú thích",
"example_comment_hash": "# Cũng là một chú thích",
"example_upstream_regular": "DNS thông thường (dùng UDP)",
"example_upstream_dot": "được mã hoá <a href='https://en.wikipedia.org/wiki/DNS_over_TLS' target='_blank'>DNS-over-TLS</a>",
"example_upstream_doh": "được mã hoá <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a>",
"example_upstream_sdns": "bạn có thể sử dụng <a href='https://dnscrypt.info/stamps/' target='_blank'>DNS Stamps</a> for <a href='https://dnscrypt.info/' target='_blank'>DNSCrypt</a> hoặc<a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a> ",
"example_upstream_tcp": "DNS thông thường(dùng TCP)",
"all_filters_up_to_date_toast": "Tất cả bộ lọc đã được cập nhật",
"updated_upstream_dns_toast": "Đã cập nhật máy chủ DNS tìm kiếm",
"dns_test_ok_toast": "Máy chủ DNS có thể sử dụng",
"dns_test_not_ok_toast": "Máy chủ \"\"': không thể sử dụng, vui lòng kiểm tra lại",
"unblock_btn": "Bỏ chặn",
"block_btn": "Chặn",
"time_table_header": "Thời gian",
"domain_name_table_header": "Tên miền",
"type_table_header": "Loại",
"response_table_header": "Phản hồi",
"client_table_header": "Người dùng cuối",
"empty_response_status": "Rỗng",
"show_all_filter_type": "Hiện tất cả",
"show_filtered_type": "Chỉ hiện đã lọc",
"no_logs_found": "Không có lịch sử truy vấn",
"disabled_log_btn": "Tắt lịch sử truy vấn",
"download_log_file_btn": "Tải tập tin lịch sử truy vấn",
"refresh_btn": "Làm mới",
"enabled_log_btn": "Bật lịch sử truy vấn",
"last_dns_queries": "5000 truy vấn DNS gần nhất",
"previous_btn": "Trang trước",
"next_btn": "Trang sau",
"loading_table_status": "\u0110ang t\u1ea3i...",
"loading_table_status": "Đang tải...",
"page_table_footer_text": "Trang",
"of_table_footer_text": "c\u1ee7a",
"rows_table_footer_text": "h\u00e0ng",
"updated_custom_filtering_toast": "\u0110\u00e3 c\u1eadp nh\u1eadt quy t\u1eafc l\u1ecdc tu\u1ef3 ch\u1ec9nh",
"rule_removed_from_custom_filtering_toast": "Quy t\u1eafc \u0111\u00e3 \u0111\u01b0\u1ee3c xo\u00e1 kh\u1ecfi quy t\u1eafc l\u1ecdc tu\u1ef3 ch\u1ec9nh",
"rule_added_to_custom_filtering_toast": "Quy t\u1eafc \u0111\u00e3 \u0111\u01b0\u1ee3c th\u00eam v\u00e0o quy t\u1eafc l\u1ecdc tu\u1ef3 ch\u1ec9nh",
"query_log_disabled_toast": "\u0110\u00e3 t\u1eaft l\u1ecbch s\u1eed truy v\u1ea5n",
"query_log_enabled_toast": "\u0110\u00e3 b\u1eadt l\u1ecbch s\u1eed truy v\u1ea5n",
"source_label": "Ngu\u1ed3n",
"found_in_known_domain_db": "T\u00ecm th\u1ea5y trong c\u01a1 s\u1edf d\u1eef li\u1ec7u t\u00ean mi\u1ec1n",
"category_label": "Th\u1ec3 lo\u1ea1i",
"rule_label": "Quy t\u1eafc",
"filter_label": "B\u1ed9 l\u1ecdc",
"url_added_successfully": "Th\u00eam b\u1ed9 l\u1ecdc th\u00e0nh c\u00f4ng",
"unknown_filter": "B\u1ed9 l\u1ecdc kh\u00f4ng r\u00f5 {{filterId}}"
"of_table_footer_text": "ca",
"rows_table_footer_text": "hàng",
"updated_custom_filtering_toast": "Đã cập nhật quy tắc lọc tuỳ chỉnh",
"rule_removed_from_custom_filtering_toast": "Quy tắc đã được xoá khỏi quy tắc lọc tuỳ chỉnh",
"rule_added_to_custom_filtering_toast": "Quy tắc đã được thêm vào quy tắc lọc tuỳ chỉnh",
"query_log_disabled_toast": "Đã tắt lịch sử truy vn",
"query_log_enabled_toast": "Đã bật lịch sử truy vn",
"source_label": "Ngun",
"found_in_known_domain_db": "Tìm thấy trong cơ sở dữ liệu tên miền",
"category_label": "Thể loại",
"rule_label": "Quy tc",
"filter_label": "Bộ lọc",
"unknown_filter": "Bộ lọc không rõ {{filterId}}"
}

View File

@@ -1,253 +1,334 @@
{
"upstream_parallel": "\u901a\u8fc7\u540c\u65f6\u67e5\u8be2\u6240\u6709\u4e0a\u6d41\u670d\u52a1\u5668\u4ee5\u4f7f\u7528\u5e76\u884c\u67e5\u8be2\u52a0\u901f\u89e3\u6790",
"bootstrap_dns": "Bootstrap DNS \u670d\u52a1\u5668",
"bootstrap_dns_desc": "Bootstrap DNS servers are used to resolve IP addresses of the DoH\/DoT resolvers you specify as upstreams.",
"url_added_successfully": "\u7f51\u5740\u6dfb\u52a0\u6210\u529f",
"check_dhcp_servers": "\u68c0\u67e5 DHCP \u670d\u52a1\u5668",
"save_config": "\u4fdd\u5b58\u914d\u7f6e",
"enabled_dhcp": "DHCP \u670d\u52a1\u5668\u5df2\u542f\u7528",
"disabled_dhcp": "DHCP \u670d\u52a1\u5668\u5df2\u7981\u7528",
"dhcp_title": "DHCP \u670d\u52a1\u5668\uff08\u5b9e\u9a8c\u6027\uff09",
"dhcp_description": "\u5982\u679c\u4f60\u7684\u8def\u7531\u5668\u6ca1\u6709\u63d0\u4f9b\u52a8\u6001\u4e3b\u673a\u8bbe\u7f6e\u534f\u8bae\uff08DHCP\uff09\u8bbe\u7f6e\uff0c\u4f60\u53ef\u4ee5\u4f7f\u7528 AdGuard \u5185\u7f6e\u7684 DHCP \u670d\u52a1\u5668\u3002",
"dhcp_enable": "\u542f\u7528 DHCP \u670d\u52a1\u5668",
"dhcp_disable": "\u7981\u7528 DHCP \u670d\u52a1\u5668",
"dhcp_not_found": "\u5728\u5f53\u524d\u7f51\u7edc\u4e2d\u672a\u68c0\u6d4b\u5230 DHCP \u670d\u52a1\u5668\u3002\u60a8\u53ef\u4ee5\u5b89\u5168\u5730\u542f\u7528\u5185\u7f6e DHCP \u670d\u52a1\u5668\u3002",
"dhcp_found": "\u5728\u5f53\u524d\u7f51\u7edc\u4e2d\u68c0\u6d4b\u5230 DHCP \u670d\u52a1\u5668\u3002\u5982\u679c\u542f\u7528\u5185\u7f6e\u7684 DHCP \u670d\u52a1\u5668\u53ef\u80fd\u4e0d\u5b89\u5168\u3002",
"dhcp_leases": "DHCP \u79df\u7ea6",
"dhcp_leases_not_found": "\u672a\u68c0\u6d4b\u5230 DHCP \u79df\u7ea6",
"dhcp_config_saved": "\u4fdd\u5b58 DHCP \u670d\u52a1\u5668\u914d\u7f6e",
"form_error_required": "\u5fc5\u586b\u5b57\u6bb5",
"form_error_ip_format": "\u65e0\u6548\u7684 IPv4 \u683c\u5f0f",
"form_error_positive": "\u5fc5\u987b\u5927\u4e8e 0",
"dhcp_form_gateway_input": "\u7f51\u5173 IP",
"dhcp_form_subnet_input": "\u5b50\u7f51\u63a9\u7801",
"dhcp_form_range_title": "IP \u5730\u5740\u8303\u56f4",
"dhcp_form_range_start": "\u8d77\u59cb IP \u5730\u5740",
"dhcp_form_range_end": "\u672b\u5c3e IP \u5730\u5740",
"dhcp_form_lease_title": "DHCP \u79df\u7ea6\u65f6\u95f4\uff08\u79d2\uff09",
"dhcp_form_lease_input": "\u79df\u671f",
"dhcp_interface_select": "\u9009\u62e9 DHCP \u63a5\u53e3",
"dhcp_hardware_address": "\u786c\u4ef6\u5730\u5740",
"dhcp_ip_addresses": "IP \u5730\u5740",
"dhcp_table_hostname": "\u4e3b\u673a\u540d",
"dhcp_table_expires": "\u5230\u671f",
"dhcp_warning": "\u5982\u679c\u4f60\u60f3\u8981\u542f\u7528\u5185\u7f6e\u7684 DHCP \u670d\u52a1\u5668\uff0c\u8bf7\u786e\u4fdd\u5728\u5f53\u524d\u7f51\u7edc\u4e2d\u6ca1\u6709\u5176\u5b83\u6d3b\u52a8\u7684 DHCP \u670d\u52a1\u5668\u3002\u5426\u5219\uff0c\u6b64\u64cd\u4f5c\u53ef\u80fd\u4f1a\u7834\u574f\u5df2\u8fde\u63a5\u8bbe\u5907\u7684\u7f51\u7edc\u8fde\u63a5\uff01",
"back": "\u8fd4\u56de",
"dashboard": "\u4eea\u8868\u76d8",
"settings": "\u8bbe\u7f6e",
"filters": "\u8fc7\u6ee4\u5668",
"query_log": "\u67e5\u8be2\u65e5\u5fd7",
"faq": "\u5e38\u89c1\u95ee\u9898",
"version": "\u7248\u672c",
"address": "\u5730\u5740",
"on": "\u542f\u7528\u4e2d",
"off": "\u7981\u7528\u4e2d",
"copyright": "\u7248\u6743",
"homepage": "\u4e3b\u9875",
"report_an_issue": "\u95ee\u9898\u53cd\u9988",
"enable_protection": "\u542f\u7528\u4fdd\u62a4",
"enabled_protection": "\u4fdd\u62a4\u5df2\u542f\u7528",
"disable_protection": "\u7981\u7528\u4fdd\u62a4",
"disabled_protection": "\u4fdd\u62a4\u5df2\u7981\u7528",
"refresh_statics": "\u5237\u65b0\u72b6\u6001",
"dns_query": "DNS\u67e5\u8be2",
"blocked_by": "\u5df2\u88ab\u8fc7\u6ee4\u5668\u62e6\u622a",
"stats_malware_phishing": "\u88ab\u62e6\u622a\u7684\u6076\u610f\/\u9493\u9c7c\u7f51\u7ad9",
"stats_adult": "\u88ab\u62e6\u622a\u7684\u6210\u4eba\u7f51\u7ad9",
"stats_query_domain": "\u8bf7\u6c42\u57df\u540d\u6392\u884c",
"for_last_24_hours": "\u5728\u8fc7\u53bb 24 \u5c0f\u65f6",
"no_domains_found": "\u672a\u627e\u5230\u57df\u540d",
"requests_count": "\u8bf7\u6c42\u6570",
"top_blocked_domains": "\u88ab\u62e6\u622a\u57df\u540d\u6392\u884c",
"top_clients": "\u5ba2\u6237\u7aef\u6392\u884c",
"no_clients_found": "\u672a\u627e\u5230\u5ba2\u6237\u7aef",
"general_statistics": "\u6982\u51b5\u7edf\u8ba1",
"number_of_dns_query_24_hours": "\u8fc7\u53bb 24 \u5c0f\u65f6\u5185\u5904\u7406\u7684 DNS \u8bf7\u6c42\u603b\u6570",
"number_of_dns_query_blocked_24_hours": "\u88ab\u5e7f\u544a\u8fc7\u6ee4\u5668\u548c Hosts \u62e6\u622a\u6e05\u5355\u62e6\u622a\u7684 DNS \u8bf7\u6c42\u603b\u6570",
"number_of_dns_query_blocked_24_hours_by_sec": "\u88ab AdGuard \u5b89\u5168\u6d4f\u89c8\u6a21\u5757\u62e6\u622a\u7684 DNS \u8bf7\u6c42\u603b\u6570",
"number_of_dns_query_blocked_24_hours_adult": "\u88ab\u62e6\u622a\u7684\u6210\u4eba\u7f51\u7ad9\u603b\u6570",
"enforced_save_search": "\u5f3a\u5236\u5b89\u5168\u641c\u7d22",
"number_of_dns_query_to_safe_search": "\u542f\u7528\u5f3a\u5236\u5b89\u5168\u641c\u7d22\u540e\u5bf9\u641c\u7d22\u5f15\u64ce\u7684 DNS \u8bf7\u6c42\u603b\u6570",
"average_processing_time": "\u5e73\u5747\u5904\u7406\u65f6\u95f4",
"average_processing_time_hint": "\u5904\u7406 DNS \u8bf7\u6c42\u7684\u5e73\u5747\u65f6\u95f4\uff08\u6beb\u79d2\uff09",
"block_domain_use_filters_and_hosts": "\u4f7f\u7528\u8fc7\u6ee4\u5668\u548c Hosts \u6587\u4ef6\u4ee5\u62e6\u622a\u6307\u5b9a\u57df\u540d",
"filters_block_toggle_hint": "\u4f60\u53ef\u4ee5\u5728 <a href='#filters'>\u8fc7\u6ee4\u5668<\/a> \u8bbe\u7f6e\u4e2d\u6dfb\u52a0\u8fc7\u6ee4\u89c4\u5219\u3002",
"use_adguard_browsing_sec": "\u4f7f\u7528 AdGuard\u3010\u6d4f\u89c8\u5b89\u5168\u3011\u7f51\u9875\u670d\u52a1",
"use_adguard_browsing_sec_hint": "AdGuard Home \u5c06\u68c0\u67e5\u57df\u540d\u662f\u5426\u88ab\u6d4f\u89c8\u5b89\u5168\u670d\u52a1\u5217\u5165\u9ed1\u540d\u5355\u3002\u5b83\u5c06\u4f7f\u7528\u9690\u79c1\u6027\u5f3a\u7684\u68c0\u7d22 API \u6765\u6267\u884c\u68c0\u67e5\uff0c\u53ea\u6709\u57df\u540d\u7684 SHA256 \u7684\u77ed\u524d\u7f00\u4f1a\u88ab\u53d1\u9001\u5230\u670d\u52a1\u5668\u3002",
"use_adguard_parental": "\u4f7f\u7528 AdGuard \u3010\u5bb6\u957f\u63a7\u5236\u3011\u670d\u52a1",
"use_adguard_parental_hint": "AdGuard Home \u5c06\u4f7f\u7528\u4e0e\u6d4f\u89c8\u5b89\u5168\u670d\u52a1\u76f8\u540c\u7684\u9690\u79c1\u6027\u5f3a\u7684 API \u6765\u68c0\u67e5\u57df\u540d\u6307\u5411\u7684\u7f51\u7ad9\u662f\u5426\u5305\u542b\u6210\u4eba\u5185\u5bb9\u3002",
"enforce_safe_search": "\u5f3a\u5236\u5b89\u5168\u641c\u7d22",
"enforce_save_search_hint": "AdGuard Home \u5c06\u5bf9\u4ee5\u4e0b\u641c\u7d22\u5f15\u64ce\u5f3a\u5236\u542f\u7528\u5b89\u5168\u641c\u7d22\uff1aGoogle\u3001YouTube\u3001Bing \u548c Yandex\u3002",
"no_servers_specified": "\u672a\u627e\u5230\u6307\u5b9a\u7684\u670d\u52a1\u5668",
"no_settings": "\u672a\u627e\u5230\u8bbe\u7f6e",
"general_settings": "\u5e38\u89c4\u8bbe\u7f6e",
"upstream_dns": "\u4e0a\u6e38 DNS \u670d\u52a1\u5668",
"upstream_dns_hint": "\u5982\u679c\u6b64\u5904\u7559\u7a7a\uff0cAdGuard Home \u5c06\u4f1a\u4f7f\u7528 <a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a> \u4f5c\u4e3a\u4e0a\u6e38 DNS\u3002\u5982\u679c\u60f3\u8981\u4f7f\u7528\u4f7f\u7528 DNS over TLS\uff0c\u8bf7\u4ee5 tls:\/\/ \u4e3a\u5f00\u5934\u3002",
"test_upstream_btn": "\u6d4b\u8bd5\u4e0a\u6e38 DNS",
"apply_btn": "\u5e94\u7528",
"disabled_filtering_toast": "\u8fc7\u6ee4\u5668\u5df2\u7981\u7528",
"enabled_filtering_toast": "\u8fc7\u6ee4\u5668\u5df2\u542f\u7528",
"disabled_safe_browsing_toast": "\u5b89\u5168\u6d4f\u89c8\u5df2\u7981\u7528",
"enabled_safe_browsing_toast": "\u5b89\u5168\u6d4f\u89c8\u5df2\u542f\u7528",
"disabled_parental_toast": "\u5bb6\u957f\u63a7\u5236\u5df2\u7981\u7528",
"enabled_parental_toast": "\u5bb6\u957f\u63a7\u5236\u5df2\u542f\u7528",
"disabled_safe_search_toast": "\u5b89\u5168\u641c\u7d22\u5df2\u7981\u7528",
"enabled_save_search_toast": "\u5b89\u5168\u641c\u7d22\u5df2\u542f\u7528",
"enabled_table_header": "\u5df2\u542f\u7528",
"name_table_header": "\u540d\u79f0",
"filter_url_table_header": "\u8fc7\u6ee4\u5668\u5730\u5740",
"rules_count_table_header": "\u89c4\u5219\u6570",
"last_time_updated_table_header": "\u4e0a\u6b21\u66f4\u65b0\u65f6\u95f4",
"actions_table_header": "\u6d3b\u8dc3\u72b6\u6001",
"delete_table_action": "\u5220\u9664",
"filters_and_hosts": "\u8fc7\u6ee4\u5668\u548c Hosts \u62e6\u622a\u6e05\u5355",
"filters_and_hosts_hint": "AdGuard Home \u53ef\u4ee5\u89e3\u6790\u57fa\u7840\u7684 adblock \u89c4\u5219\u548c Hosts \u8bed\u6cd5\u3002",
"no_filters_added": "\u672a\u6dfb\u52a0\u4efb\u4f55\u8fc7\u6ee4\u5668",
"add_filter_btn": "\u6dfb\u52a0\u8fc7\u6ee4\u5668",
"cancel_btn": "\u53d6\u6d88",
"enter_name_hint": "\u8f93\u5165\u540d\u79f0",
"enter_url_hint": "\u8f93\u5165 URL",
"check_updates_btn": "\u68c0\u67e5\u66f4\u65b0",
"new_filter_btn": "\u8ba2\u9605\u65b0\u7684\u8fc7\u6ee4\u5668",
"enter_valid_filter_url": "\u8f93\u5165\u4e00\u4e2a\u8fc7\u6ee4\u5668\u8ba2\u9605\u6216 Hosts \u6587\u4ef6\u7684\u6709\u6548 URL",
"custom_filter_rules": "\u81ea\u5b9a\u4e49\u8fc7\u6ee4\u5668\u89c4\u5219",
"custom_filter_rules_hint": "\u8bf7\u786e\u4fdd\u6bcf\u884c\u53ea\u8f93\u5165\u4e00\u6761\u89c4\u5219\u3002\u4f60\u53ef\u4ee5\u8f93\u5165\u7b26\u5408 adblock \u8bed\u6cd5\u6216 Hosts \u8bed\u6cd5\u7684\u89c4\u5219\u3002",
"examples_title": "\u8303\u4f8b",
"example_meaning_filter_block": "\u62e6\u622a example.org \u57df\u540d\u53ca\u5176\u6240\u6709\u5b50\u57df\u540d",
"example_meaning_filter_whitelist": "\u653e\u884c example.org \u53ca\u5176\u6240\u6709\u5b50\u57df\u540d",
"example_meaning_host_block": "AdGuard Home \u73b0\u5728\u5c06\u4f1a\u628a example.org\uff08\u4f46\u4e0d\u5305\u62ec\u5b83\u7684\u5b50\u57df\u540d\uff09\u89e3\u6790\u5230 127.0.0.1\u3002",
"example_comment": "! \u8fd9\u662f\u4e00\u884c\u6ce8\u91ca",
"example_comment_meaning": "\u53ea\u662f\u4e00\u6761\u6ce8\u91ca",
"example_comment_hash": "# \u8fd9\u4e5f\u662f\u4e00\u884c\u6ce8\u91ca",
"example_regex_meaning": "\u963b\u6b62\u8bbf\u95ee\u4e0e\u6307\u5b9a\u7684\u6b63\u5219\u8868\u8fbe\u5f0f\u5339\u914d\u7684\u57df\u540d",
"example_upstream_regular": "\u5e38\u89c4 DNS\uff08\u57fa\u4e8e UDP\uff09",
"example_upstream_dot": "\u52a0\u5bc6 <0>DNS-over-TLS<\/0>",
"example_upstream_doh": "\u52a0\u5bc6 <0>DNS-over-HTTPS<\/0>",
"example_upstream_sdns": "\u4f60\u53ef\u4ee5\u4f7f\u7528 <0>DNSCrypt<\/0> \u7684 <1>DNS Stamps<\/1> \u6216\u8005 <2>DNS-over-HTTPS<\/2> \u89e3\u6790\u5668",
"example_upstream_tcp": "\u5e38\u89c4 DNS\uff08\u57fa\u4e8e TCP \uff09",
"all_filters_up_to_date_toast": "\u6240\u6709\u8fc7\u6ee4\u5668\u5df2\u66f4\u65b0\u81f3\u6700\u65b0",
"updated_upstream_dns_toast": "\u4e0a\u6e38 DNS \u5df2\u66f4\u65b0",
"dns_test_ok_toast": "\u6307\u5b9a\u7684 DNS \u670d\u52a1\u5668\u73b0\u5df2\u6b63\u5e38\u8fd0\u884c",
"dns_test_not_ok_toast": "\u670d\u52a1\u5668 \"{{key}}\"\uff1a\u65e0\u6cd5\u4f7f\u7528\uff0c\u8bf7\u68c0\u67e5\u4f60\u8f93\u5165\u7684\u662f\u5426\u6b63\u786e",
"unblock_btn": "\u653e\u884c",
"block_btn": "\u62e6\u622a",
"time_table_header": "\u65f6\u95f4",
"domain_name_table_header": "\u57df\u540d",
"type_table_header": "\u7c7b\u578b",
"response_table_header": "\u54cd\u5e94",
"client_table_header": "\u5ba2\u6237\u7aef",
"empty_response_status": "\u7a7a",
"show_all_filter_type": "\u663e\u793a\u6240\u6709",
"show_filtered_type": "\u663e\u793a\u88ab\u62e6\u622a\u7684",
"no_logs_found": "\u672a\u627e\u5230\u65e5\u5fd7",
"disabled_log_btn": "\u7981\u7528\u65e5\u5fd7",
"download_log_file_btn": "\u4e0b\u8f7d\u65e5\u5fd7\u6587\u4ef6",
"refresh_btn": "\u5237\u65b0",
"enabled_log_btn": "\u542f\u7528\u65e5\u5fd7",
"last_dns_queries": "\u6700\u8fd1\u7684 5000 \u4e2a DNS \u8bf7\u6c42",
"previous_btn": "\u4e0a\u4e00\u9875",
"next_btn": "\u4e0b\u4e00\u9875",
"loading_table_status": "\u52a0\u8f7d\u4e2d\u2026\u2026",
"page_table_footer_text": "\u9875",
"of_table_footer_text": "\u5728",
"rows_table_footer_text": "\u884c",
"updated_custom_filtering_toast": "\u81ea\u5b9a\u4e49\u8fc7\u6ee4\u89c4\u5219\u5df2\u66f4\u65b0",
"rule_removed_from_custom_filtering_toast": "\u89c4\u5219\u5df2\u4ece\u81ea\u5b9a\u4e49\u8fc7\u6ee4\u89c4\u5219\u5217\u8868\u4e2d\u79fb\u9664",
"rule_added_to_custom_filtering_toast": "\u89c4\u5219\u5df2\u6dfb\u52a0\u5230\u81ea\u5b9a\u4e49\u8fc7\u6ee4\u89c4\u5219\u5217\u8868\u4e2d",
"query_log_disabled_toast": "\u67e5\u8be2\u65e5\u5fd7\u5df2\u7981\u7528",
"query_log_enabled_toast": "\u67e5\u8be2\u65e5\u5fd7\u5df2\u542f\u7528",
"source_label": "\u6e90",
"found_in_known_domain_db": "\u6210\u529f\u5728\u5df2\u77e5\u57df\u540d\u6570\u636e\u5e93\u4e2d\u67e5\u8be2\u5230",
"category_label": "\u7c7b\u522b",
"rule_label": "\u89c4\u5219",
"filter_label": "\u8fc7\u6ee4\u5668",
"unknown_filter": "\u672a\u77e5\u8fc7\u6ee4\u5668 {{filterId}}",
"install_welcome_title": "\u6b22\u8fce\u4f7f\u7528 AdGuard Home\uff01",
"install_welcome_desc": "AdGuard Home \u662f\u4e00\u4e2a\u53ef\u5728\u7279\u5b9a\u7f51\u7edc\u8303\u56f4\u5185\u62e6\u622a\u6240\u6709\u5e7f\u544a\u548c\u8ddf\u8e2a\u5668\u7684 DNS \u670d\u52a1\u5668\u3002\u5b83\u7684\u76ee\u7684\u662f\u8ba9\u60a8\u63a7\u5236\u6574\u4e2a\u7f51\u7edc\u548c\u60a8\u7684\u6240\u6709\u8bbe\u5907\uff0c\u4e14\u4e0d\u9700\u8981\u4f7f\u7528\u4efb\u4f55\u5ba2\u6237\u7aef\u7a0b\u5e8f\u3002",
"install_settings_title": "\u7f51\u9875\u7ba1\u7406\u754c\u9762",
"install_settings_listen": "\u76d1\u542c\u63a5\u53e3",
"install_settings_port": "\u7aef\u53e3",
"install_settings_interface_link": "\u60a8\u53ef\u4ee5\u901a\u8fc7\u4ee5\u4e0b\u5730\u5740\u8bbf\u95ee\u60a8\u7684 AdGuard Home \u7f51\u9875\u7ba1\u7406\u754c\u9762\uff1a",
"form_error_port": "\u8f93\u5165\u6709\u6548\u7684\u7aef\u53e3\u503c",
"install_settings_dns": "DNS \u670d\u52a1\u5668",
"install_settings_dns_desc": "\u60a8\u5c06\u9700\u8981\u4f7f\u7528\u4ee5\u4e0b\u5730\u5740\u6765\u8bbe\u7f6e\u60a8\u7684\u8bbe\u5907\u6216\u8def\u7531\u5668\u7684 DNS \u670d\u52a1\u5668\uff1a",
"install_settings_all_interfaces": "\u6240\u6709\u63a5\u53e3",
"install_auth_title": "\u8eab\u4efd\u8ba4\u8bc1",
"install_auth_desc": "\u6211\u4eec\u5f3a\u70c8\u5efa\u8bae\u60a8\u4e3a AdGuard Home \u7684\u7f51\u9875\u7ba1\u7406\u754c\u9762\u914d\u7f6e\u5bc6\u7801\u3002\u5c3d\u7ba1\u8be5\u9875\u9762\u53ea\u80fd\u901a\u8fc7\u60a8\u7684\u672c\u5730\u7f51\u7edc\u8bbf\u95ee\uff0c\u4f46\u907f\u514d\u5b83\u88ab\u4e0d\u52a0\u9650\u5236\u5730\u8bbf\u95ee\u4ecd\u5341\u5206\u91cd\u8981\u3002",
"install_auth_username": "\u7528\u6237\u540d",
"install_auth_password": "\u5bc6\u7801",
"install_auth_confirm": "\u786e\u8ba4\u5bc6\u7801",
"install_auth_username_enter": "\u8f93\u5165\u7528\u6237\u540d",
"install_auth_password_enter": "\u8f93\u5165\u5bc6\u7801",
"install_step": "\u6b65\u9aa4",
"install_devices_title": "\u914d\u7f6e\u60a8\u7684\u8bbe\u5907",
"install_devices_desc": "\u4e3a\u4fdd\u8bc1 AdGuard Home \u53ef\u4ee5\u5f00\u59cb\u6b63\u5e38\u5de5\u4f5c\uff0c\u60a8\u9700\u8981\u5728\u8bbe\u5907\u4e0a\u5bf9\u5176\u8fdb\u884c\u914d\u7f6e\u3002",
"install_submit_title": "\u606d\u559c\u60a8\uff01",
"install_submit_desc": "\u5b89\u88c5\u8fc7\u7a0b\u5df2\u7ecf\u5b8c\u6210\uff0c\u60a8\u53ef\u4ee5\u5f00\u59cb\u4f7f\u7528 AdGuard Home \u4e86\u3002",
"install_devices_router": "\u8def\u7531\u5668",
"install_devices_router_desc": "\u6b64\u8bbe\u7f6e\u5c06\u81ea\u52a8\u8986\u76d6\u8fde\u63a5\u5230\u60a8\u7684\u5bb6\u5ead\u8def\u7531\u5668\u7684\u6240\u6709\u8bbe\u5907\uff0c\u60a8\u4e0d\u9700\u8981\u624b\u52a8\u914d\u7f6e\u5b83\u4eec\u3002",
"install_devices_address": "AdGuard Home DNS \u670d\u52a1\u5668\u6b63\u5728\u76d1\u542c\u4ee5\u4e0b\u5730\u5740",
"install_devices_router_list_1": "\u6253\u5f00\u60a8\u7684\u8def\u7531\u5668\u914d\u7f6e\u754c\u9762\u3002\u901a\u5e38\u60c5\u51b5\u4e0b\uff0c\u60a8\u53ef\u4ee5\u901a\u8fc7\u6d4f\u89c8\u5668\u8bbf\u95ee\u5730\u5740\uff08\u5982 http:\/\/192.168.0.1\/ \u6216 http:\/\/192.168.1.1 \uff09\u3002\u6253\u5f00\u540e\u60a8\u53ef\u80fd\u9700\u8981\u8f93\u5165\u5bc6\u7801\u4ee5\u8fdb\u5165\u914d\u7f6e\u754c\u9762\u3002\u5982\u679c\u60a8\u4e0d\u8bb0\u5f97\u5bc6\u7801\uff0c\u901a\u5e38\u53ef\u4ee5\u901a\u8fc7\u6309\u4e0b\u8def\u7531\u5668\u4e0a\u7684\u91cd\u7f6e\u6309\u94ae\u6765\u91cd\u8bbe\u5bc6\u7801\u3002\u4e00\u4e9b\u8def\u7531\u5668\u53ef\u80fd\u9700\u8981\u901a\u8fc7\u7279\u5b9a\u7684\u5e94\u7528\u6765\u8fdb\u884c\u8fd9\u4e00\u64cd\u4f5c\uff0c\u8bf7\u786e\u4fdd\u60a8\u5df2\u7ecf\u5728\u8ba1\u7b97\u673a\u6216\u624b\u673a\u4e0a\u5b89\u88c5\u4e86\u76f8\u5173\u5e94\u7528\u3002",
"install_devices_router_list_2": "\u627e\u5230\u8def\u7531\u5668\u7684 DHCP\/DNS \u8bbe\u7f6e\u9875\u9762\u3002\u60a8\u4f1a\u5728 DNS \u8fd9\u4e00\u5355\u8bcd\u65c1\u8fb9\u627e\u5230\u4e24\u5230\u4e09\u884c\u5141\u8bb8\u8f93\u5165\u7684\u8f93\u5165\u6846\uff0c\u6bcf\u4e00\u884c\u8f93\u5165\u6846\u5206\u4e3a\u56db\u7ec4\uff0c\u6bcf\u7ec4\u5141\u8bb8\u8f93\u5165\u4e00\u5230\u4e09\u4e2a\u6570\u5b57\u3002",
"install_devices_router_list_3": "\u8bf7\u5728\u6b64\u5904\u8f93\u5165\u60a8\u7684 AdGuard Home \u670d\u52a1\u5668\u5730\u5740\u3002",
"install_devices_windows_list_1": "\u901a\u8fc7\u5f00\u59cb\u83dc\u5355\u6216 Windows \u641c\u7d22\u529f\u80fd\u6253\u5f00\u63a7\u5236\u9762\u677f\u3002",
"install_devices_windows_list_2": "\u70b9\u51fb\u8fdb\u5165 \u201d\u7f51\u7edc\u548c Internet\u201c \u540e\uff0c\u518d\u6b21\u70b9\u51fb\u8fdb\u5165 \u201c\u7f51\u7edc\u548c\u5171\u4eab\u4e2d\u5fc3\u201d",
"install_devices_windows_list_3": "\u5728\u7a97\u53e3\u7684\u5de6\u4fa7\u627e\u5230 \u201d\u66f4\u6539\u9002\u914d\u5668\u8bbe\u7f6e\u201c \u5e76\u70b9\u51fb\u8fdb\u5165\u3002",
"install_devices_windows_list_4": "\u9009\u62e9\u60a8\u6b63\u5728\u8fde\u63a5\u7684\u7f51\u7edc\u8bbe\u5907\uff0c\u53f3\u51fb\u5b83\u5e76\u9009\u62e9 \u201d\u5c5e\u6027\u201c \u3002",
"install_devices_windows_list_5": "\u5728\u5217\u8868\u4e2d\u627e\u5230 \u201dInternet \u534f\u8bae\u7248\u672c 4 (TCP\/IPv4)\u201c \uff0c\u9009\u62e9\u5e76\u518d\u6b21\u70b9\u51fb \u201d\u5c5e\u6027\u201c \u3002",
"install_devices_windows_list_6": "\u9009\u62e9 \u201d\u4f7f\u7528\u4e0b\u9762\u7684 DNS \u670d\u52a1\u5668\u5730\u5740\u201c \uff0c\u5e76\u8f93\u5165\u60a8\u7684 AdGuard Home \u670d\u52a1\u5668\u5730\u5740\u3002",
"install_devices_macos_list_1": "\u70b9\u51fb\u82f9\u679c\u56fe\u6807\uff0c\u8fdb\u5165 \u201d\u7cfb\u7edf\u9996\u9009\u9879\u201c\u3002",
"install_devices_macos_list_2": "\u70b9\u51fb \u201d\u7f51\u7edc\u201c \u3002",
"install_devices_macos_list_3": "\u9009\u62e9\u5728\u5217\u8868\u4e2d\u7684\u7b2c\u4e00\u4e2a\u8fde\u63a5\uff0c\u5e76\u70b9\u51fb \u201d\u9ad8\u7ea7\u201c \u3002",
"install_devices_macos_list_4": "\u9009\u62e9 \u201dDNS\u201c \u9009\u9879\u5361\uff0c\u5e76\u8f93\u5165\u60a8\u7684 AdGuard Home \u670d\u52a1\u5668\u5730\u5740\u3002",
"install_devices_android_list_1": "\u5728\u5b89\u5353\u4e3b\u5c4f\u5e55\u83dc\u5355\u4e2d\u70b9\u51fb\u8bbe\u7f6e\u3002",
"install_devices_android_list_2": "\u70b9\u51fb\u83dc\u5355\u4e0a\u7684 \u201d\u65e0\u7ebf\u5c40\u57df\u7f51\u201c \u9009\u9879\u3002\u5728\u5c4f\u5e55\u4e0a\u5c06\u5217\u51fa\u6240\u6709\u53ef\u7528\u7684\u7f51\u7edc\uff08\u8702\u7a9d\u79fb\u52a8\u7f51\u7edc\u4e0d\u652f\u6301\u4fee\u6539 DNS \uff09\u3002",
"install_devices_android_list_3": "\u957f\u6309\u5f53\u524d\u5df2\u8fde\u63a5\u7684\u7f51\u7edc\uff0c\u7136\u540e\u70b9\u51fb \u201d\u4fee\u6539\u7f51\u7edc\u8bbe\u7f6e\u201c \u3002",
"install_devices_android_list_4": "\u5728\u67d0\u4e9b\u8bbe\u5907\u4e0a\uff0c\u60a8\u53ef\u80fd\u9700\u8981\u9009\u4e2d \u201d\u9ad8\u7ea7\u201c \u590d\u9009\u6846\u4ee5\u67e5\u770b\u8fdb\u4e00\u6b65\u7684\u8bbe\u7f6e\u3002\u60a8\u53ef\u80fd\u9700\u8981\u8c03\u6574\u60a8\u5b89\u5353\u8bbe\u5907\u7684 DNS \u8bbe\u7f6e\uff0c\u6216\u662f\u9700\u8981\u5c06 IP \u8bbe\u7f6e\u4ece DHCP \u5207\u6362\u5230\u9759\u6001\u3002",
"install_devices_android_list_5": "\u5c06 \"DNS 1 \/ \u4e3b DNS\" \u548c \u201dDNS 2 \/ \u526f DNS\u201c \u7684\u503c\u6539\u4e3a\u60a8\u7684 AdGuard Home \u670d\u52a1\u5668\u5730\u5740\u3002",
"install_devices_ios_list_1": "\u4ece\u4e3b\u5c4f\u5e55\u4e2d\u70b9\u51fb \u201d\u8bbe\u7f6e\u201c \u3002",
"install_devices_ios_list_2": "\u4ece\u5de6\u4fa7\u76ee\u5f55\u4e2d\u9009\u62e9 \u201d\u65e0\u7ebf\u5c40\u57df\u7f51\u201c\uff08\u79fb\u52a8\u6570\u636e\u7f51\u7edc\u73af\u5883\u4e0b\u4e0d\u652f\u6301\u4fee\u6539 DNS \uff09\u3002",
"install_devices_ios_list_3": "\u70b9\u51fb\u5f53\u524d\u5df2\u8fde\u63a5\u7f51\u7edc\u7684\u540d\u79f0\u3002",
"install_devices_ios_list_4": "\u5728 DNS \u5b57\u6bb5\u4e2d\u8f93\u5165\u60a8\u7684 AdGuard Home \u670d\u52a1\u5668\u5730\u5740\u3002",
"get_started": "\u5f00\u59cb\u914d\u7f6e",
"next": "\u4e0b\u4e00\u6b65",
"open_dashboard": "\u6253\u5f00\u4eea\u8868\u76d8",
"install_saved": "\u4fdd\u5b58\u6210\u529f",
"encryption_title": "\u52a0\u5bc6",
"encryption_desc": "\u4e3a DNS \u4e0e\u7f51\u9875\u7ba1\u7406\u754c\u9762\u542f\u7528\u52a0\u5bc6\uff08HTTPS\/TLS\uff09",
"encryption_config_saved": "\u52a0\u5bc6\u914d\u7f6e\u5df2\u4fdd\u5b58",
"encryption_server": "\u670d\u52a1\u5668\u540d\u79f0",
"encryption_server_enter": "\u8f93\u5165\u60a8\u7684\u57df\u540d",
"encryption_server_desc": "\u82e5\u8981\u4f7f\u7528 HTTPS \uff0c\u60a8\u9700\u8981\u8f93\u5165\u4e0e SSL \u8bc1\u4e66\u76f8\u5339\u914d\u7684\u670d\u52a1\u5668\u540d\u79f0\u3002",
"encryption_redirect": "HTTPS \u81ea\u52a8\u91cd\u5b9a\u5411",
"encryption_redirect_desc": "\u5982\u679c\u52fe\u9009\u6b64\u9009\u9879\uff0cAdGuard Home \u5c06\u81ea\u52a8\u5c06\u60a8\u4ece HTTP \u91cd\u5b9a\u5411\u5230 HTTPS \u5730\u5740\u3002",
"encryption_https": "HTTPS \u7aef\u53e3",
"encryption_https_desc": "\u5982\u679c\u914d\u7f6e\u4e86 HTTPS \u7aef\u53e3\uff0cAdGuard Home \u7ba1\u7406\u754c\u9762\u5c06\u53ef\u4ee5\u901a\u8fc7 HTTPS \u8bbf\u95ee\uff0c\u5b83\u8fd8\u5c06\u5728\u5728 '\/dns-query' \u4f4d\u7f6e\u63d0\u4f9b DNS-over-HTTPS \u3002",
"encryption_dot": "DNS-over-TLS \u7aef\u53e3",
"encryption_dot_desc": "\u5982\u679c\u914d\u7f6e\u4e86\u6b64\u7aef\u53e3\uff0cAdGuard Home \u5c06\u5728\u6b64\u7aef\u53e3\u4e0a\u8fd0\u884c\u4e00\u4e2a DNS-over-TLS \u670d\u52a1\u5668\u3002",
"encryption_certificates": "\u8bc1\u4e66",
"encryption_certificates_desc": "\u4e3a\u4e86\u4f7f\u7528\u52a0\u5bc6\uff0c\u60a8\u9700\u8981\u4e3a\u57df\u63d0\u4f9b\u6709\u6548\u7684 SSL \u8bc1\u4e66\u94fe\u3002\u60a8\u53ef\u4ee5\u5728 <0>{{link}}<\/0> \u4e0a\u83b7\u5f97\u514d\u8d39\u8bc1\u4e66\uff0c\u4e5f\u53ef\u4ee5\u4ece\u53d7\u4fe1\u4efb\u7684\u8bc1\u4e66\u9881\u53d1\u673a\u6784\u8d2d\u4e70\u8bc1\u4e66\u3002",
"encryption_certificates_input": "\u5c06\u60a8\u4ee5 PEM \u683c\u5f0f\u7f16\u7801\u7684\u8bc1\u4e66\u590d\u5236\u7c98\u8d34\u5230\u6b64\u5904\u3002",
"encryption_status": "\u72b6\u6001",
"encryption_expire": "\u6709\u6548\u671f",
"encryption_key": "\u79c1\u94a5",
"encryption_key_input": "\u5c06\u60a8\u4ee5 PEM \u683c\u5f0f\u7f16\u7801\u7684\u8bc1\u4e66\u79c1\u94a5\u590d\u5236\u7c98\u8d34\u5230\u6b64\u5904\u3002",
"encryption_enable": "\u542f\u7528\u52a0\u5bc6\uff08HTTPS\u3001DNS-over-HTTPS\u3001DNS-over-TLS\uff09",
"encryption_enable_desc": "\u5982\u679c\u542f\u7528\u52a0\u5bc6\u9009\u9879\uff0cAdGuard Home \u7684\u7f51\u9875\u7ba1\u7406\u754c\u9762\u5c06\u901a\u8fc7 HTTPS \u8fde\u63a5\u8bbf\u95ee\uff0c\u540c\u65f6 DNS \u670d\u52a1\u5668\u5c06\u76d1\u542c\u901a\u8fc7 DNS-over-HTTPS \u4e0e DNS-over-TLS \u53d1\u9001\u7684\u8bf7\u6c42\u3002",
"encryption_chain_valid": "\u8bc1\u4e66\u94fe\u9a8c\u8bc1\u6709\u6548",
"encryption_chain_invalid": "\u8bc1\u4e66\u94fe\u9a8c\u8bc1\u65e0\u6548",
"encryption_key_valid": "\u8be5 {{type}} \u79c1\u94a5\u9a8c\u8bc1\u6709\u6548",
"encryption_key_invalid": "\u8be5 {{type}} \u79c1\u94a5\u9a8c\u8bc1\u65e0\u6548",
"encryption_subject": "\u4f7f\u7528\u8005",
"encryption_issuer": "\u9881\u53d1\u8005",
"encryption_hostnames": "\u4e3b\u673a\u540d",
"encryption_reset": "\u60a8\u786e\u5b9a\u60f3\u8981\u91cd\u7f6e\u52a0\u5bc6\u8bbe\u7f6e\uff1f",
"topline_expiring_certificate": "\u60a8\u7684 SSL \u8bc1\u4e66\u5373\u5c06\u8fc7\u671f\u3002\u8bf7\u66f4\u65b0 <0>\u52a0\u5bc6\u8bbe\u7f6e<\/0> \u3002",
"topline_expired_certificate": "\u60a8\u7684 SSL \u8bc1\u4e66\u5df2\u8fc7\u671f\u3002\u8bf7\u66f4\u65b0 <0>\u52a0\u5bc6\u8bbe\u7f6e<\/0> \u3002",
"form_error_port_range": "\u8f93\u5165 80 - 65535 \u8303\u56f4\u5185\u7684\u7aef\u53e3\u503c",
"form_error_port_unsafe": "\u8fd9\u662f\u4e00\u4e2a\u4e0d\u5b89\u5168\u7684\u7aef\u53e3",
"form_error_equal": "\u4e0d\u5e94\u8be5\u76f8\u540c",
"form_error_password": "\u5bc6\u7801\u4e0d\u5339\u914d",
"reset_settings": "\u91cd\u7f6e\u8bbe\u7f6e",
"update_announcement": "AdGuard Home {{version}} \u73b0\u5df2\u53d1\u5e03\uff01 <0>\u70b9\u51fb\u6b64\u5904<\/0> \u4ee5\u83b7\u53d6\u8be6\u7ec6\u4fe1\u606f\u3002"
"client_settings": "客户端设置",
"example_upstream_reserved": "您可以<0>为特定域</0>指定上游 DNS",
"upstream_parallel": "通过同时查询所有上流服务器以使用并行查询加速解析",
"bootstrap_dns": "Bootstrap DNS 服务器",
"bootstrap_dns_desc": "Bootstrap DNS 服务器用于解析您指定为上游的 DoH / DoT 解析器的 IP 地址。",
"url_added_successfully": "网址添加成功",
"check_dhcp_servers": "检查 DHCP 服务器",
"save_config": "保存配置",
"enabled_dhcp": "DHCP 服务器已启用",
"disabled_dhcp": "DHCP 服务器已禁用",
"dhcp_title": "DHCP 服务器(实验性)",
"dhcp_description": "如果你的路由器没有提供动态主机设置协议DHCP设置你可以使用 AdGuard 内置的 DHCP 服务器。",
"dhcp_enable": "启用 DHCP 服务器",
"dhcp_disable": "禁用 DHCP 服务器",
"dhcp_not_found": "在当前网络中未检测到 DHCP 服务器。您可以安全地启用内置 DHCP 服务器。",
"dhcp_found": "在当前网络中检测到 DHCP 服务器。如果启用内置的 DHCP 服务器可能不安全。",
"dhcp_leases": "DHCP 租约",
"dhcp_static_leases": "DHCP 静态租约",
"dhcp_leases_not_found": "未检测到 DHCP 租约",
"dhcp_config_saved": "保存 DHCP 服务器配置",
"form_error_required": "必填字段",
"form_error_ip_format": "无效的 IPv4 格式",
"form_error_mac_format": "无效的 MAC 格式",
"form_error_positive": "必须大于 0",
"dhcp_form_gateway_input": "网关 IP",
"dhcp_form_subnet_input": "子网掩码",
"dhcp_form_range_title": "IP 地址范围",
"dhcp_form_range_start": "起始 IP 地址",
"dhcp_form_range_end": "末尾 IP 地址",
"dhcp_form_lease_title": "DHCP 租约时间(秒)",
"dhcp_form_lease_input": "租期",
"dhcp_interface_select": "选择 DHCP 接口",
"dhcp_hardware_address": "硬件地址",
"dhcp_ip_addresses": "IP 地址",
"dhcp_table_hostname": "主机名",
"dhcp_table_expires": "到期",
"dhcp_warning": "如果你想要启用内置的 DHCP 服务器,请确保在当前网络中没有其它活动的 DHCP 服务器。否则,此操作可能会破坏已连接设备的网络连接!",
"dhcp_error": "我们无法确定网络上是否有其它 DHCP 服务器。",
"dhcp_static_ip_error": "要使用 DHCP 服务器,则必须设置静态 IP。我们无法确定此网络接口是否是使用静态 IP 配置的。请手动设置静态 IP 地址。",
"dhcp_dynamic_ip_found": "您的系统使用了动态 IP 地址配置 <0>{{interfaceName}}</0> 接口。要使用 DHCP 服务器,则必须设置为静态 IP 地址。您当前的 IP 地址为 <0>{{ipAddress}}</0>。如您点击 开启 DHCP 按钮,则我们会自动设置此 IP 地址为静态。",
"dhcp_lease_added": "静态租约 \"{{key}}\" 添加成功",
"dhcp_lease_deleted": "静态租约 \"{{key}}\" 删除成功",
"dhcp_new_static_lease": "新建静态租约",
"dhcp_static_leases_not_found": "未找到 DHCP 静态租约",
"dhcp_add_static_lease": "添加静态租约",
"delete_confirm": "您确定要删除 \"{{key}}\"",
"form_enter_hostname": "输入主机名称",
"error_details": "详细错误信息",
"back": "返回",
"dashboard": "仪表盘",
"settings": "设置",
"filters": "过滤器",
"query_log": "查询日志",
"faq": "常见问题",
"version": "版本",
"address": "地址",
"on": "启用中",
"off": "禁用中",
"copyright": "版权",
"homepage": "主页",
"report_an_issue": "问题反馈",
"privacy_policy": "隐私策略",
"enable_protection": "启用保护",
"enabled_protection": "保护已启用",
"disable_protection": "禁用保护",
"disabled_protection": "保护已禁用",
"refresh_statics": "刷新状态",
"dns_query": "DNS查询",
"blocked_by": "已被过滤器拦截",
"stats_malware_phishing": "被拦截的恶意/钓鱼网站",
"stats_adult": "被拦截的成人网站",
"stats_query_domain": "请求域名排行",
"for_last_24_hours": "在过去 24 小时",
"no_domains_found": "未找到域名",
"requests_count": "请求数",
"top_blocked_domains": "被拦截域名排行",
"top_clients": "客户端排行",
"no_clients_found": "未找到客户端",
"general_statistics": "概况统计",
"number_of_dns_query_24_hours": "过去 24 小时内处理的 DNS 请求总数",
"number_of_dns_query_blocked_24_hours": "被广告过滤器和 Hosts 拦截清单拦截的 DNS 请求总数",
"number_of_dns_query_blocked_24_hours_by_sec": "被 AdGuard 安全浏览模块拦截的 DNS 请求总数",
"number_of_dns_query_blocked_24_hours_adult": "被拦截的成人网站总数",
"enforced_save_search": "强制安全搜索",
"number_of_dns_query_to_safe_search": "启用强制安全搜索后对搜索引擎的 DNS 请求总数",
"average_processing_time": "平均处理时间",
"average_processing_time_hint": "处理 DNS 请求的平均时间(毫秒)",
"block_domain_use_filters_and_hosts": "使用过滤器和 Hosts 文件以拦截指定域名",
"filters_block_toggle_hint": "你可以在 <a href='#filters'>过滤器</a> 设置中添加过滤规则。",
"use_adguard_browsing_sec": "使用 AdGuard【浏览安全】网页服务",
"use_adguard_browsing_sec_hint": "AdGuard Home 将检查域名是否被浏览安全服务列入黑名单。它将使用隐私性强的检索 API 来执行检查,只有域名的 SHA256 的短前缀会被发送到服务器。",
"use_adguard_parental": "使用 AdGuard 【家长控制】服务",
"use_adguard_parental_hint": "AdGuard Home 将使用与浏览安全服务相同的隐私性强的 API 来检查域名指向的网站是否包含成人内容。",
"enforce_safe_search": "强制安全搜索",
"enforce_save_search_hint": "AdGuard Home 将对以下搜索引擎强制启用安全搜索Google、YouTube、Bing 和 Yandex。",
"no_servers_specified": "未找到指定的服务器",
"no_settings": "未找到设置",
"general_settings": "常规设置",
"dns_settings": "DNS 设置",
"encryption_settings": "加密设置",
"dhcp_settings": "DHCP 设置",
"upstream_dns": "上游 DNS 服务器",
"upstream_dns_hint": "如果此处留空,AdGuard Home 将会使用 <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> 作为上游 DNS。如果想要使用使用 DNS over TLS请以 tls:// 为开头。",
"test_upstream_btn": "测试上游 DNS",
"apply_btn": "应用",
"disabled_filtering_toast": "过滤器已禁用",
"enabled_filtering_toast": "过滤器已启用",
"disabled_safe_browsing_toast": "安全浏览已禁用",
"enabled_safe_browsing_toast": "安全浏览已启用",
"disabled_parental_toast": "家长控制已禁用",
"enabled_parental_toast": "家长控制已启用",
"disabled_safe_search_toast": "安全搜索已禁用",
"enabled_save_search_toast": "安全搜索已启用",
"enabled_table_header": "已启用",
"name_table_header": "名称",
"filter_url_table_header": "过滤器地址",
"rules_count_table_header": "规则数",
"last_time_updated_table_header": "上次更新时间",
"actions_table_header": "活跃状态",
"edit_table_action": "编辑",
"delete_table_action": "删除",
"filters_and_hosts": "过滤器和 Hosts 拦截清单",
"filters_and_hosts_hint": "AdGuard Home 可以解析基础的 adblock 规则和 Hosts 语法。",
"no_filters_added": "未添加任何过滤器",
"add_filter_btn": "添加过滤器",
"cancel_btn": "取消",
"enter_name_hint": "输入名称",
"enter_url_hint": "输入 URL",
"check_updates_btn": "检查更新",
"new_filter_btn": "订阅新的过滤器",
"enter_valid_filter_url": "输入一个过滤器订阅或 Hosts 文件的有效 URL",
"custom_filter_rules": "自定义过滤器规则",
"custom_filter_rules_hint": "请确保每行只输入一条规则。你可以输入符合 adblock 语法或 Hosts 语法的规则。",
"examples_title": "范例",
"example_meaning_filter_block": "拦截 example.org 域名及其所有子域名",
"example_meaning_filter_whitelist": "放行 example.org 及其所有子域名",
"example_meaning_host_block": "AdGuard Home 现在将会把 example.org但不包括它的子域名解析到 127.0.0.1。",
"example_comment": "! 这是一行注释",
"example_comment_meaning": "只是一条注释",
"example_comment_hash": "# 这也是一行注释",
"example_upstream_regular": "常规 DNS基于 UDP",
"example_upstream_dot": "加密 <a href='https://en.wikipedia.org/wiki/DNS_over_TLS' target='_blank'>DNS-over-TLS</a>",
"example_upstream_doh": "加密 <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a>",
"example_upstream_sdns": "你可以使用 <a href='https://dnscrypt.info/' target='_blank'>DNSCrypt</a> 的 <a href='https://dnscrypt.info/stamps/' target='_blank'>DNS Stamps</a> 或者 <a href='https://en.wikipedia.org/wiki/DNS_over_HTTPS' target='_blank'>DNS-over-HTTPS</a> 解析器",
"example_upstream_tcp": "常规 DNS基于 TCP ",
"all_filters_up_to_date_toast": "所有过滤器已更新至最新",
"updated_upstream_dns_toast": "上游 DNS 已更新",
"dns_test_ok_toast": "指定的 DNS 服务器现已正常运行",
"dns_test_not_ok_toast": "服务器 \"{{key}}\":无法使用,请检查你输入的是否正确",
"unblock_btn": "放行",
"block_btn": "拦截",
"time_table_header": "时间",
"domain_name_table_header": "域名",
"type_table_header": "类型",
"response_table_header": "响应",
"client_table_header": "客户端",
"empty_response_status": "空",
"show_all_filter_type": "显示所有",
"show_filtered_type": "显示被拦截的",
"no_logs_found": "未找到日志",
"disabled_log_btn": "禁用日志",
"download_log_file_btn": "下载日志文件",
"refresh_btn": "刷新",
"enabled_log_btn": "启用日志",
"last_dns_queries": "最近的 5000 个 DNS 请求",
"previous_btn": "上一页",
"next_btn": "下一页",
"loading_table_status": "加载中……",
"page_table_footer_text": "页",
"of_table_footer_text": "在",
"rows_table_footer_text": "行",
"updated_custom_filtering_toast": "自定义过滤规则已更新",
"rule_removed_from_custom_filtering_toast": "规则已从自定义过滤规则列表中移除",
"rule_added_to_custom_filtering_toast": "规则已添加到自定义过滤规则列表中",
"query_log_disabled_toast": "查询日志已禁用",
"query_log_enabled_toast": "查询日志已启用",
"source_label": "源",
"found_in_known_domain_db": "成功在已知域名数据库中查询到",
"category_label": "类别",
"rule_label": "规则",
"filter_label": "过滤器",
"unknown_filter": "未知过滤器 {{filterId}}",
"install_welcome_title": "欢迎使用 AdGuard Home",
"install_welcome_desc": "AdGuard Home 是一个可在特定网络范围内拦截所有广告和跟踪器的 DNS 服务器。它的目的是让您控制整个网络和您的所有设备,且不需要使用任何客户端程序。",
"install_settings_title": "网页管理界面",
"install_settings_listen": "监听接口",
"install_settings_port": "端口",
"install_settings_interface_link": "您可以通过以下地址访问您的 AdGuard Home 网页管理界面:",
"form_error_port": "输入有效的端口值",
"install_settings_dns": "DNS 服务器",
"install_settings_dns_desc": "您将需要使用以下地址来设置您的设备或路由器的 DNS 服务器:",
"install_settings_all_interfaces": "所有接口",
"install_auth_title": "身份认证",
"install_auth_desc": "我们强烈建议您为 AdGuard Home 的网页管理界面配置密码。尽管该页面只能通过您的本地网络访问,但避免它被不加限制地访问仍十分重要。",
"install_auth_username": "用户名",
"install_auth_password": "密码",
"install_auth_confirm": "确认密码",
"install_auth_username_enter": "输入用户名",
"install_auth_password_enter": "输入密码",
"install_step": "步骤",
"install_devices_title": "配置您的设备",
"install_devices_desc": "为保证 AdGuard Home 可以开始正常工作,您需要在设备上对其进行配置。",
"install_submit_title": "恭喜您!",
"install_submit_desc": "安装过程已经完成,您可以开始使用 AdGuard Home 了。",
"install_devices_router": "路由器",
"install_devices_router_desc": "此设置将自动覆盖连接到您的家庭路由器的所有设备,您不需要手动配置它们。",
"install_devices_address": "AdGuard Home DNS 服务器正在监听以下地址",
"install_devices_router_list_1": "打开您的路由器配置界面。通常情况下,您可以通过浏览器访问地址(如 http://192.168.0.1/ 或 http://192.168.1.1 )。打开后您可能需要输入密码以进入配置界面。如果您不记得密码,通常可以通过按下路由器上的重置按钮来重设密码。一些路由器可能需要通过特定的应用来进行这一操作,请确保您已经在计算机或手机上安装了相关应用。",
"install_devices_router_list_2": "找到路由器的 DHCP/DNS 设置页面。您会在 DNS 这一单词旁边找到两到三行允许输入的输入框,每一行输入框分为四组,每组允许输入一到三个数字。",
"install_devices_router_list_3": "请在此处输入您的 AdGuard Home 服务器地址。",
"install_devices_windows_list_1": "通过开始菜单或 Windows 搜索功能打开控制面板。",
"install_devices_windows_list_2": "点击进入 ”网络和 Internet“ 后,再次点击进入 “网络和共享中心”",
"install_devices_windows_list_3": "在窗口的左侧找到 ”更改适配器设置“ 并点击进入。",
"install_devices_windows_list_4": "选择您正在连接的网络设备,右击它并选择 ”属性“ 。",
"install_devices_windows_list_5": "在列表中找到 ”Internet 协议版本 4 (TCP/IPv4)“ ,选择并再次点击 ”属性“ 。",
"install_devices_windows_list_6": "选择 ”使用下面的 DNS 服务器地址“ ,并输入您的 AdGuard Home 服务器地址。",
"install_devices_macos_list_1": "点击苹果图标,进入 ”系统首选项“。",
"install_devices_macos_list_2": "点击 ”网络“ 。",
"install_devices_macos_list_3": "选择在列表中的第一个连接,并点击 ”高级“ 。",
"install_devices_macos_list_4": "选择 ”DNS“ 选项卡,并输入您的 AdGuard Home 服务器地址。",
"install_devices_android_list_1": "在安卓主屏幕菜单中点击设置。",
"install_devices_android_list_2": "点击菜单上的 ”无线局域网“ 选项。在屏幕上将列出所有可用的网络(蜂窝移动网络不支持修改 DNS )。",
"install_devices_android_list_3": "长按当前已连接的网络,然后点击 ”修改网络设置“ 。",
"install_devices_android_list_4": "在某些设备上,您可能需要选中 ”高级“ 复选框以查看进一步的设置。您可能需要调整您安卓设备的 DNS 设置,或是需要将 IP 设置从 DHCP 切换到静态。",
"install_devices_android_list_5": "将 \"DNS 1 / 主 DNS\" 和 ”DNS 2 / 副 DNS“ 的值改为您的 AdGuard Home 服务器地址。",
"install_devices_ios_list_1": "从主屏幕中点击 ”设置“ 。",
"install_devices_ios_list_2": "从左侧目录中选择 ”无线局域网“(移动数据网络环境下不支持修改 DNS )。",
"install_devices_ios_list_3": "点击当前已连接网络的名称。",
"install_devices_ios_list_4": "在 DNS 字段中输入您的 AdGuard Home 服务器地址。",
"get_started": "开始配置",
"next": "下一步",
"open_dashboard": "打开仪表盘",
"install_saved": "保存成功",
"encryption_title": "加密",
"encryption_desc": "为 DNS 与网页管理界面启用加密HTTPS/TLS",
"encryption_config_saved": "加密配置已保存",
"encryption_server": "服务器名称",
"encryption_server_enter": "输入您的域名",
"encryption_server_desc": "若要使用 HTTPS ,您需要输入与 SSL 证书相匹配的服务器名称。",
"encryption_redirect": "HTTPS 自动重定向",
"encryption_redirect_desc": "如果勾选此选项AdGuard Home 将自动将您从 HTTP 重定向到 HTTPS 地址。",
"encryption_https": "HTTPS 端口",
"encryption_https_desc": "如果配置了 HTTPS 端口AdGuard Home 管理界面将可以通过 HTTPS 访问,它还将在在 '/dns-query' 位置提供 DNS-over-HTTPS 。",
"encryption_dot": "DNS-over-TLS 端口",
"encryption_dot_desc": "如果配置了此端口AdGuard Home 将在此端口上运行一个 DNS-over-TLS 服务器。",
"encryption_certificates": "证书",
"encryption_certificates_desc": "为了使用加密,您需要为域提供有效的 SSL 证书链。您可以在 <0>{{link}}</0> 上获得免费证书,也可以从受信任的证书颁发机构购买证书。",
"encryption_certificates_input": "将您以 PEM 格式编码的证书复制粘贴到此处。",
"encryption_status": "状态",
"encryption_expire": "有效期",
"encryption_key": "私钥",
"encryption_key_input": "将您以 PEM 格式编码的证书私钥复制粘贴到此处。",
"encryption_enable": "启用加密HTTPS、DNS-over-HTTPS、DNS-over-TLS",
"encryption_enable_desc": "如果启用加密选项AdGuard Home 的网页管理界面将通过 HTTPS 连接访问,同时 DNS 服务器将监听通过 DNS-over-HTTPS 与 DNS-over-TLS 发送的请求。",
"encryption_chain_valid": "证书链验证有效",
"encryption_chain_invalid": "证书链验证无效",
"encryption_key_valid": "该 {{type}} 私钥验证有效",
"encryption_key_invalid": "该 {{type}} 私钥验证无效",
"encryption_subject": "使用者",
"encryption_issuer": "颁发者",
"encryption_hostnames": "主机名",
"encryption_reset": "您确定想要重置加密设置?",
"topline_expiring_certificate": "您的 SSL 证书即将过期。请更新 <0>加密设置</0> 。",
"topline_expired_certificate": "您的 SSL 证书已过期。请更新 <0>加密设置</0> 。",
"form_error_port_range": "输入 80 - 65535 范围内的端口值",
"form_error_port_unsafe": "这是一个不安全的端口",
"form_error_equal": "不应该相同",
"form_error_password": "密码不匹配",
"reset_settings": "重置设置",
"update_announcement": "AdGuard Home {{version}} 现已发布! <0>点击此处</0> 以获取详细信息。",
"setup_guide": "设置指导",
"dns_addresses": "DNS 地址",
"down": "下移",
"fix": "修复",
"dns_providers": "此为可从中选择的<0>已知 DNS 提供商列表</0>。",
"update_now": "立即更新",
"update_failed": "自动更新失败。请<a href='https://github.com/AdguardTeam/AdGuardHome/wiki/Getting-Started#update'>跟随这些步骤</a>以手动更新。",
"processing_update": "正在更新 AdGuard Home请稍侯",
"clients_title": "客户端",
"clients_desc": "配置已连接到 AdGuard Home 的设备",
"settings_global": "全局",
"settings_custom": "自定义",
"table_client": "客户端",
"table_name": "名称",
"save_btn": "保存",
"client_add": "添加客户端",
"client_new": "新建客户端",
"client_edit": "编辑客户端",
"client_identifier": "标识符",
"ip_address": "IP 地址",
"client_identifier_desc": "客户端可通过 IP 地址或 MAC 地址识别。请注意,如 AdGuard Home 也是 <0>DHCP 服务器</0>,则仅能将 MAC 用作标识符",
"form_enter_ip": "输入 IP",
"form_enter_mac": "输入 MAC",
"form_client_name": "输入客户端名称",
"client_global_settings": "使用全局设置",
"client_deleted": "客户端 \"{{key}}\" 删除成功",
"client_added": "客户端 \"{{key}}\" 添加成功",
"client_updated": "客户端 \"{{key}}\" 更新成功",
"table_statistics": "请求次数(最后 24 小时)",
"clients_not_found": "未找到客户端",
"client_confirm_delete": "您确定要删除客户端 \"{{key}}\"",
"filter_confirm_delete": "您确定是要删除过滤器?",
"auto_clients_title": "客户端(运行时间)",
"auto_clients_desc": "使用 Adguard Home 但未存储在配置中的客户端上的数据",
"access_title": "访问设置",
"access_desc": "您可在此处配置 AdGuard Home DNS 服务器的访问规则。",
"access_allowed_title": "允许的客户端",
"access_allowed_desc": "CIDR 或 IP 地址列表。如配置,则 AdGuard Home 仅会接受源自这些 IP 地址的请求。",
"access_disallowed_title": "不允许的客户端",
"access_disallowed_desc": "CIDR 或 IP 地址列表。如配置,则 AdGuard Home 会放弃源自这些 IP 地址的请求。",
"access_blocked_title": "拦截的域",
"access_blocked_desc": "不要与过滤器混淆。在查询问题时 AdGuard Home 会放弃源自这些域的 DNS 查询。",
"access_settings_saved": "访问设置保存成功",
"updates_checked": "检查更新成功",
"updates_version_equal": "AdGuard Home已经是最新版本",
"check_updates_now": "立即检查更新",
"dns_privacy": "DNS 隐私",
"setup_dns_privacy_1": "<0>DNS-over-TLS:</0> 使用 <1>{{address}}</1> 字符串。",
"setup_dns_privacy_2": "<0>DNS-over-HTTPS:</0> 使用 <1>{{address}}</1> 字符串。",
"setup_dns_privacy_3": "<0>请注意,加密的 DNS 协议仅适用于 Android 9。所以您需要为其他操作系统上安装额外的软件。</0><0>以下是您可以使用软件的列表。</0>",
"setup_dns_privacy_android_1": "Android 9 原生支持 DNS-over-TLS。 要进行配置,请转到 设置 → 网络和互联网 → 高级 → 私有 DNS然后在那里输入您的域名。",
"setup_dns_privacy_android_2": "<0>AdGuard for Android</0> 支持 <1>DNS-over-HTTPS</1> 和 <1>DNS-over-TLS</1>。",
"setup_dns_privacy_android_3": "<0>Intra</0> 为 Android 提供了 <1>DNS-over-HTTPS</1> 的支持。",
"setup_dns_privacy_ios_1": "<0>DNSCloak</0> 支持 <1>DNS-over-HTTPS</1> ,但为了设置使用您自己的服务器,您需要为了它生成一个 <2>DNS Stamp</2> 。",
"setup_dns_privacy_ios_2": "<0>AdGuard for iOS</0> 支持 <1>DNS-over-HTTPS</1> 和 <1>DNS-over-TLS</1>。",
"setup_dns_privacy_other_title": "其他实施方案",
"setup_dns_privacy_other_1": "AdGuard Home 本身可以作为任何平台上的安全 DNS 客户端。",
"setup_dns_privacy_other_2": "<0>dnsproxy</0> 支持所有已知的安全 DNS 协议。",
"setup_dns_privacy_other_3": "<0>dnscrypt-proxy</0> 支持 <1>DNS-over-HTTPS</1>。",
"setup_dns_privacy_other_4": "<0>Mozilla Firefox</0> 支持 <1>DNS-over-HTTPS</1>。",
"setup_dns_privacy_other_5": "您可以从 <0>这里</0> 和 <1>这里</1> 找到更多的实施方案。",
"setup_dns_notice": "为了使用 <1>DNS-over-HTTPS</1> 或者 <1>DNS-over-TLS</1> ,您需要在 AdGuard Home 设置中 <0>配置加密</0> 。"
}

View File

@@ -1,256 +1,357 @@
{
"example_upstream_reserved": "\u60a8\u53ef\u660e\u78ba\u6307\u5b9a<0>\u7528\u65bc\u7279\u5b9a\u7684\u7db2\u57df<\/0>\u4e4bDNS\u4e0a\u6e38",
"upstream_parallel": "\u900f\u904e\u540c\u6642\u5730\u67e5\u8a62\u6240\u6709\u4e0a\u6e38\u7684\u4f3a\u670d\u5668\uff0c\u4f7f\u7528\u4e26\u884c\u7684\u67e5\u8a62\u4ee5\u52a0\u901f\u89e3\u6790",
"bootstrap_dns": "\u81ea\u6211\u555f\u52d5\uff08Bootstrap\uff09DNS \u4f3a\u670d\u5668",
"bootstrap_dns_desc": "\u81ea\u6211\u555f\u52d5\uff08Bootstrap\uff09DNS\u4f3a\u670d\u5668\u88ab\u7528\u65bc\u89e3\u6790\u60a8\u660e\u78ba\u6307\u5b9a\u4f5c\u70ba\u4e0a\u6e38\u7684DoH\/DoT\u89e3\u6790\u5668\u4e4bIP\u4f4d\u5740\u3002",
"url_added_successfully": "\u7db2\u5740\u88ab\u6210\u529f\u5730\u52a0\u5165",
"check_dhcp_servers": "\u6aa2\u67e5\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668",
"save_config": "\u5132\u5b58\u914d\u7f6e",
"enabled_dhcp": "\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668\u88ab\u555f\u7528",
"disabled_dhcp": "\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668\u88ab\u7981\u7528",
"dhcp_title": "\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668\uff08\u5be6\u9a57\u6027\u7684\uff01\uff09",
"dhcp_description": "\u5982\u679c\u60a8\u7684\u8def\u7531\u5668\u672a\u63d0\u4f9b\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u8a2d\u5b9a\uff0c\u60a8\u53ef\u4f7f\u7528AdGuard\u81ea\u8eab\u5167\u5efa\u7684DHCP\u4f3a\u670d\u5668\u3002",
"dhcp_enable": "\u555f\u7528\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668",
"dhcp_disable": "\u7981\u7528\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668",
"dhcp_not_found": "\u65bc\u8a72\u7db2\u8def\u4e0a\u7121\u73fe\u884c\u7684\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668\u88ab\u767c\u73fe\u3002\u555f\u7528\u5167\u5efa\u7684DHCP\u4f3a\u670d\u5668\u70ba\u5b89\u5168\u7684\u3002",
"dhcp_found": "\u65bc\u8a72\u7db2\u8def\u4e0a\u67d0\u4e9b\u73fe\u884c\u7684\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668\u88ab\u767c\u73fe\u3002\u555f\u7528\u5167\u5efa\u7684DHCP\u4f3a\u670d\u5668\u70ba\u4e0d\u5b89\u5168\u7684\u3002",
"dhcp_leases": "\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u79df\u8cc3",
"dhcp_leases_not_found": "\u7121\u5df2\u767c\u73fe\u4e4b\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u79df\u8cc3",
"dhcp_config_saved": "\u5df2\u5132\u5b58\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668\u914d\u7f6e",
"form_error_required": "\u5fc5\u586b\u7684\u6b04\u4f4d",
"form_error_ip_format": "\u7121\u6548\u7684IPv4\u683c\u5f0f",
"form_error_positive": "\u5fc5\u9808\u5927\u65bc0",
"dhcp_form_gateway_input": "\u9598\u9053 IP",
"dhcp_form_subnet_input": "\u5b50\u7db2\u8def\u906e\u7f69",
"dhcp_form_range_title": "IP \u4f4d\u5740\u7bc4\u570d",
"dhcp_form_range_start": "\u7bc4\u570d\u958b\u59cb",
"dhcp_form_range_end": "\u7bc4\u570d\u7d50\u675f",
"dhcp_form_lease_title": "\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u79df\u8cc3\u6642\u9593\uff08\u4ee5\u79d2\u6578\uff09",
"dhcp_form_lease_input": "\u79df\u8cc3\u6301\u7e8c\u6642\u9593",
"dhcp_interface_select": "\u9078\u64c7\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4ecb\u9762",
"dhcp_hardware_address": "\u786c\u9ad4\u4f4d\u5740",
"dhcp_ip_addresses": "IP \u4f4d\u5740",
"dhcp_table_hostname": "\u4e3b\u6a5f\u540d\u7a31",
"dhcp_table_expires": "\u5230\u671f",
"dhcp_warning": "\u5982\u679c\u60a8\u60f3\u8981\u555f\u7528\u5167\u5efa\u7684\u52d5\u614b\u4e3b\u6a5f\u8a2d\u5b9a\u5354\u5b9a\uff08DHCP\uff09\u4f3a\u670d\u5668\uff0c\u78ba\u4fdd\u7121\u5176\u5b83\u73fe\u884c\u7684DHCP\u4f3a\u670d\u5668\u3002\u5426\u5247\uff0c\u5b83\u53ef\u80fd\u6703\u7834\u58de\u4f9b\u5df2\u9023\u7dda\u7684\u88dd\u7f6e\u4e4b\u7db2\u969b\u7db2\u8def\uff01",
"back": "\u8fd4\u56de",
"dashboard": "\u5100\u8868\u677f",
"settings": "\u8a2d\u5b9a",
"filters": "\u904e\u6ffe\u5668",
"query_log": "\u67e5\u8a62\u8a18\u9304",
"faq": "\u5e38\u898b\u554f\u7b54\u96c6",
"version": "\u7248\u672c",
"address": "\u4f4d\u5740",
"on": "\u958b\u8457",
"off": "\u95dc\u8457",
"copyright": "\u7248\u6b0a",
"homepage": "\u9996\u9801",
"report_an_issue": "\u5831\u544a\u554f\u984c",
"enable_protection": "\u555f\u7528\u9632\u8b77",
"enabled_protection": "\u5df2\u555f\u7528\u9632\u8b77",
"disable_protection": "\u7981\u7528\u9632\u8b77",
"disabled_protection": "\u5df2\u7981\u7528\u9632\u8b77",
"refresh_statics": "\u91cd\u65b0\u6574\u7406\u7d71\u8a08\u8cc7\u6599",
"dns_query": "DNS \u67e5\u8a62",
"blocked_by": "\u5df2\u88ab\u904e\u6ffe\u5668\u5c01\u9396",
"stats_malware_phishing": "\u5df2\u5c01\u9396\u7684\u60e1\u610f\u8edf\u9ad4\/\u7db2\u8def\u91e3\u9b5a",
"stats_adult": "\u5df2\u5c01\u9396\u7684\u6210\u4eba\u7db2\u7ad9",
"stats_query_domain": "\u71b1\u9580\u5df2\u67e5\u8a62\u7684\u7db2\u57df",
"for_last_24_hours": "\u5728\u6700\u8fd1\u768424\u5c0f\u6642\u5167",
"no_domains_found": "\u7121\u5df2\u767c\u73fe\u4e4b\u7db2\u57df",
"requests_count": "\u8acb\u6c42\u7e3d\u6578",
"top_blocked_domains": "\u71b1\u9580\u5df2\u5c01\u9396\u7684\u7db2\u57df",
"top_clients": "\u71b1\u9580\u7528\u6236\u7aef",
"no_clients_found": "\u7121\u5df2\u767c\u73fe\u4e4b\u7528\u6236\u7aef",
"general_statistics": "\u4e00\u822c\u7684\u7d71\u8a08\u8cc7\u6599",
"number_of_dns_query_24_hours": "\u5728\u6700\u8fd1\u768424\u5c0f\u6642\u5167\u5df2\u8655\u7406\u7684DNS\u67e5\u8a62\u4e4b\u6578\u91cf",
"number_of_dns_query_blocked_24_hours": "\u5df2\u88ab\u5ee3\u544a\u5c01\u9396\u904e\u6ffe\u5668\u548c\u4e3b\u6a5f\u5c01\u9396\u6e05\u55ae\u5c01\u9396\u7684DNS\u8acb\u6c42\u4e4b\u6578\u91cf",
"number_of_dns_query_blocked_24_hours_by_sec": "\u5df2\u88abAdGuard\u700f\u89bd\u5b89\u5168\u6a21\u7d44\u5c01\u9396\u7684DNS\u8acb\u6c42\u4e4b\u6578\u91cf",
"number_of_dns_query_blocked_24_hours_adult": "\u5df2\u5c01\u9396\u7684\u6210\u4eba\u7db2\u7ad9\u4e4b\u6578\u91cf",
"enforced_save_search": "\u5df2\u5f37\u5236\u57f7\u884c\u7684\u5b89\u5168\u641c\u5c0b",
"number_of_dns_query_to_safe_search": "\u5c0d\u65bc\u90a3\u4e9b\u5b89\u5168\u641c\u5c0b\u5df2\u88ab\u5f37\u5236\u57f7\u884c\u4e4b\u5c6c\u65bc\u641c\u5c0b\u5f15\u64ce\u7684DNS\u8acb\u6c42\u4e4b\u6578\u91cf",
"average_processing_time": "\u5e73\u5747\u7684\u8655\u7406\u6642\u9593",
"average_processing_time_hint": "\u65bc\u8655\u7406\u4e00\u9805DNS\u8acb\u6c42\u4e0a\u4ee5\u6beb\u79d2\uff08ms\uff09\u8a08\u4e4b\u5e73\u5747\u7684\u6642\u9593",
"block_domain_use_filters_and_hosts": "\u900f\u904e\u904e\u6ffe\u5668\u548c\u4e3b\u6a5f\u6a94\u6848\u5c01\u9396\u7db2\u57df",
"filters_block_toggle_hint": "\u60a8\u53ef\u5728<a href='#filters'>\u904e\u6ffe\u5668<\/a>\u8a2d\u5b9a\u4e2d\u8a2d\u7f6e\u5c01\u9396\u898f\u5247\u3002",
"use_adguard_browsing_sec": "\u4f7f\u7528AdGuard\u700f\u89bd\u5b89\u5168\u7db2\u8def\u670d\u52d9",
"use_adguard_browsing_sec_hint": "AdGuard Home\u5c07\u6aa2\u67e5\u7db2\u57df\u662f\u5426\u88ab\u700f\u89bd\u5b89\u5168\u7db2\u8def\u670d\u52d9\u5217\u5165\u9ed1\u540d\u55ae\u3002\u5b83\u5c07\u4f7f\u7528\u53cb\u597d\u7684\u96b1\u79c1\u67e5\u627e\u61c9\u7528\u7a0b\u5f0f\u4ecb\u9762\uff08API\uff09\u4ee5\u57f7\u884c\u6aa2\u67e5\uff1a\u50c5\u57df\u540dSHA256\u96dc\u6e4a\u7684\u77ed\u524d\u7db4\u88ab\u50b3\u9001\u5230\u4f3a\u670d\u5668\u3002",
"use_adguard_parental": "\u4f7f\u7528AdGuard\u5bb6\u9577\u76e3\u63a7\u4e4b\u7db2\u8def\u670d\u52d9",
"use_adguard_parental_hint": "AdGuard Home\u5c07\u6aa2\u67e5\u7db2\u57df\u662f\u5426\u5305\u542b\u6210\u4eba\u8cc7\u6599\u3002\u5b83\u4f7f\u7528\u5982\u540c\u700f\u89bd\u5b89\u5168\u7db2\u8def\u670d\u52d9\u4e00\u6a23\u4e4b\u53cb\u597d\u7684\u96b1\u79c1\u61c9\u7528\u7a0b\u5f0f\u4ecb\u9762\uff08API\uff09\u3002",
"enforce_safe_search": "\u5f37\u5236\u57f7\u884c\u5b89\u5168\u641c\u5c0b",
"enforce_save_search_hint": "AdGuard Home\u53ef\u5728\u4e0b\u5217\u7684\u641c\u5c0b\u5f15\u64ce\uff1aGoogle\u3001YouTube\u3001Bing\u548cYandex\u4e2d\u5f37\u5236\u57f7\u884c\u5b89\u5168\u641c\u5c0b\u3002",
"no_servers_specified": "\u7121\u5df2\u660e\u78ba\u6307\u5b9a\u7684\u4f3a\u670d\u5668",
"no_settings": "\u7121\u8a2d\u5b9a",
"general_settings": "\u4e00\u822c\u7684\u8a2d\u5b9a",
"upstream_dns": "\u4e0a\u6e38\u7684DNS\u4f3a\u670d\u5668",
"upstream_dns_hint": "\u5982\u679c\u60a8\u5c07\u8a72\u6b04\u4f4d\u7559\u7a7a\uff0cAdGuard Home\u5c07\u4f7f\u7528<a href='https:\/\/1.1.1.1\/' target='_blank'>Cloudflare DNS<\/a>\u4f5c\u70ba\u4e0a\u6e38\u3002",
"test_upstream_btn": "\u6e2c\u8a66\u4e0a\u884c\u8cc7\u6599\u6d41",
"apply_btn": "\u5957\u7528",
"disabled_filtering_toast": "\u5df2\u7981\u7528\u904e\u6ffe",
"enabled_filtering_toast": "\u5df2\u555f\u7528\u904e\u6ffe",
"disabled_safe_browsing_toast": "\u5df2\u7981\u7528\u5b89\u5168\u700f\u89bd",
"enabled_safe_browsing_toast": "\u5df2\u555f\u7528\u5b89\u5168\u700f\u89bd",
"disabled_parental_toast": "\u5df2\u7981\u7528\u5bb6\u9577\u76e3\u63a7",
"enabled_parental_toast": "\u5df2\u555f\u7528\u5bb6\u9577\u76e3\u63a7",
"disabled_safe_search_toast": "\u5df2\u7981\u7528\u5b89\u5168\u641c\u5c0b",
"enabled_save_search_toast": "\u5df2\u555f\u7528\u5b89\u5168\u641c\u5c0b",
"enabled_table_header": "\u5df2\u555f\u7528\u7684",
"name_table_header": "\u540d\u7a31",
"filter_url_table_header": "\u904e\u6ffe\u5668\u7db2\u5740",
"rules_count_table_header": "\u898f\u5247\u7e3d\u6578",
"last_time_updated_table_header": "\u6700\u8fd1\u7684\u66f4\u65b0\u6642\u9593",
"actions_table_header": "\u884c\u52d5",
"delete_table_action": "\u522a\u9664",
"filters_and_hosts": "\u904e\u6ffe\u5668\u548c\u4e3b\u6a5f\u5c01\u9396\u6e05\u55ae",
"filters_and_hosts_hint": "AdGuard Home\u61c2\u5f97\u57fa\u672c\u7684\u5ee3\u544a\u5c01\u9396\u898f\u5247\u548c\u4e3b\u6a5f\u6a94\u6848\u8a9e\u6cd5\u3002",
"no_filters_added": "\u7121\u5df2\u52a0\u5165\u7684\u904e\u6ffe\u5668",
"add_filter_btn": "\u589e\u52a0\u904e\u6ffe\u5668",
"cancel_btn": "\u53d6\u6d88",
"enter_name_hint": "\u8f38\u5165\u540d\u7a31",
"enter_url_hint": "\u8f38\u5165\u7db2\u5740",
"check_updates_btn": "\u6aa2\u67e5\u66f4\u65b0",
"new_filter_btn": "\u65b0\u7684\u904e\u6ffe\u5668\u8a02\u95b1",
"enter_valid_filter_url": "\u8f38\u5165\u95dc\u65bc\u904e\u6ffe\u5668\u8a02\u95b1\u6216\u4e3b\u6a5f\u6a94\u6848\u4e4b\u6709\u6548\u7684\u7db2\u5740\u3002",
"custom_filter_rules": "\u81ea\u8a02\u7684\u904e\u6ffe\u898f\u5247",
"custom_filter_rules_hint": "\u65bc\u4e00\u884c\u4e0a\u8f38\u5165\u4e00\u500b\u898f\u5247\u3002\u60a8\u53ef\u4f7f\u7528\u5ee3\u544a\u5c01\u9396\u898f\u5247\u6216\u4e3b\u6a5f\u6a94\u6848\u8a9e\u6cd5\u3002",
"examples_title": "\u7bc4\u4f8b",
"example_meaning_filter_block": "\u5c01\u9396\u81f3example.org\u7db2\u57df\u53ca\u5176\u6240\u6709\u7684\u5b50\u7db2\u57df\u4e4b\u5b58\u53d6",
"example_meaning_filter_whitelist": "\u89e3\u9664\u5c01\u9396\u81f3example.org\u7db2\u57df\u53ca\u5176\u6240\u6709\u7684\u5b50\u7db2\u57df\u4e4b\u5b58\u53d6",
"example_meaning_host_block": "AdGuard Home\u73fe\u5728\u5c07\u5c0dexample.org\u7db2\u57df\u8fd4\u56de127.0.0.1\u4f4d\u5740\uff08\u4f46\u975e\u5176\u5b50\u7db2\u57df\uff09\u3002",
"example_comment": "! \u770b\uff0c\u4e00\u500b\u8a3b\u89e3",
"example_comment_meaning": "\u53ea\u662f\u4e00\u500b\u8a3b\u89e3",
"example_comment_hash": "# \u4e5f\u662f\u4e00\u500b\u8a3b\u89e3",
"example_regex_meaning": "\u5c01\u9396\u81f3\u8207\u5df2\u660e\u78ba\u6307\u5b9a\u7684\u898f\u5247\u904b\u7b97\u5f0f\uff08Regular Expression\uff09\u76f8\u7b26\u7684\u7db2\u57df\u4e4b\u5b58\u53d6",
"example_upstream_regular": "\u4e00\u822c\u7684 DNS\uff08\u900f\u904eUDP\uff09",
"example_upstream_dot": "\u52a0\u5bc6\u7684 <0>DNS-over-TLS<\/0>",
"example_upstream_doh": "\u52a0\u5bc6\u7684 <0>DNS-over-HTTPS<\/0>",
"example_upstream_sdns": "\u60a8\u53ef\u4f7f\u7528\u95dc\u65bc <1>DNSCrypt<\/1> \u6216 <2>DNS-over-HTTPS<\/2> \u89e3\u6790\u5668\u4e4b <0>DNS \u6233\u8a18<\/0>",
"example_upstream_tcp": "\u4e00\u822c\u7684 DNS\uff08\u900f\u904eTCP\uff09",
"all_filters_up_to_date_toast": "\u6240\u6709\u7684\u904e\u6ffe\u5668\u5df2\u662f\u6700\u65b0\u7684",
"updated_upstream_dns_toast": "\u5df2\u66f4\u65b0\u4e0a\u6e38\u7684DNS\u4f3a\u670d\u5668",
"dns_test_ok_toast": "\u5df2\u660e\u78ba\u6307\u5b9a\u7684DNS\u4f3a\u670d\u5668\u6b63\u5728\u6b63\u78ba\u5730\u904b\u4f5c",
"dns_test_not_ok_toast": "\u4f3a\u670d\u5668 \"{{key}}\"\uff1a\u7121\u6cd5\u88ab\u4f7f\u7528\uff0c\u8acb\u6aa2\u67e5\u60a8\u5df2\u6b63\u78ba\u5730\u586b\u5beb\u5b83",
"unblock_btn": "\u89e3\u9664\u5c01\u9396",
"block_btn": "\u5c01\u9396",
"time_table_header": "\u6642\u9593",
"domain_name_table_header": "\u57df\u540d",
"type_table_header": "\u985e\u578b",
"response_table_header": "\u56de\u61c9",
"client_table_header": "\u7528\u6236\u7aef",
"empty_response_status": "\u7a7a\u767d\u7684",
"show_all_filter_type": "\u986f\u793a\u5168\u90e8",
"show_filtered_type": "\u986f\u793a\u5df2\u904e\u6ffe\u7684",
"no_logs_found": "\u7121\u5df2\u767c\u73fe\u4e4b\u8a18\u9304",
"disabled_log_btn": "\u7981\u7528\u8a18\u9304",
"download_log_file_btn": "\u4e0b\u8f09\u8a18\u9304\u6a94\u6848",
"refresh_btn": "\u91cd\u65b0\u6574\u7406",
"enabled_log_btn": "\u555f\u7528\u8a18\u9304",
"last_dns_queries": "\u6700\u8fd1\u76845000\u7b46DNS\u67e5\u8a62",
"previous_btn": "\u4e0a\u4e00\u9801",
"next_btn": "\u4e0b\u4e00\u9801",
"loading_table_status": "\u6b63\u5728\u8f09\u5165...",
"page_table_footer_text": "\u9801\u9762",
"of_table_footer_text": "\u4e4b",
"rows_table_footer_text": "\u5217",
"updated_custom_filtering_toast": "\u5df2\u66f4\u65b0\u81ea\u8a02\u7684\u904e\u6ffe\u898f\u5247",
"rule_removed_from_custom_filtering_toast": "\u898f\u5247\u5f9e\u81ea\u8a02\u7684\u904e\u6ffe\u898f\u5247\u4e2d\u88ab\u79fb\u9664",
"rule_added_to_custom_filtering_toast": "\u898f\u5247\u88ab\u52a0\u81f3\u81ea\u8a02\u7684\u904e\u6ffe\u898f\u5247\u4e2d",
"query_log_disabled_toast": "\u67e5\u8a62\u8a18\u9304\u88ab\u7981\u7528",
"query_log_enabled_toast": "\u67e5\u8a62\u8a18\u9304\u88ab\u555f\u7528",
"source_label": "\u4f86\u6e90",
"found_in_known_domain_db": "\u5728\u5df2\u77e5\u7684\u57df\u540d\u8cc7\u6599\u5eab\u4e2d\u88ab\u767c\u73fe\u3002",
"category_label": "\u985e\u5225",
"rule_label": "\u898f\u5247",
"filter_label": "\u904e\u6ffe\u5668",
"unknown_filter": "\u672a\u77e5\u7684\u904e\u6ffe\u5668 {{filterId}}",
"install_welcome_title": "\u6b61\u8fce\u81f3AdGuard Home\uff01",
"install_welcome_desc": "AdGuard Home\u662f\u5168\u7db2\u8def\u7bc4\u570d\u5ee3\u544a\u548c\u8ffd\u8e64\u5668\u5c01\u9396\u7684DNS\u4f3a\u670d\u5668\u3002\u5b83\u7684\u76ee\u7684\u70ba\u8b93\u60a8\u63a7\u5236\u60a8\u6574\u500b\u7684\u7db2\u8def\u548c\u6240\u6709\u60a8\u7684\u88dd\u7f6e\uff0c\u4e14\u4e0d\u9700\u8981\u4f7f\u7528\u7528\u6236\u7aef\u7a0b\u5f0f\u3002",
"install_settings_title": "\u7ba1\u7406\u54e1\u7db2\u9801\u4ecb\u9762",
"install_settings_listen": "\u76e3\u807d\u4ecb\u9762",
"install_settings_port": "\u9023\u63a5\u57e0",
"install_settings_interface_link": "\u60a8\u7684AdGuard Home\u7ba1\u7406\u54e1\u7db2\u9801\u4ecb\u9762\u5c07\u65bc\u4e0b\u5217\u7684\u4f4d\u5740\u4e0a\u70ba\u53ef\u7528\u7684\uff1a",
"form_error_port": "\u8f38\u5165\u6709\u6548\u7684\u9023\u63a5\u57e0\u503c",
"install_settings_dns": "DNS \u4f3a\u670d\u5668",
"install_settings_dns_desc": "\u60a8\u5c07\u9700\u8981\u914d\u7f6e\u60a8\u7684\u88dd\u7f6e\u6216\u8def\u7531\u5668\u4ee5\u4f7f\u7528\u65bc\u4e0b\u5217\u7684\u4f4d\u5740\u4e0a\u4e4bDNS\u4f3a\u670d\u5668\uff1a",
"install_settings_all_interfaces": "\u6240\u6709\u7684\u4ecb\u9762",
"install_auth_title": "\u9a57\u8b49",
"install_auth_desc": "\u88ab\u975e\u5e38\u5efa\u8b70\u914d\u7f6e\u5c6c\u65bc\u60a8\u7684AdGuard Home\u7ba1\u7406\u54e1\u7db2\u9801\u4ecb\u9762\u4e4b\u5bc6\u78bc\u9a57\u8b49\u3002\u5373\u4f7f\u5b83\u50c5\u5728\u60a8\u7684\u5340\u57df\u7db2\u8def\u4e2d\u70ba\u53ef\u5b58\u53d6\u7684\uff0c\u8b93\u5b83\u53d7\u4fdd\u8b77\u514d\u65bc\u4e0d\u53d7\u9650\u5236\u7684\u5b58\u53d6\u70ba\u4ecd\u7136\u91cd\u8981\u7684\u3002",
"install_auth_username": "\u7528\u6236\u540d",
"install_auth_password": "\u5bc6\u78bc",
"install_auth_confirm": "\u78ba\u8a8d\u5bc6\u78bc",
"install_auth_username_enter": "\u8f38\u5165\u7528\u6236\u540d",
"install_auth_password_enter": "\u8f38\u5165\u5bc6\u78bc",
"install_step": "\u6b65\u9a5f",
"install_devices_title": "\u914d\u7f6e\u60a8\u7684\u88dd\u7f6e",
"install_devices_desc": "\u70ba\u4f7fAdGuard Home\u958b\u59cb\u904b\u4f5c\uff0c\u60a8\u9700\u8981\u914d\u7f6e\u60a8\u7684\u88dd\u7f6e\u4ee5\u4f7f\u7528\u5b83\u3002",
"install_submit_title": "\u606d\u559c\uff01",
"install_submit_desc": "\u8a72\u8a2d\u7f6e\u7a0b\u5e8f\u88ab\u5b8c\u6210\uff0c\u4e14\u60a8\u6e96\u5099\u597d\u958b\u59cb\u4f7f\u7528AdGuard Home\u3002",
"install_devices_router": "\u8def\u7531\u5668",
"install_devices_router_desc": "\u8a72\u8a2d\u7f6e\u5c07\u81ea\u52d5\u5730\u6db5\u84cb\u88ab\u9023\u7dda\u81f3\u60a8\u7684\u5bb6\u5ead\u8def\u7531\u5668\u4e4b\u6240\u6709\u7684\u88dd\u7f6e\uff0c\u4e14\u60a8\u5c07\u7121\u9700\u624b\u52d5\u5730\u914d\u7f6e\u5b83\u5011\u6bcf\u500b\u3002",
"install_devices_address": "AdGuard Home DNS\u4f3a\u670d\u5668\u6b63\u5728\u76e3\u807d\u4e0b\u5217\u7684\u4f4d\u5740",
"install_devices_router_list_1": "\u958b\u555f\u95dc\u65bc\u60a8\u7684\u8def\u7531\u5668\u4e4b\u504f\u597d\u8a2d\u5b9a\u3002\u901a\u5e38\u5730\uff0c\u60a8\u53ef\u900f\u904e\u7db2\u5740\uff08\u5982 http:\/\/192.168.0.1\/ \u6216 http:\/\/192.168.1.1\/\uff09\u5f9e\u60a8\u7684\u700f\u89bd\u5668\u4e2d\u5b58\u53d6\u5b83\u3002\u60a8\u53ef\u80fd\u88ab\u8981\u6c42\u8f38\u5165\u8a72\u5bc6\u78bc\u3002\u5982\u679c\u60a8\u4e0d\u8a18\u5f97\u5b83\uff0c\u60a8\u7d93\u5e38\u53ef\u900f\u904e\u6309\u58d3\u65bc\u8a72\u8def\u7531\u5668\u672c\u8eab\u4e0a\u7684\u6309\u9215\u4f86\u91cd\u7f6e\u5bc6\u78bc\u3002\u67d0\u4e9b\u8def\u7531\u5668\u9700\u8981\u7279\u5b9a\u7684\u61c9\u7528\u7a0b\u5f0f\uff0c\u65e2\u7136\u5982\u6b64\u5176\u61c9\u5df2\u88ab\u5b89\u88dd\u65bc\u60a8\u7684\u96fb\u8166\/\u624b\u6a5f\u4e0a\u3002",
"install_devices_router_list_2": "\u627e\u5230DHCP\/DNS\u8a2d\u5b9a\u3002\u5c0b\u627e\u7dca\u9130\u8457\u5141\u8a31\u5169\u7d44\u6216\u4e09\u7d44\u6578\u5b57\u96c6\u7684\u6b04\u4f4d\u4e4bDNS\u5b57\u6bcd\uff0c\u6bcf\u7d44\u88ab\u62c6\u6210\u56db\u500b\u542b\u6709\u4e00\u81f3\u4e09\u500b\u6578\u5b57\u7684\u7fa4\u96c6\u3002",
"install_devices_router_list_3": "\u5728\u90a3\u88e1\u8f38\u5165\u60a8\u7684AdGuard Home\u4f3a\u670d\u5668\u4f4d\u5740\u3002",
"install_devices_windows_list_1": "\u901a\u904e\u958b\u59cb\u529f\u80fd\u8868\u6216Windows \u641c\u5c0b\uff0c\u958b\u555f\u63a7\u5236\u53f0\u3002",
"install_devices_windows_list_2": "\u53bb\u7db2\u8def\u548c\u7db2\u969b\u7db2\u8def\u985e\u5225\uff0c\u7136\u5f8c\u53bb\u7db2\u8def\u548c\u5171\u7528\u4e2d\u5fc3\u3002",
"install_devices_windows_list_3": "\u65bc\u756b\u9762\u4e4b\u5de6\u5074\u4e0a\u627e\u5230\u8b8a\u66f4\u4ecb\u9762\u5361\u8a2d\u5b9a\u4e26\u65bc\u5b83\u4e0a\u9ede\u64ca\u3002",
"install_devices_windows_list_4": "\u9078\u64c7\u60a8\u73fe\u884c\u7684\u9023\u7dda\uff0c\u65bc\u5b83\u4e0a\u9ede\u64ca\u6ed1\u9f20\u53f3\u9375\uff0c\u7136\u5f8c\u9078\u64c7\u5167\u5bb9\u3002",
"install_devices_windows_list_5": "\u5728\u6e05\u55ae\u4e2d\u627e\u5230\u7db2\u969b\u7db2\u8def\u901a\u8a0a\u5354\u5b9a\u7b2c 4 \u7248\uff08TCP\/IPv4\uff09\uff0c\u9078\u64c7\u5b83\uff0c\u7136\u5f8c\u518d\u6b21\u65bc\u5167\u5bb9\u4e0a\u9ede\u64ca\u3002",
"install_devices_windows_list_6": "\u9078\u64c7\u4f7f\u7528\u4e0b\u5217\u7684DNS\u4f3a\u670d\u5668\u4f4d\u5740\uff0c\u7136\u5f8c\u8f38\u5165\u60a8\u7684AdGuard Home\u4f3a\u670d\u5668\u4f4d\u5740\u3002",
"install_devices_macos_list_1": "\u65bcApple\u5716\u50cf\u4e0a\u9ede\u64ca\uff0c\u7136\u5f8c\u53bb\u7cfb\u7d71\u504f\u597d\u8a2d\u5b9a\u3002",
"install_devices_macos_list_2": "\u65bc\u7db2\u8def\u4e0a\u9ede\u64ca\u3002",
"install_devices_macos_list_3": "\u9078\u64c7\u5728\u60a8\u7684\u6e05\u55ae\u4e2d\u4e4b\u9996\u8981\u7684\u9023\u7dda\uff0c\u7136\u5f8c\u9ede\u64ca\u9032\u968e\u7684\u3002",
"install_devices_macos_list_4": "\u9078\u64c7\u8a72DNS\u5206\u9801\uff0c\u7136\u5f8c\u8f38\u5165\u60a8\u7684AdGuard Home\u4f3a\u670d\u5668\u4f4d\u5740\u3002",
"install_devices_android_list_1": "\u5f9eAndroid\u9078\u55ae\u4e3b\u756b\u9762\u4e2d\uff0c\u8f15\u89f8\u8a2d\u5b9a\u3002",
"install_devices_android_list_2": "\u65bc\u8a72\u9078\u55ae\u4e0a\u8f15\u89f8Wi-Fi\u3002\u6b63\u5728\u5217\u51fa\u6240\u6709\u53ef\u7528\u7684\u7db2\u8def\u4e4b\u756b\u9762\u5c07\u88ab\u986f\u793a\uff08\u4e0d\u53ef\u80fd\u70ba\u884c\u52d5\u9023\u7dda\u8a2d\u5b9a\u81ea\u8a02\u7684DNS\uff09\u3002",
"install_devices_android_list_3": "\u9577\u6309\u60a8\u6240\u9023\u7dda\u81f3\u7684\u7db2\u8def\uff0c\u7136\u5f8c\u8f15\u89f8\u4fee\u6539\u7db2\u8def\u3002",
"install_devices_android_list_4": "\u65bc\u67d0\u4e9b\u88dd\u7f6e\u4e0a\uff0c\u60a8\u53ef\u80fd\u9700\u8981\u6aa2\u67e5\u95dc\u65bc\u9032\u968e\u7684\u65b9\u6846\u4ee5\u67e5\u770b\u9032\u4e00\u6b65\u7684\u8a2d\u5b9a\u3002\u70ba\u4e86\u8abf\u6574\u60a8\u7684Android DNS\u8a2d\u5b9a\uff0c\u60a8\u5c07\u9700\u8981\u628aIP \u8a2d\u5b9a\u5f9eDHCP\u8f49\u63db\u6210\u975c\u614b\u3002",
"install_devices_android_list_5": "\u4f7f\u8a2d\u5b9aDNS 1\u548cDNS 2\u503c\u66f4\u6539\u6210\u60a8\u7684AdGuard Home\u4f3a\u670d\u5668\u4f4d\u5740\u3002",
"install_devices_ios_list_1": "\u5f9e\u4e3b\u756b\u9762\u4e2d\uff0c\u8f15\u89f8\u8a2d\u5b9a\u3002",
"install_devices_ios_list_2": "\u5728\u5de6\u5074\u7684\u9078\u55ae\u4e2d\u9078\u64c7Wi-Fi\uff08\u4e0d\u53ef\u80fd\u70ba\u884c\u52d5\u7db2\u8def\u914d\u7f6eDNS\uff09\u3002",
"install_devices_ios_list_3": "\u65bc\u76ee\u524d\u73fe\u884c\u7684\u7db2\u8def\u4e4b\u540d\u7a31\u4e0a\u8f15\u89f8\u3002",
"install_devices_ios_list_4": "\u5728\u8a72DNS\u6b04\u4f4d\u4e2d\uff0c\u8f38\u5165\u60a8\u7684AdGuard Home\u4f3a\u670d\u5668\u4f4d\u5740\u3002",
"get_started": "\u958b\u59cb\u5427",
"next": "\u4e0b\u4e00\u6b65",
"open_dashboard": "\u958b\u555f\u5100\u8868\u677f",
"install_saved": "\u5df2\u6210\u529f\u5730\u5132\u5b58",
"encryption_title": "\u52a0\u5bc6",
"encryption_desc": "\u52a0\u5bc6\uff08HTTPS\/TLS\uff09\u652f\u63f4\u4f9bDNS\u548c\u7ba1\u7406\u54e1\u7db2\u9801\u4ecb\u9762\u5169\u8005",
"encryption_config_saved": "\u52a0\u5bc6\u914d\u7f6e\u5df2\u88ab\u5132\u5b58",
"encryption_server": "\u4f3a\u670d\u5668\u540d\u7a31",
"encryption_server_enter": "\u8f38\u5165\u60a8\u7684\u57df\u540d",
"encryption_server_desc": "\u70ba\u4e86\u4f7f\u7528HTTPS\uff0c\u60a8\u9700\u8981\u8f38\u5165\u8207\u60a8\u7684\u5b89\u5168\u901a\u8a0a\u7aef\u5c64\uff08SSL\uff09\u6191\u8b49\u76f8\u7b26\u7684\u4f3a\u670d\u5668\u540d\u7a31\u3002",
"encryption_redirect": "\u81ea\u52d5\u5730\u91cd\u5b9a\u5411\u5230HTTPS",
"encryption_redirect_desc": "\u5982\u679c\u88ab\u52fe\u9078\uff0cAdGuard Home\u5c07\u81ea\u52d5\u5730\u91cd\u5b9a\u5411\u60a8\u5f9eHTTP\u5230HTTPS\u4f4d\u5740\u3002",
"encryption_https": "HTTPS \u9023\u63a5\u57e0",
"encryption_https_desc": "\u5982\u679cHTTPS\u9023\u63a5\u57e0\u88ab\u914d\u7f6e\uff0cAdGuard Home\u7ba1\u7406\u54e1\u4ecb\u9762\u900f\u904eHTTPS\u5c07\u70ba\u53ef\u5b58\u53d6\u7684\uff0c\u4e14\u5b83\u4e5f\u5c07\u65bc '\/dns-query' \u4f4d\u7f6e\u4e0a\u63d0\u4f9bDNS-over-HTTPS\u3002",
"encryption_dot": "DNS-over-TLS \u9023\u63a5\u57e0",
"encryption_dot_desc": "\u5982\u679c\u8a72\u9023\u63a5\u57e0\u88ab\u914d\u7f6e\uff0cAdGuard Home\u5c07\u65bc\u6b64\u9023\u63a5\u57e0\u4e0a\u904b\u884cDNS-over-TLS\u4f3a\u670d\u5668\u3002",
"encryption_certificates": "\u6191\u8b49",
"encryption_certificates_desc": "\u70ba\u4e86\u4f7f\u7528\u52a0\u5bc6\uff0c\u60a8\u9700\u8981\u63d0\u4f9b\u6709\u6548\u7684\u5b89\u5168\u901a\u8a0a\u7aef\u5c64\uff08SSL\uff09\u6191\u8b49\u93c8\u7d50\u4f9b\u60a8\u7684\u7db2\u57df\u3002\u65bc <0>{{link}}<\/0> \u4e0a\u60a8\u53ef\u53d6\u5f97\u514d\u8cbb\u7684\u6191\u8b49\u6216\u60a8\u53ef\u5f9e\u53d7\u4fe1\u4efb\u7684\u6191\u8b49\u6388\u6b0a\u55ae\u4f4d\u4e4b\u4e00\u8cfc\u8cb7\u5b83\u3002",
"encryption_certificates_input": "\u65bc\u6b64\u8907\u88fd\/\u8cbc\u4e0a\u60a8\u7684\u96b1\u79c1\u589e\u5f37\u90f5\u4ef6\u7de8\u78bc\u4e4b\uff08PEM-encoded\uff09\u6191\u8b49\u3002",
"encryption_status": "\u72c0\u614b",
"encryption_expire": "\u5230\u671f",
"encryption_key": "\u79c1\u5bc6\u91d1\u9470",
"encryption_key_input": "\u65bc\u6b64\u8907\u88fd\/\u8cbc\u4e0a\u60a8\u7684\u96b1\u79c1\u589e\u5f37\u90f5\u4ef6\u7de8\u78bc\u4e4b\uff08PEM-encoded\uff09\u79c1\u5bc6\u91d1\u9470\u4f9b\u60a8\u7684\u6191\u8b49\u3002",
"encryption_enable": "\u555f\u7528\u52a0\u5bc6\uff08HTTPS\u3001DNS-over-HTTPS\u548cDNS-over-TLS\uff09",
"encryption_enable_desc": "\u5982\u679c\u52a0\u5bc6\u88ab\u555f\u7528\uff0cAdGuard Home\u7ba1\u7406\u54e1\u4ecb\u9762\u900f\u904eHTTPS\u5c07\u904b\u4f5c\uff0c\u4e14\u8a72DNS\u4f3a\u670d\u5668\u5c07\u7559\u5fc3\u76e3\u807d\u900f\u904eDNS-over-HTTPS\u548cDNS-over-TLS\u4e4b\u8acb\u6c42\u3002",
"encryption_chain_valid": "\u6191\u8b49\u93c8\u7d50\u70ba\u6709\u6548\u7684",
"encryption_chain_invalid": "\u6191\u8b49\u93c8\u7d50\u70ba\u7121\u6548\u7684",
"encryption_key_valid": "\u6b64\u70ba\u6709\u6548\u7684 {{type}} \u79c1\u5bc6\u91d1\u9470",
"encryption_key_invalid": "\u6b64\u70ba\u7121\u6548\u7684 {{type}} \u79c1\u5bc6\u91d1\u9470",
"encryption_subject": "\u7269\u4ef6",
"encryption_issuer": "\u7c3d\u767c\u8005",
"encryption_hostnames": "\u4e3b\u6a5f\u540d\u7a31",
"encryption_reset": "\u60a8\u78ba\u5b9a\u60a8\u60f3\u8981\u91cd\u7f6e\u52a0\u5bc6\u8a2d\u5b9a\u55ce\uff1f",
"topline_expiring_certificate": "\u60a8\u7684\u5b89\u5168\u901a\u8a0a\u7aef\u5c64\uff08SSL\uff09\u6191\u8b49\u5373\u5c07\u5230\u671f\u3002\u66f4\u65b0<0>\u52a0\u5bc6\u8a2d\u5b9a<\/0>\u3002",
"topline_expired_certificate": "\u60a8\u7684\u5b89\u5168\u901a\u8a0a\u7aef\u5c64\uff08SSL\uff09\u6191\u8b49\u70ba\u5df2\u5230\u671f\u7684\u3002\u66f4\u65b0<0>\u52a0\u5bc6\u8a2d\u5b9a<\/0>\u3002",
"form_error_port_range": "\u572880-65535\u4e4b\u7bc4\u570d\u5167\u8f38\u5165\u9023\u63a5\u57e0\u503c",
"form_error_port_unsafe": "\u6b64\u70ba\u4e0d\u5b89\u5168\u7684\u9023\u63a5\u57e0",
"form_error_equal": "\u4e0d\u61c9\u70ba\u76f8\u7b49\u7684",
"form_error_password": "\u4e0d\u76f8\u7b26\u7684\u5bc6\u78bc",
"reset_settings": "\u91cd\u7f6e\u8a2d\u5b9a",
"update_announcement": "AdGuard Home {{version}} \u73fe\u70ba\u53ef\u7528\u7684\uff01\u95dc\u65bc\u66f4\u591a\u7684\u8cc7\u8a0a\uff0c<0>\u9ede\u64ca\u9019\u88e1<\/0>\u3002",
"setup_guide": "\u5b89\u88dd\u6307\u5357",
"dns_addresses": "DNS \u4f4d\u5740"
"client_settings": "用戶端設定",
"example_upstream_reserved": "您可明確指定<0>用於特定的網域</0>之 DNS 上游",
"upstream_parallel": "透過同時地查詢所有上游的伺服器,使用並行的查詢以加速解析",
"bootstrap_dns": "自我啟動BootstrapDNS 伺服器",
"bootstrap_dns_desc": "自我啟動BootstrapDNS 伺服器被用於解析您明確指定作為上游的 DoH/DoT 解析器之 IP 位址。",
"url_added_successfully": "網址被成功地加入",
"check_dhcp_servers": "檢查動態主機設定協定DHCP伺服器",
"save_config": "儲存配置",
"enabled_dhcp": "動態主機設定協定DHCP伺服器被啟用",
"disabled_dhcp": "動態主機設定協定DHCP伺服器被禁用",
"dhcp_title": "動態主機設定協定DHCP伺服器實驗性的",
"dhcp_description": "如果您的路由器未提供動態主機設定協定DHCP設定您可使用 AdGuard 自身內建的 DHCP 伺服器。",
"dhcp_enable": "啟用動態主機設定協定DHCP伺服器",
"dhcp_disable": "禁用動態主機設定協定DHCP伺服器",
"dhcp_not_found": "啟用內建的動態主機設定協定DHCP伺服器為安全的 - 於該網路上,我們未發現任何現行的 DHCP 伺服器。然而,我們鼓勵您手動地重新檢查它,因為我們的自動之測試目前不予 100 保證。",
"dhcp_found": "於該網路上一個現行的動態主機設定協定DHCP伺服器被發現。啟用內建的 DHCP 伺服器為不安全的。",
"dhcp_leases": "動態主機設定協定DHCP租賃",
"dhcp_static_leases": "動態主機設定協定DHCP靜態租賃",
"dhcp_leases_not_found": "無已發現之動態主機設定協定DHCP租賃",
"dhcp_config_saved": "已儲存動態主機設定協定DHCP伺服器配置",
"form_error_required": "必填的欄位",
"form_error_ip_format": "無效的 IPv4 格式",
"form_error_mac_format": "無效的媒體存取控制MAC格式",
"form_error_positive": "必須大於 0",
"dhcp_form_gateway_input": "閘道 IP",
"dhcp_form_subnet_input": "子網路遮罩",
"dhcp_form_range_title": "IP 位址範圍",
"dhcp_form_range_start": "範圍開始",
"dhcp_form_range_end": "範圍結束",
"dhcp_form_lease_title": "動態主機設定協定DHCP租賃時間以秒數",
"dhcp_form_lease_input": "租賃持續時間",
"dhcp_interface_select": "選擇動態主機設定協定DHCP介面",
"dhcp_hardware_address": "硬體位址",
"dhcp_ip_addresses": "IP 位址",
"dhcp_table_hostname": "主機名稱",
"dhcp_table_expires": "到期",
"dhcp_warning": "如果您無論如何想要啟用動態主機設定協定DHCP伺服器確保在您的網路無其它現行的 DHCP 伺服器。否則,它可能會破壞供已連線的裝置之網際網路!",
"dhcp_error": "我們無法確定在該網路是否有另外的動態主機設定協定DHCP伺服器。",
"dhcp_static_ip_error": "為了使用動態主機設定協定DHCP伺服器靜態 IP 位址必須被設定。我們未能確定該網路介面是否被配置使用靜態 IP 位址。請手動地設定靜態 IP 位址。",
"dhcp_dynamic_ip_found": "您的系統使用動態 IP 位址配置供介面 <0>{{interfaceName}}</0>。為了使用動態主機設定協定DHCP伺服器靜態 IP 位址必須被設定。您現行的 IP 位址為 <0>{{ipAddress}}</0>。如果您按啟用 DHCP 按鈕,我們將自動地設定此 IP 位址作為靜態。",
"dhcp_lease_added": "靜態租賃 \"{{key}}\" 被成功地加入",
"dhcp_lease_deleted": "靜態租賃 \"{{key}}\" 被成功地刪除",
"dhcp_new_static_lease": "新的靜態租賃",
"dhcp_static_leases_not_found": "無已發現之動態主機設定協定DHCP靜態租賃",
"dhcp_add_static_lease": "增加靜態租賃",
"delete_confirm": "您確定您想要刪除 \"{{key}}\" 嗎?",
"form_enter_hostname": "輸入主機名稱",
"error_details": "錯誤細節",
"back": "返回",
"dashboard": "儀表板",
"settings": "設定",
"filters": "過濾器",
"query_log": "查詢記錄",
"faq": "常見問答集",
"version": "版本",
"address": "位址",
"on": "開著",
"off": "關著",
"copyright": "版權",
"homepage": "首頁",
"report_an_issue": "報告問題",
"privacy_policy": "隱私政策",
"enable_protection": "啟用防護",
"enabled_protection": "已啟用防護",
"disable_protection": "禁用防護",
"disabled_protection": "已禁用防護",
"refresh_statics": "重新整理統計資料",
"dns_query": "DNS 查詢",
"blocked_by": "被過濾器封鎖",
"stats_malware_phishing": "已封鎖的惡意軟體/網路釣魚",
"stats_adult": "已封鎖的成人網站",
"stats_query_domain": "熱門已查詢的網域",
"for_last_24_hours": "在最近的 24 小時內",
"no_domains_found": "無已發現之網域",
"requests_count": "請求總數",
"top_blocked_domains": "熱門已封鎖的網域",
"top_clients": "熱門用戶端",
"no_clients_found": "無已發現之用戶端",
"general_statistics": "一般的統計資料",
"number_of_dns_query_24_hours": "在最近的 24 小時內已處理的 DNS 查詢之數量",
"number_of_dns_query_blocked_24_hours": "被廣告封鎖過濾器和主機封鎖清單封鎖的 DNS 請求之數量",
"number_of_dns_query_blocked_24_hours_by_sec": "被 AdGuard 瀏覽安全模組封鎖的 DNS 請求之數量",
"number_of_dns_query_blocked_24_hours_adult": "已封鎖的成人網站之數量",
"enforced_save_search": "已強制執行的安全搜尋",
"number_of_dns_query_to_safe_search": "安全搜尋已被強制執行之屬於搜尋引擎的 DNS 請求之數量",
"average_processing_time": "平均的處理時間",
"average_processing_time_hint": "於處理一項 DNS 請求上以毫秒ms計之平均的時間",
"block_domain_use_filters_and_hosts": "透過過濾器和主機檔案封鎖網域",
"filters_block_toggle_hint": "您可在<a href='#filters'>過濾器</a>設定中設置封鎖規則。",
"use_adguard_browsing_sec": "使用 AdGuard 瀏覽安全網路服務",
"use_adguard_browsing_sec_hint": "AdGuard Home 將檢查網域是否被瀏覽安全網路服務列入黑名單。它將使用友好的隱私查找應用程式介面API以執行檢查僅域名 SHA256 雜湊的短前綴被傳送到伺服器。",
"use_adguard_parental": "使用 AdGuard 家長監控之網路服務",
"use_adguard_parental_hint": "AdGuard Home 將檢查網域是否包含成人資料。它使用如同瀏覽安全網路服務一樣之友好的隱私應用程式介面API",
"enforce_safe_search": "強制執行安全搜尋",
"enforce_save_search_hint": "AdGuard Home 可在下列的搜尋引擎Google、YouTube、Bing、DuckDuckGo 和 Yandex 中強制執行安全搜尋。",
"no_servers_specified": "無已明確指定的伺服器",
"no_settings": "無設定",
"general_settings": "一般的設定",
"dns_settings": "DNS 設定",
"encryption_settings": "加密設定",
"dhcp_settings": "動態主機設定協定DHCP設定",
"upstream_dns": "上游的 DNS 伺服器",
"upstream_dns_hint": "如果您將該欄位留空AdGuard Home 將使用 <a href='https://1.1.1.1/' target='_blank'>Cloudflare DNS</a> 作為上游。",
"test_upstream_btn": "測試上行資料流",
"apply_btn": "套用",
"disabled_filtering_toast": "已禁用過濾",
"enabled_filtering_toast": "已啟用過濾",
"disabled_safe_browsing_toast": "已禁用安全瀏覽",
"enabled_safe_browsing_toast": "已啟用安全瀏覽",
"disabled_parental_toast": "已禁用家長監控",
"enabled_parental_toast": "已啟用家長監控",
"disabled_safe_search_toast": "已禁用安全搜尋",
"enabled_save_search_toast": "已啟用安全搜尋",
"enabled_table_header": "已啟用的",
"name_table_header": "名稱",
"filter_url_table_header": "過濾器網址",
"rules_count_table_header": "規則總數",
"last_time_updated_table_header": "最近的更新時間",
"actions_table_header": "行動",
"edit_table_action": "編輯",
"delete_table_action": "刪除",
"filters_and_hosts": "過濾器和主機封鎖清單",
"filters_and_hosts_hint": "AdGuard Home 懂得基本的廣告封鎖規則和主機檔案語法。",
"no_filters_added": "無已加入的過濾器",
"add_filter_btn": "增加過濾器",
"cancel_btn": "取消",
"enter_name_hint": "輸入名稱",
"enter_url_hint": "輸入網址",
"check_updates_btn": "檢查更新",
"new_filter_btn": "新的過濾器訂閱",
"enter_valid_filter_url": "輸入關於過濾器訂閱或主機檔案之有效的網址。",
"custom_filter_rules": "自訂的過濾規則",
"custom_filter_rules_hint": "於一行上輸入一個規則。您可使用廣告封鎖規則或主機檔案語法。",
"examples_title": "範例",
"example_meaning_filter_block": "封鎖至 example.org 網域及其所有的子網域之存取",
"example_meaning_filter_whitelist": "解除封鎖至 example.org 網域及其所有的子網域之存取",
"example_meaning_host_block": "AdGuard Home 現在將對 example.org 網域返回 127.0.0.1 位址(但非其子網域)。",
"example_comment": "! 看,一個註解",
"example_comment_meaning": "只是一個註解",
"example_comment_hash": "# 也是一個註解",
"example_regex_meaning": "封鎖至與<0>已明確指定的規則運算式</0>Regular Expression相符的網域之存取",
"example_upstream_regular": "一般的 DNS透過 UDP",
"example_upstream_dot": "加密的 <0>DNS-over-TLS</0>",
"example_upstream_doh": "加密的 <0>DNS-over-HTTPS</0>",
"example_upstream_sdns": "您可使用關於 <1>DNSCrypt</1> 或 <2>DNS-over-HTTPS</2> 解析器之 <0>DNS 戳記</0>",
"example_upstream_tcp": "一般的 DNS透過 TCP",
"all_filters_up_to_date_toast": "所有的過濾器已是最新的",
"updated_upstream_dns_toast": "已更新上游的 DNS 伺服器",
"dns_test_ok_toast": "已明確指定的 DNS 伺服器正在正確地運作",
"dns_test_not_ok_toast": "伺服器 \"{{key}}\":無法被使用,請檢查您已正確地填寫它",
"unblock_btn": "解除封鎖",
"block_btn": "封鎖",
"time_table_header": "時間",
"domain_name_table_header": "域名",
"type_table_header": "類型",
"response_table_header": "回應",
"client_table_header": "用戶端",
"empty_response_status": "空白的",
"show_all_filter_type": "顯示全部",
"show_filtered_type": "顯示已過濾的",
"no_logs_found": "無已發現之記錄",
"disabled_log_btn": "禁用記錄",
"download_log_file_btn": "下載記錄檔案",
"refresh_btn": "重新整理",
"enabled_log_btn": "啟用記錄",
"last_dns_queries": "最近的 5000 筆 DNS 查詢",
"previous_btn": "上一頁",
"next_btn": "下一頁",
"loading_table_status": "正在載入…",
"page_table_footer_text": "頁面",
"of_table_footer_text": "之",
"rows_table_footer_text": "列",
"updated_custom_filtering_toast": "已更新自訂的過濾規則",
"rule_removed_from_custom_filtering_toast": "規則從自訂的過濾規則中被移除",
"rule_added_to_custom_filtering_toast": "規則被加至自訂的過濾規則中",
"query_log_disabled_toast": "查詢記錄被禁用",
"query_log_enabled_toast": "查詢記錄被啟用",
"source_label": "來源",
"found_in_known_domain_db": "在已知的域名資料庫中被發現。",
"category_label": "類別",
"rule_label": "規則",
"filter_label": "過濾器",
"unknown_filter": "未知的過濾器 {{filterId}}",
"install_welcome_title": "歡迎至 AdGuard Home",
"install_welcome_desc": "AdGuard Home 是全網路範圍廣告和追蹤器封鎖的 DNS 伺服器。它的目的為讓您控制您整個的網路和所有您的裝置,且不需要使用用戶端程式。",
"install_settings_title": "管理員網路介面",
"install_settings_listen": "監聽介面",
"install_settings_port": "連接埠",
"install_settings_interface_link": "您的 AdGuard Home 管理員網路介面將於下列的位址上為可用的:",
"form_error_port": "輸入有效的連接埠值",
"install_settings_dns": "DNS 伺服器",
"install_settings_dns_desc": "您將需要配置您的裝置或路由器以使用於下列的位址上之 DNS 伺服器:",
"install_settings_all_interfaces": "所有的介面",
"install_auth_title": "驗證",
"install_auth_desc": "被非常建議配置屬於您的 AdGuard Home 管理員網路介面之密碼驗證。即使它僅在您的區域網路中為可存取的,讓它受保護免於不受限制的存取為仍然重要的。",
"install_auth_username": "使用者名稱",
"install_auth_password": "密碼",
"install_auth_confirm": "確認密碼",
"install_auth_username_enter": "輸入使用者名稱",
"install_auth_password_enter": "輸入密碼",
"install_step": "步驟",
"install_devices_title": "配置您的裝置",
"install_devices_desc": "為了開始使用 AdGuard Home您需要配置您的裝置以使用它。",
"install_submit_title": "恭喜!",
"install_submit_desc": "該設置程序被完成,且您準備好開始使用 AdGuard Home。",
"install_devices_router": "路由器",
"install_devices_router_desc": "該設置將自動地涵蓋被連線至您的家庭路由器之所有的裝置,且您將無需手動地配置它們每個。",
"install_devices_address": "AdGuard Home DNS 伺服器正在監聽下列的位址",
"install_devices_router_list_1": "開啟關於您的路由器之偏好設定。通常地,您可透過網址(如 http://192.168.0.1/ 或 http://192.168.1.1/)從您的瀏覽器中存取它。您可能被要求輸入該密碼。如果您不記得它,您經常可透過按壓於該路由器本身上的按鈕來重置密碼。某些路由器需要特定的應用程式,既然如此其應已被安裝於您的電腦/手機上。",
"install_devices_router_list_2": "找到 DHCP/DNS 設定。尋找緊鄰著允許兩組或三組數字集的欄位之 DNS 字母,每組被拆成四個含有一至三個數字的群集。",
"install_devices_router_list_3": "在那裡輸入您的 AdGuard Home 伺服器位址。",
"install_devices_windows_list_1": "通過開始功能表或 Windows 搜尋,開啟控制台。",
"install_devices_windows_list_2": "去網路和網際網路類別,然後去網路和共用中心。",
"install_devices_windows_list_3": "於畫面之左側上找到變更介面卡設定並於它上點擊。",
"install_devices_windows_list_4": "選擇您現行的連線,於它上點擊滑鼠右鍵,然後選擇內容。",
"install_devices_windows_list_5": "在清單中找到網際網路通訊協定第 4 版TCP/IPv4選擇它然後再次於內容上點擊。",
"install_devices_windows_list_6": "選擇使用下列的 DNS 伺服器位址,然後輸入您的 AdGuard Home 伺服器位址。",
"install_devices_macos_list_1": "於 Apple 圖像上點擊,然後去系統偏好設定。",
"install_devices_macos_list_2": "於網路上點擊。",
"install_devices_macos_list_3": "選擇在您的清單中之首要的連線,然後點擊進階的。",
"install_devices_macos_list_4": "選擇該 DNS 分頁,然後輸入您的 AdGuard Home 伺服器位址。",
"install_devices_android_list_1": "從 Android 選單主畫面中,輕觸設定。",
"install_devices_android_list_2": "於該選單上輕觸 Wi-Fi。正在列出所有可用的網路之畫面將被顯示不可能為行動連線設定自訂的 DNS",
"install_devices_android_list_3": "長按您所連線至的網路,然後輕觸修改網路。",
"install_devices_android_list_4": "於某些裝置上,您可能需要檢查關於進階的方框以查看進一步的設定。為了調整您的 Android DNS 設定,您將需要把 IP 設定從 DHCP 轉換成靜態。",
"install_devices_android_list_5": "更改 DNS 1 和 DNS 2 位置的值為您的 AdGuard Home 伺服器位址。",
"install_devices_ios_list_1": "從主畫面中,輕觸設定。",
"install_devices_ios_list_2": "在左側的選單中選擇 Wi-Fi不可能為行動網路配置 DNS",
"install_devices_ios_list_3": "於目前現行的網路之名稱上輕觸。",
"install_devices_ios_list_4": "在該 DNS 欄位中,輸入您的 AdGuard Home 伺服器位址。",
"get_started": "開始吧",
"next": "下一頁",
"open_dashboard": "開啟儀表板",
"install_saved": "已成功地儲存",
"encryption_title": "加密",
"encryption_desc": "供 DNS 和管理員網路介面兩者之加密HTTPS/TLS支援",
"encryption_config_saved": "加密配置被儲存",
"encryption_server": "伺服器名稱",
"encryption_server_enter": "輸入您的域名",
"encryption_server_desc": "為了使用 HTTPS您需要輸入與您的安全通訊端層SSL憑證相符的伺服器名稱。",
"encryption_redirect": "自動地重新導向到 HTTPS",
"encryption_redirect_desc": "如果被勾選AdGuard Home 將自動地重新導向您從 HTTP 到 HTTPS 位址。",
"encryption_https": "HTTPS 連接埠",
"encryption_https_desc": "如果 HTTPS 連接埠被配置AdGuard Home 管理員介面透過 HTTPS 將為可存取的,且它也將於 '/dns-query' 位置上提供 DNS-over-HTTPS。",
"encryption_dot": "DNS-over-TLS 連接埠",
"encryption_dot_desc": "如果該連接埠被配置AdGuard Home 將於此連接埠上運行 DNS-over-TLS 伺服器。",
"encryption_certificates": "憑證",
"encryption_certificates_desc": "為了使用加密您需要提供有效的安全通訊端層SSL憑證鏈結供您的網域。於 <0>{{link}}</0> 上您可取得免費的憑證或您可從受信任的憑證授權單位之一購買它。",
"encryption_certificates_input": "於此複製/貼上您的隱私增強郵件編碼之PEM-encoded憑證。",
"encryption_status": "狀態",
"encryption_expire": "到期",
"encryption_key": "私密金鑰",
"encryption_key_input": "於此複製/貼上您的隱私增強郵件編碼之PEM-encoded私密金鑰供您的憑證。",
"encryption_enable": "啟用加密HTTPS、DNS-over-HTTPS 和 DNS-over-TLS",
"encryption_enable_desc": "如果加密被啟用AdGuard Home 管理員介面透過 HTTPS 將運作,且該 DNS 伺服器將留心監聽透過 DNS-over-HTTPS 和 DNS-over-TLS 之請求。",
"encryption_chain_valid": "憑證鏈結為有效的",
"encryption_chain_invalid": "憑證鏈結為無效的",
"encryption_key_valid": "此為有效的 {{type}} 私密金鑰",
"encryption_key_invalid": "此為無效的 {{type}} 私密金鑰",
"encryption_subject": "物件",
"encryption_issuer": "簽發者",
"encryption_hostnames": "主機名稱",
"encryption_reset": "您確定您想要重置加密設定嗎?",
"topline_expiring_certificate": "您的安全通訊端層SSL憑證即將到期。更新<0>加密設定</0>。",
"topline_expired_certificate": "您的安全通訊端層SSL憑證為已到期的。更新<0>加密設定</0>。",
"form_error_port_range": "在 80-65535 之範圍內輸入連接埠值",
"form_error_port_unsafe": "此為不安全的連接埠",
"form_error_equal": "不應為相等的",
"form_error_password": "不相符的密碼",
"reset_settings": "重置設定",
"update_announcement": "AdGuard Home {{version}} 現為可用的!關於更多的資訊,<0>點擊這裡</0>。",
"setup_guide": "安裝指南",
"dns_addresses": "DNS 位址",
"down": "停止運作的",
"fix": "修復",
"dns_providers": "這裡是一個從中選擇之<0>已知的 DNS 供應商之清單</0>。",
"update_now": "立即更新",
"update_failed": "自動更新已失敗。請<a href='https://github.com/AdguardTeam/AdGuardHome/wiki/Getting-Started#update'>遵循這些步驟</a>以手動地更新。",
"processing_update": "請等待AdGuard Home 正被更新",
"clients_title": "用戶端",
"clients_desc": "配置被連線到 AdGuard Home 的裝置",
"settings_global": "全域的",
"settings_custom": "自訂的",
"table_client": "用戶端",
"table_name": "名稱",
"save_btn": "儲存",
"client_add": "增加用戶端",
"client_new": "新的用戶端",
"client_edit": "編輯用戶端",
"client_identifier": "識別碼",
"ip_address": "IP 位址",
"client_identifier_desc": "用戶端可被 IP 位址或媒體存取控制MAC位址識別。請注意僅若 AdGuard Home 也是<0>動態主機設定協定DHCP伺服器</0>,使用 MAC 作為識別碼是可能的",
"form_enter_ip": "輸入 IP",
"form_enter_mac": "輸入媒體存取控制MAC",
"form_client_name": "輸入用戶端名稱",
"client_global_settings": "使用全域的設定",
"client_deleted": "用戶端 \"{{key}}\" 被成功地刪除",
"client_added": "用戶端 \"{{key}}\" 被成功地加入",
"client_updated": "用戶端 \"{{key}}\" 被成功地更新",
"table_statistics": "請求總數(最近的 24 小時)",
"clients_not_found": "無已發現之用戶端",
"client_confirm_delete": "您確定您想要刪除用戶端 \"{{key}}\" 嗎?",
"filter_confirm_delete": "您確定您想要刪除該過濾器嗎?",
"auto_clients_title": "用戶端(執行時期)",
"auto_clients_desc": "使用 AdGuard Home 但未被儲存在配置中之關於用戶端的資料",
"access_title": "存取設定",
"access_desc": "於此您可配置用於 AdGuard Home DNS 伺服器之存取規則。",
"access_allowed_title": "已允許的用戶端",
"access_allowed_desc": "無類別網域間路由CIDR或 IP 位址之清單。如果被配置AdGuard Home 將僅從這些 IP 位址中接受請求。",
"access_disallowed_title": "不允許的用戶端",
"access_disallowed_desc": "無類別網域間路由CIDR或 IP 位址之清單。如果被配置AdGuard Home 將從這些 IP 位址中排除請求。",
"access_blocked_title": "已封鎖的網域",
"access_blocked_desc": "不要把這個和過濾器混淆。AdGuard Home 將從查詢的詢問中排除有這些網域的 DNS 查詢。",
"access_settings_saved": "存取設定被成功地儲存",
"updates_checked": "更新被成功地檢查",
"updates_version_equal": "AdGuard Home 為最新的",
"check_updates_now": "立即檢查更新",
"dns_privacy": "DNS 隱私",
"setup_dns_privacy_1": "<0>DNS-over-TLS</0>使用 <1>{{address}}</1> 字串。",
"setup_dns_privacy_2": "<0>DNS-over-HTTPS</0>使用 <1>{{address}}</1> 字串。",
"setup_dns_privacy_3": "<0>請注意,加密的 DNS 協定僅於 Android 9 上被支援。所以您需要安裝額外的軟體供其它的作業系統。</0><0>這裡是您可使用的軟體之清單。</0>",
"setup_dns_privacy_android_1": "Android 9 原生地支援 DNS-over-TLS。為了配置它去設定 → 網路 & 網際網路 → 進階 → 私人 DNS 並在那輸入您的域名。",
"setup_dns_privacy_android_2": "<0>AdGuard for Android</0> 支援 <1>DNS-over-HTTPS</1> 和 <1>DNS-over-TLS</1>。",
"setup_dns_privacy_android_3": "<0>Intra</0> 對 Android 增加 <1>DNS-over-HTTPS</1> 支援。",
"setup_dns_privacy_ios_1": "<0>DNSCloak</0> 支援 <1>DNS-over-HTTPS</1>,但為了配置它以使用您自己的伺服器,您將需要為它產生一個 <2>DNS 戳記</2>。",
"setup_dns_privacy_ios_2": "<0>AdGuard for iOS</0> 支援 <1>DNS-over-HTTPS</1> 和 <1>DNS-over-TLS</1> 設置。",
"setup_dns_privacy_other_title": "其它的執行",
"setup_dns_privacy_other_1": "於任何的平台上AdGuard Home 它本身可以是安全的 DNS 用戶端。",
"setup_dns_privacy_other_2": "<0>dnsproxy</0> 支援所有已知安全的 DNS 協定。",
"setup_dns_privacy_other_3": "<0>dnscrypt-proxy</0> 支援 <1>DNS-over-HTTPS</1>。",
"setup_dns_privacy_other_4": "<0>Mozilla Firefox</0> 支援 <1>DNS-over-HTTPS</1>。",
"setup_dns_privacy_other_5": "在<0>這裡</0>和<1>這裡</1>,您將發現更多的執行。",
"setup_dns_notice": "為了使用 <1>DNS-over-HTTPS</1> 或 <1>DNS-over-TLS</1>,您需要在 AdGuard Home 設定裡<0>配置加密</0>。",
"rewrite_added": "對於 \"{{key}}\" 之 DNS 改寫被成功地加入",
"rewrite_deleted": "對於 \"{{key}}\" 之 DNS 改寫被成功地刪除",
"rewrite_add": "增加 DNS 改寫",
"rewrite_not_found": "無已發現之 DNS 改寫",
"rewrite_confirm_delete": "您確定您想要刪除對於 \"{{key}}\" 之 DNS 改寫嗎?",
"rewrite_desc": "允許輕易地配置自訂的 DNS 回應供特定的域名。",
"rewrite_applied": "已套用的改寫規則",
"dns_rewrites": "DNS 改寫",
"form_domain": "輸入網域",
"form_answer": "輸入 IP 位址或域名",
"form_error_domain_format": "無效的網域格式",
"form_error_answer_format": "無效的回應格式",
"configure": "配置",
"main_settings": "主設定",
"block_services": "封鎖特定的服務",
"blocked_services": "已封鎖的服務",
"blocked_services_desc": "允許立即封鎖熱門的網站和服務。",
"blocked_services_saved": "已封鎖的服務被成功地儲存",
"blocked_services_global": "使用全域已封鎖的服務",
"blocked_service": "已封鎖的服務",
"block_all": "封鎖全部",
"unblock_all": "解除封鎖全部"
}

View File

@@ -0,0 +1,45 @@
import { createAction } from 'redux-actions';
import Api from '../api/Api';
import { addErrorToast, addSuccessToast } from './index';
import { normalizeTextarea } from '../helpers/helpers';
const apiClient = new Api();
export const getAccessListRequest = createAction('GET_ACCESS_LIST_REQUEST');
export const getAccessListFailure = createAction('GET_ACCESS_LIST_FAILURE');
export const getAccessListSuccess = createAction('GET_ACCESS_LIST_SUCCESS');
export const getAccessList = () => async (dispatch) => {
dispatch(getAccessListRequest());
try {
const data = await apiClient.getAccessList();
dispatch(getAccessListSuccess(data));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(getAccessListFailure());
}
};
export const setAccessListRequest = createAction('SET_ACCESS_LIST_REQUEST');
export const setAccessListFailure = createAction('SET_ACCESS_LIST_FAILURE');
export const setAccessListSuccess = createAction('SET_ACCESS_LIST_SUCCESS');
export const setAccessList = config => async (dispatch) => {
dispatch(setAccessListRequest());
try {
const { allowed_clients, disallowed_clients, blocked_hosts } = config;
const values = {
allowed_clients: (allowed_clients && normalizeTextarea(allowed_clients)) || [],
disallowed_clients: (disallowed_clients && normalizeTextarea(disallowed_clients)) || [],
blocked_hosts: (blocked_hosts && normalizeTextarea(blocked_hosts)) || [],
};
await apiClient.setAccessList(values);
dispatch(setAccessListSuccess());
dispatch(addSuccessToast('access_settings_saved'));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(setAccessListFailure());
}
};

View File

@@ -0,0 +1,84 @@
import { createAction } from 'redux-actions';
import { t } from 'i18next';
import Api from '../api/Api';
import { addErrorToast, addSuccessToast, getClients } from './index';
import { CLIENT_ID } from '../helpers/constants';
const apiClient = new Api();
export const toggleClientModal = createAction('TOGGLE_CLIENT_MODAL');
export const addClientRequest = createAction('ADD_CLIENT_REQUEST');
export const addClientFailure = createAction('ADD_CLIENT_FAILURE');
export const addClientSuccess = createAction('ADD_CLIENT_SUCCESS');
export const addClient = config => async (dispatch) => {
dispatch(addClientRequest());
try {
let data;
if (config.identifier === CLIENT_ID.MAC) {
const { ip, identifier, ...values } = config;
data = { ...values };
} else {
const { mac, identifier, ...values } = config;
data = { ...values };
}
await apiClient.addClient(data);
dispatch(addClientSuccess());
dispatch(toggleClientModal());
dispatch(addSuccessToast(t('client_added', { key: config.name })));
dispatch(getClients());
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(addClientFailure());
}
};
export const deleteClientRequest = createAction('DELETE_CLIENT_REQUEST');
export const deleteClientFailure = createAction('DELETE_CLIENT_FAILURE');
export const deleteClientSuccess = createAction('DELETE_CLIENT_SUCCESS');
export const deleteClient = config => async (dispatch) => {
dispatch(deleteClientRequest());
try {
await apiClient.deleteClient(config);
dispatch(deleteClientSuccess());
dispatch(addSuccessToast(t('client_deleted', { key: config.name })));
dispatch(getClients());
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(deleteClientFailure());
}
};
export const updateClientRequest = createAction('UPDATE_CLIENT_REQUEST');
export const updateClientFailure = createAction('UPDATE_CLIENT_FAILURE');
export const updateClientSuccess = createAction('UPDATE_CLIENT_SUCCESS');
export const updateClient = (config, name) => async (dispatch) => {
dispatch(updateClientRequest());
try {
let data;
if (config.identifier === CLIENT_ID.MAC) {
const { ip, identifier, ...values } = config;
data = { name, data: { ...values } };
} else {
const { mac, identifier, ...values } = config;
data = { name, data: { ...values } };
}
await apiClient.updateClient(data);
dispatch(updateClientSuccess());
dispatch(toggleClientModal());
dispatch(addSuccessToast(t('client_updated', { key: name })));
dispatch(getClients());
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(updateClientFailure());
}
};

View File

@@ -2,15 +2,19 @@ import { createAction } from 'redux-actions';
import round from 'lodash/round';
import { t } from 'i18next';
import { showLoading, hideLoading } from 'react-redux-loading-bar';
import axios from 'axios';
import { normalizeHistory, normalizeFilteringStatus, normalizeLogs, normalizeTextarea } from '../helpers/helpers';
import { SETTINGS_NAMES } from '../helpers/constants';
import versionCompare from '../helpers/versionCompare';
import { normalizeHistory, normalizeFilteringStatus, normalizeLogs, normalizeTextarea, sortClients } from '../helpers/helpers';
import { SETTINGS_NAMES, CHECK_TIMEOUT } from '../helpers/constants';
import { getTlsStatus } from './encryption';
import Api from '../api/Api';
const apiClient = new Api();
export const addErrorToast = createAction('ADD_ERROR_TOAST');
export const addSuccessToast = createAction('ADD_SUCCESS_TOAST');
export const addNoticeToast = createAction('ADD_NOTICE_TOAST');
export const removeToast = createAction('REMOVE_TOAST');
export const toggleSettingStatus = createAction('SETTING_STATUS_TOGGLE');
@@ -143,17 +147,84 @@ export const getVersionRequest = createAction('GET_VERSION_REQUEST');
export const getVersionFailure = createAction('GET_VERSION_FAILURE');
export const getVersionSuccess = createAction('GET_VERSION_SUCCESS');
export const getVersion = () => async (dispatch) => {
export const getVersion = (recheck = false) => async (dispatch, getState) => {
dispatch(getVersionRequest());
try {
const newVersion = await apiClient.getGlobalVersion();
dispatch(getVersionSuccess(newVersion));
const data = await apiClient.getGlobalVersion({ recheck_now: recheck });
dispatch(getVersionSuccess(data));
if (recheck) {
const { dnsVersion } = getState().dashboard;
const currentVersion = dnsVersion === 'undefined' ? 0 : dnsVersion;
if (data && versionCompare(currentVersion, data.new_version) === -1) {
dispatch(addSuccessToast('updates_checked'));
} else {
dispatch(addSuccessToast('updates_version_equal'));
}
}
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(getVersionFailure());
}
};
export const getUpdateRequest = createAction('GET_UPDATE_REQUEST');
export const getUpdateFailure = createAction('GET_UPDATE_FAILURE');
export const getUpdateSuccess = createAction('GET_UPDATE_SUCCESS');
export const getUpdate = () => async (dispatch, getState) => {
const { dnsVersion } = getState().dashboard;
dispatch(getUpdateRequest());
try {
await apiClient.getUpdate();
const checkUpdate = async (attempts) => {
let count = attempts || 1;
let timeout;
if (count > 60) {
dispatch(addNoticeToast({ error: 'update_failed' }));
dispatch(getUpdateFailure());
return false;
}
const rmTimeout = t => t && clearTimeout(t);
const setRecursiveTimeout = (time, ...args) => setTimeout(
checkUpdate,
time,
...args,
);
axios.get('control/status')
.then((response) => {
rmTimeout(timeout);
if (response && response.status === 200) {
const responseVersion = response.data && response.data.version;
if (dnsVersion !== responseVersion) {
dispatch(getUpdateSuccess());
window.location.reload(true);
}
}
timeout = setRecursiveTimeout(CHECK_TIMEOUT, count += 1);
})
.catch(() => {
rmTimeout(timeout);
timeout = setRecursiveTimeout(CHECK_TIMEOUT, count += 1);
});
return false;
};
checkUpdate();
} catch (error) {
dispatch(addNoticeToast({ error: 'update_failed' }));
dispatch(getUpdateFailure());
}
};
export const getClientsRequest = createAction('GET_CLIENTS_REQUEST');
export const getClientsFailure = createAction('GET_CLIENTS_FAILURE');
export const getClientsSuccess = createAction('GET_CLIENTS_SUCCESS');
@@ -161,14 +232,41 @@ export const getClientsSuccess = createAction('GET_CLIENTS_SUCCESS');
export const getClients = () => async (dispatch) => {
dispatch(getClientsRequest());
try {
const clients = await apiClient.getGlobalClients();
dispatch(getClientsSuccess(clients));
const data = await apiClient.getClients();
const sortedClients = data.clients && sortClients(data.clients);
const sortedAutoClients = data.auto_clients && sortClients(data.auto_clients);
dispatch(getClientsSuccess({
clients: sortedClients || [],
autoClients: sortedAutoClients || [],
}));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(getClientsFailure());
}
};
export const getTopStatsRequest = createAction('GET_TOP_STATS_REQUEST');
export const getTopStatsFailure = createAction('GET_TOP_STATS_FAILURE');
export const getTopStatsSuccess = createAction('GET_TOP_STATS_SUCCESS');
export const getTopStats = () => async (dispatch, getState) => {
dispatch(getTopStatsRequest());
const timer = setInterval(async () => {
const state = getState();
if (state.dashboard.isCoreRunning) {
clearInterval(timer);
try {
const stats = await apiClient.getGlobalStatsTop();
dispatch(getTopStatsSuccess(stats));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(getTopStatsFailure(error));
}
}
}, 100);
};
export const dnsStatusRequest = createAction('DNS_STATUS_REQUEST');
export const dnsStatusFailure = createAction('DNS_STATUS_FAILURE');
export const dnsStatusSuccess = createAction('DNS_STATUS_SUCCESS');
@@ -179,7 +277,7 @@ export const getDnsStatus = () => async (dispatch) => {
const dnsStatus = await apiClient.getGlobalStatus();
dispatch(dnsStatusSuccess(dnsStatus));
dispatch(getVersion());
dispatch(getClients());
dispatch(getTlsStatus());
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(initSettingsFailure());
@@ -237,27 +335,6 @@ export const getStats = () => async (dispatch) => {
}
};
export const getTopStatsRequest = createAction('GET_TOP_STATS_REQUEST');
export const getTopStatsFailure = createAction('GET_TOP_STATS_FAILURE');
export const getTopStatsSuccess = createAction('GET_TOP_STATS_SUCCESS');
export const getTopStats = () => async (dispatch, getState) => {
dispatch(getTopStatsRequest());
const timer = setInterval(async () => {
const state = getState();
if (state.dashboard.isCoreRunning) {
clearInterval(timer);
try {
const stats = await apiClient.getGlobalStatsTop();
dispatch(getTopStatsSuccess(stats));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(getTopStatsFailure(error));
}
}
}, 100);
};
export const getLogsRequest = createAction('GET_LOGS_REQUEST');
export const getLogsFailure = createAction('GET_LOGS_FAILURE');
export const getLogsSuccess = createAction('GET_LOGS_SUCCESS');
@@ -603,41 +680,18 @@ export const setDhcpConfigRequest = createAction('SET_DHCP_CONFIG_REQUEST');
export const setDhcpConfigSuccess = createAction('SET_DHCP_CONFIG_SUCCESS');
export const setDhcpConfigFailure = createAction('SET_DHCP_CONFIG_FAILURE');
// TODO rewrite findActiveDhcp part
export const setDhcpConfig = values => async (dispatch, getState) => {
const { config } = getState().dhcp;
const updatedConfig = { ...config, ...values };
dispatch(setDhcpConfigRequest());
if (values.interface_name) {
dispatch(findActiveDhcpRequest());
try {
const activeDhcp = await apiClient.findActiveDhcp(values.interface_name);
dispatch(findActiveDhcpSuccess(activeDhcp));
if (!activeDhcp.found) {
try {
await apiClient.setDhcpConfig(updatedConfig);
dispatch(setDhcpConfigSuccess(updatedConfig));
dispatch(addSuccessToast('dhcp_config_saved'));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(setDhcpConfigFailure());
}
} else {
dispatch(addErrorToast({ error: 'dhcp_found' }));
}
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(findActiveDhcpFailure());
}
} else {
try {
await apiClient.setDhcpConfig(updatedConfig);
dispatch(setDhcpConfigSuccess(updatedConfig));
dispatch(addSuccessToast('dhcp_config_saved'));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(setDhcpConfigFailure());
}
dispatch(findActiveDhcp(values.interface_name));
try {
await apiClient.setDhcpConfig(updatedConfig);
dispatch(setDhcpConfigSuccess(updatedConfig));
dispatch(addSuccessToast('dhcp_config_saved'));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(setDhcpConfigFailure());
}
};
@@ -645,40 +699,60 @@ export const toggleDhcpRequest = createAction('TOGGLE_DHCP_REQUEST');
export const toggleDhcpFailure = createAction('TOGGLE_DHCP_FAILURE');
export const toggleDhcpSuccess = createAction('TOGGLE_DHCP_SUCCESS');
// TODO rewrite findActiveDhcp part
export const toggleDhcp = config => async (dispatch) => {
export const toggleDhcp = values => async (dispatch) => {
dispatch(toggleDhcpRequest());
let config = { ...values, enabled: false };
let successMessage = 'disabled_dhcp';
if (config.enabled) {
try {
await apiClient.setDhcpConfig({ ...config, enabled: false });
dispatch(toggleDhcpSuccess());
dispatch(addSuccessToast('disabled_dhcp'));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(toggleDhcpFailure());
}
} else {
dispatch(findActiveDhcpRequest());
try {
const activeDhcp = await apiClient.findActiveDhcp(config.interface_name);
dispatch(findActiveDhcpSuccess(activeDhcp));
if (!values.enabled) {
config = { ...values, enabled: true };
successMessage = 'enabled_dhcp';
dispatch(findActiveDhcp(values.interface_name));
}
if (!activeDhcp.found) {
try {
await apiClient.setDhcpConfig({ ...config, enabled: true });
dispatch(toggleDhcpSuccess());
dispatch(addSuccessToast('enabled_dhcp'));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(toggleDhcpFailure());
}
} else {
dispatch(addErrorToast({ error: 'dhcp_found' }));
}
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(findActiveDhcpFailure());
}
try {
await apiClient.setDhcpConfig(config);
dispatch(toggleDhcpSuccess());
dispatch(addSuccessToast(successMessage));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(toggleDhcpFailure());
}
};
export const toggleLeaseModal = createAction('TOGGLE_LEASE_MODAL');
export const addStaticLeaseRequest = createAction('ADD_STATIC_LEASE_REQUEST');
export const addStaticLeaseFailure = createAction('ADD_STATIC_LEASE_FAILURE');
export const addStaticLeaseSuccess = createAction('ADD_STATIC_LEASE_SUCCESS');
export const addStaticLease = config => async (dispatch) => {
dispatch(addStaticLeaseRequest());
try {
const name = config.hostname || config.ip;
await apiClient.addStaticLease(config);
dispatch(addStaticLeaseSuccess(config));
dispatch(addSuccessToast(t('dhcp_lease_added', { key: name })));
dispatch(toggleLeaseModal());
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(addStaticLeaseFailure());
}
};
export const removeStaticLeaseRequest = createAction('REMOVE_STATIC_LEASE_REQUEST');
export const removeStaticLeaseFailure = createAction('REMOVE_STATIC_LEASE_FAILURE');
export const removeStaticLeaseSuccess = createAction('REMOVE_STATIC_LEASE_SUCCESS');
export const removeStaticLease = config => async (dispatch) => {
dispatch(removeStaticLeaseRequest());
try {
const name = config.hostname || config.ip;
await apiClient.removeStaticLease(config);
dispatch(removeStaticLeaseSuccess(config));
dispatch(addSuccessToast(t('dhcp_lease_deleted', { key: name })));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(removeStaticLeaseFailure());
}
};

View File

@@ -0,0 +1,58 @@
import { createAction } from 'redux-actions';
import { t } from 'i18next';
import Api from '../api/Api';
import { addErrorToast, addSuccessToast } from './index';
const apiClient = new Api();
export const toggleRewritesModal = createAction('TOGGLE_REWRITES_MODAL');
export const getRewritesListRequest = createAction('GET_REWRITES_LIST_REQUEST');
export const getRewritesListFailure = createAction('GET_REWRITES_LIST_FAILURE');
export const getRewritesListSuccess = createAction('GET_REWRITES_LIST_SUCCESS');
export const getRewritesList = () => async (dispatch) => {
dispatch(getRewritesListRequest());
try {
const data = await apiClient.getRewritesList();
dispatch(getRewritesListSuccess(data));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(getRewritesListFailure());
}
};
export const addRewriteRequest = createAction('ADD_REWRITE_REQUEST');
export const addRewriteFailure = createAction('ADD_REWRITE_FAILURE');
export const addRewriteSuccess = createAction('ADD_REWRITE_SUCCESS');
export const addRewrite = config => async (dispatch) => {
dispatch(addRewriteRequest());
try {
await apiClient.addRewrite(config);
dispatch(addRewriteSuccess(config));
dispatch(toggleRewritesModal());
dispatch(getRewritesList());
dispatch(addSuccessToast(t('rewrite_added', { key: config.domain })));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(addRewriteFailure());
}
};
export const deleteRewriteRequest = createAction('DELETE_REWRITE_REQUEST');
export const deleteRewriteFailure = createAction('DELETE_REWRITE_FAILURE');
export const deleteRewriteSuccess = createAction('DELETE_REWRITE_SUCCESS');
export const deleteRewrite = config => async (dispatch) => {
dispatch(deleteRewriteRequest());
try {
await apiClient.deleteRewrite(config);
dispatch(deleteRewriteSuccess());
dispatch(getRewritesList());
dispatch(addSuccessToast(t('rewrite_deleted', { key: config.domain })));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(deleteRewriteFailure());
}
};

View File

@@ -0,0 +1,37 @@
import { createAction } from 'redux-actions';
import Api from '../api/Api';
import { addErrorToast, addSuccessToast } from './index';
const apiClient = new Api();
export const getBlockedServicesRequest = createAction('GET_BLOCKED_SERVICES_REQUEST');
export const getBlockedServicesFailure = createAction('GET_BLOCKED_SERVICES_FAILURE');
export const getBlockedServicesSuccess = createAction('GET_BLOCKED_SERVICES_SUCCESS');
export const getBlockedServices = () => async (dispatch) => {
dispatch(getBlockedServicesRequest());
try {
const data = await apiClient.getBlockedServices();
dispatch(getBlockedServicesSuccess(data));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(getBlockedServicesFailure());
}
};
export const setBlockedServicesRequest = createAction('SET_BLOCKED_SERVICES_REQUEST');
export const setBlockedServicesFailure = createAction('SET_BLOCKED_SERVICES_FAILURE');
export const setBlockedServicesSuccess = createAction('SET_BLOCKED_SERVICES_SUCCESS');
export const setBlockedServices = values => async (dispatch) => {
dispatch(setBlockedServicesRequest());
try {
await apiClient.setBlockedServices(values);
dispatch(setBlockedServicesSuccess());
dispatch(getBlockedServices());
dispatch(addSuccessToast('blocked_services_saved'));
} catch (error) {
dispatch(addErrorToast({ error }));
dispatch(setBlockedServicesFailure());
}
};

View File

@@ -36,10 +36,10 @@ export default class Api {
GLOBAL_QUERY_LOG_DISABLE = { path: 'querylog_disable', method: 'POST' };
GLOBAL_SET_UPSTREAM_DNS = { path: 'set_upstreams_config', method: 'POST' };
GLOBAL_TEST_UPSTREAM_DNS = { path: 'test_upstream_dns', method: 'POST' };
GLOBAL_VERSION = { path: 'version.json', method: 'GET' };
GLOBAL_VERSION = { path: 'version.json', method: 'POST' };
GLOBAL_ENABLE_PROTECTION = { path: 'enable_protection', method: 'POST' };
GLOBAL_DISABLE_PROTECTION = { path: 'disable_protection', method: 'POST' };
GLOBAL_CLIENTS = { path: 'clients', method: 'GET' }
GLOBAL_UPDATE = { path: 'update', method: 'POST' };
restartGlobalFiltering() {
const { path, method } = this.GLOBAL_RESTART;
@@ -125,9 +125,13 @@ export default class Api {
return this.makeRequest(path, method, config);
}
getGlobalVersion() {
getGlobalVersion(data) {
const { path, method } = this.GLOBAL_VERSION;
return this.makeRequest(path, method);
const config = {
data,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, config);
}
enableGlobalProtection() {
@@ -140,8 +144,8 @@ export default class Api {
return this.makeRequest(path, method);
}
getGlobalClients() {
const { path, method } = this.GLOBAL_CLIENTS;
getUpdate() {
const { path, method } = this.GLOBAL_UPDATE;
return this.makeRequest(path, method);
}
@@ -188,15 +192,14 @@ export default class Api {
return this.makeRequest(path, method, config);
}
removeFilter(url) {
removeFilter(config) {
const { path, method } = this.FILTERING_REMOVE_FILTER;
const parameter = 'url';
const requestBody = `${parameter}=${url}`;
const config = {
data: requestBody,
header: { 'Content-Type': 'text/plain' },
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, config);
return this.makeRequest(path, method, parameters);
}
setRules(rules) {
@@ -318,6 +321,8 @@ export default class Api {
DHCP_SET_CONFIG = { path: 'dhcp/set_config', method: 'POST' };
DHCP_FIND_ACTIVE = { path: 'dhcp/find_active_dhcp', method: 'POST' };
DHCP_INTERFACES = { path: 'dhcp/interfaces', method: 'GET' };
DHCP_ADD_STATIC_LEASE = { path: 'dhcp/add_static_lease', method: 'POST' };
DHCP_REMOVE_STATIC_LEASE = { path: 'dhcp/remove_static_lease', method: 'POST' };
getDhcpStatus() {
const { path, method } = this.DHCP_STATUS;
@@ -347,6 +352,24 @@ export default class Api {
return this.makeRequest(path, method, parameters);
}
addStaticLease(config) {
const { path, method } = this.DHCP_ADD_STATIC_LEASE;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
removeStaticLease(config) {
const { path, method } = this.DHCP_REMOVE_STATIC_LEASE;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
// Installation
INSTALL_GET_ADDRESSES = { path: 'install/get_addresses', method: 'GET' };
INSTALL_CONFIGURE = { path: 'install/configure', method: 'POST' };
@@ -402,4 +425,106 @@ export default class Api {
};
return this.makeRequest(path, method, parameters);
}
// Per-client settings
GET_CLIENTS = { path: 'clients', method: 'GET' };
ADD_CLIENT = { path: 'clients/add', method: 'POST' };
DELETE_CLIENT = { path: 'clients/delete', method: 'POST' };
UPDATE_CLIENT = { path: 'clients/update', method: 'POST' };
getClients() {
const { path, method } = this.GET_CLIENTS;
return this.makeRequest(path, method);
}
addClient(config) {
const { path, method } = this.ADD_CLIENT;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
deleteClient(config) {
const { path, method } = this.DELETE_CLIENT;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
updateClient(config) {
const { path, method } = this.UPDATE_CLIENT;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
// DNS access settings
ACCESS_LIST = { path: 'access/list', method: 'GET' };
ACCESS_SET = { path: 'access/set', method: 'POST' };
getAccessList() {
const { path, method } = this.ACCESS_LIST;
return this.makeRequest(path, method);
}
setAccessList(config) {
const { path, method } = this.ACCESS_SET;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
// DNS rewrites
REWRITES_LIST = { path: 'rewrite/list', method: 'GET' };
REWRITE_ADD = { path: 'rewrite/add', method: 'POST' };
REWRITE_DELETE = { path: 'rewrite/delete', method: 'POST' };
getRewritesList() {
const { path, method } = this.REWRITES_LIST;
return this.makeRequest(path, method);
}
addRewrite(config) {
const { path, method } = this.REWRITE_ADD;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
deleteRewrite(config) {
const { path, method } = this.REWRITE_DELETE;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
// Blocked services
BLOCKED_SERVICES_LIST = { path: 'blocked_services/list', method: 'GET' };
BLOCKED_SERVICES_SET = { path: 'blocked_services/set', method: 'POST' };
getBlockedServices() {
const { path, method } = this.BLOCKED_SERVICES_LIST;
return this.makeRequest(path, method);
}
setBlockedServices(config) {
const { path, method } = this.BLOCKED_SERVICES_SET;
const parameters = {
data: config,
headers: { 'Content-Type': 'application/json' },
};
return this.makeRequest(path, method, parameters);
}
}

View File

@@ -13,13 +13,21 @@ import Header from '../../containers/Header';
import Dashboard from '../../containers/Dashboard';
import Settings from '../../containers/Settings';
import Filters from '../../containers/Filters';
import Dns from '../../containers/Dns';
import Encryption from '../../containers/Encryption';
import Dhcp from '../../containers/Dhcp';
import Clients from '../../containers/Clients';
import Logs from '../../containers/Logs';
import SetupGuide from '../../containers/SetupGuide';
import Toasts from '../Toasts';
import Footer from '../ui/Footer';
import Status from '../ui/Status';
import UpdateTopline from '../ui/UpdateTopline';
import UpdateOverlay from '../ui/UpdateOverlay';
import EncryptionTopline from '../ui/EncryptionTopline';
import Icons from '../ui/Icons';
import i18n from '../../i18n';
class App extends Component {
@@ -37,6 +45,10 @@ class App extends Component {
this.props.enableDns();
};
handleUpdate = () => {
this.props.getUpdate();
};
setLanguage = () => {
const { processing, language } = this.props.dashboard;
@@ -49,49 +61,57 @@ class App extends Component {
i18n.on('languageChanged', (lang) => {
this.props.changeLanguage(lang);
});
}
};
render() {
const { dashboard, encryption } = this.props;
const updateAvailable =
!dashboard.processingVersions &&
dashboard.isCoreRunning &&
dashboard.isUpdateAvailable;
const updateAvailable = dashboard.isCoreRunning && dashboard.isUpdateAvailable;
return (
<HashRouter hashType='noslash'>
<HashRouter hashType="noslash">
<Fragment>
{updateAvailable &&
<UpdateTopline
url={dashboard.announcementUrl}
version={dashboard.version}
/>
}
{!encryption.processing &&
{updateAvailable && (
<Fragment>
<UpdateTopline
url={dashboard.announcementUrl}
version={dashboard.newVersion}
canAutoUpdate={dashboard.canAutoUpdate}
getUpdate={this.handleUpdate}
processingUpdate={dashboard.processingUpdate}
/>
<UpdateOverlay processingUpdate={dashboard.processingUpdate} />
</Fragment>
)}
{!encryption.processing && (
<EncryptionTopline notAfter={encryption.not_after} />
}
)}
<LoadingBar className="loading-bar" updateTime={1000} />
<Route component={Header} />
<div className="container container--wrap">
{!dashboard.processing && !dashboard.isCoreRunning &&
{!dashboard.processing && !dashboard.isCoreRunning && (
<div className="row row-cards">
<div className="col-lg-12">
<Status handleStatusChange={this.handleStatusChange} />
</div>
</div>
}
{!dashboard.processing && dashboard.isCoreRunning &&
)}
{!dashboard.processing && dashboard.isCoreRunning && (
<Fragment>
<Route path="/" exact component={Dashboard} />
<Route path="/settings" component={Settings} />
<Route path="/dns" component={Dns} />
<Route path="/encryption" component={Encryption} />
<Route path="/dhcp" component={Dhcp} />
<Route path="/clients" component={Clients} />
<Route path="/filters" component={Filters} />
<Route path="/logs" component={Logs} />
<Route path="/guide" component={SetupGuide} />
</Fragment>
}
)}
</div>
<Footer />
<Toasts />
<Icons />
</Fragment>
</HashRouter>
);
@@ -100,6 +120,7 @@ class App extends Component {
App.propTypes = {
getDnsStatus: PropTypes.func,
getUpdate: PropTypes.func,
enableDns: PropTypes.func,
dashboard: PropTypes.object,
isCoreRunning: PropTypes.bool,

View File

@@ -24,7 +24,8 @@ class Clients extends Component {
Header: 'IP',
accessor: 'ip',
Cell: ({ value }) => {
const clientName = getClientName(this.props.clients, value);
const clientName = getClientName(this.props.clients, value)
|| getClientName(this.props.autoClients, value);
let client;
if (clientName) {
@@ -79,6 +80,7 @@ Clients.propTypes = {
dnsQueries: PropTypes.number.isRequired,
refreshButton: PropTypes.node.isRequired,
clients: PropTypes.array.isRequired,
autoClients: PropTypes.array.isRequired,
t: PropTypes.func,
};

View File

@@ -21,6 +21,7 @@ class Dashboard extends Component {
this.props.getStats();
this.props.getStatsHistory();
this.props.getTopStats();
this.props.getClients();
}
getToggleFilteringButton = () => {
@@ -49,8 +50,26 @@ class Dashboard extends Component {
dashboard.processingClients ||
dashboard.processingTopStats;
const refreshFullButton = <button type="button" className="btn btn-outline-primary btn-sm" onClick={() => this.getAllStats()}><Trans>refresh_statics</Trans></button>;
const refreshButton = <button type="button" className="btn btn-outline-primary btn-sm card-refresh" onClick={() => this.getAllStats()} />;
const refreshFullButton = (
<button
type="button"
className="btn btn-outline-primary btn-sm"
onClick={() => this.getAllStats()}
>
<Trans>refresh_statics</Trans>
</button>
);
const refreshButton = (
<button
type="button"
className="btn btn-icon btn-outline-primary btn-sm"
onClick={() => this.getAllStats()}
>
<svg className="icons">
<use xlinkHref="#refresh" />
</svg>
</button>
);
return (
<Fragment>
@@ -96,6 +115,7 @@ class Dashboard extends Component {
refreshButton={refreshButton}
topClients={dashboard.topStats.top_clients}
clients={dashboard.clients}
autoClients={dashboard.autoClients}
/>
</div>
<div className="col-lg-6">
@@ -131,6 +151,7 @@ Dashboard.propTypes = {
isCoreRunning: PropTypes.bool,
getFiltering: PropTypes.func,
toggleProtection: PropTypes.func,
getClients: PropTypes.func,
processingProtection: PropTypes.bool,
t: PropTypes.func,
};

View File

@@ -1,13 +0,0 @@
.remove-icon {
position: relative;
top: 2px;
display: inline-block;
width: 20px;
height: 18px;
opacity: 0.6;
}
.remove-icon:hover {
cursor: pointer;
opacity: 1;
}

View File

@@ -4,7 +4,7 @@ import ReactModal from 'react-modal';
import classnames from 'classnames';
import { Trans, withNamespaces } from 'react-i18next';
import { R_URL_REQUIRES_PROTOCOL } from '../../helpers/constants';
import './Modal.css';
import '../ui/Modal.css';
ReactModal.setAppElement('#root');
@@ -17,10 +17,7 @@ const initialState = {
class Modal extends Component {
state = initialState;
// eslint-disable-next-line
isUrlValid = url => {
return R_URL_REQUIRES_PROTOCOL.test(url);
};
isUrlValid = url => R_URL_REQUIRES_PROTOCOL.test(url);
handleUrlChange = async (e) => {
const { value: url } = e.currentTarget;

View File

@@ -17,12 +17,13 @@ class UserRules extends Component {
render() {
const { t } = this.props;
return (
<Card
title={ t('custom_filter_rules') }
subtitle={ t('custom_filter_rules_hint') }
>
<Card title={t('custom_filter_rules')} subtitle={t('custom_filter_rules_hint')}>
<form onSubmit={this.handleSubmit}>
<textarea className="form-control form-control--textarea-large" value={this.props.userRules} onChange={this.handleChange} />
<textarea
className="form-control form-control--textarea-large"
value={this.props.userRules}
onChange={this.handleChange}
/>
<div className="card-actions">
<button
className="btn btn-success btn-standard"
@@ -33,27 +34,42 @@ class UserRules extends Component {
</button>
</div>
</form>
<hr/>
<hr />
<div className="list leading-loose">
<Trans>examples_title</Trans>:
<ol className="leading-loose">
<li>
<code>||example.org^</code> - { t('example_meaning_filter_block') }
<code>||example.org^</code> {t('example_meaning_filter_block')}
</li>
<li>
<code> @@||example.org^</code> - { t('example_meaning_filter_whitelist') }
<code> @@||example.org^</code> {t('example_meaning_filter_whitelist')}
</li>
<li>
<code>127.0.0.1 example.org</code> - { t('example_meaning_host_block') }
<code>127.0.0.1 example.org</code> {t('example_meaning_host_block')}
</li>
<li>
<code>{ t('example_comment') }</code> - { t('example_comment_meaning') }
<code>{t('example_comment')}</code> {t('example_comment_meaning')}
</li>
<li>
<code>{ t('example_comment_hash') }</code> - { t('example_comment_meaning') }
<code>{t('example_comment_hash')}</code> &nbsp;
{t('example_comment_meaning')}
</li>
<li>
<code>/REGEX/</code> - { t('example_regex_meaning') }
<code>/REGEX/</code> &nbsp;
<Trans
components={[
<a
href="https://kb.adguard.com/general/dns-filtering-syntax"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
]}
>
example_regex_meaning
</Trans>
</li>
</ol>
</div>

View File

@@ -2,11 +2,10 @@ import React, { Component } from 'react';
import ReactTable from 'react-table';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import Modal from '../ui/Modal';
import Modal from './Modal';
import PageTitle from '../ui/PageTitle';
import Card from '../ui/Card';
import UserRules from './UserRules';
import './Filters.css';
class Filters extends Component {
componentDidMount() {
@@ -33,6 +32,13 @@ class Filters extends Component {
);
};
handleDelete = (url) => {
// eslint-disable-next-line no-alert
if (window.confirm(this.props.t('filter_confirm_delete'))) {
this.props.removeFilter({ url });
}
}
columns = [{
Header: <Trans>enabled_table_header</Trans>,
accessor: 'enabled',
@@ -59,7 +65,18 @@ class Filters extends Component {
}, {
Header: <Trans>actions_table_header</Trans>,
accessor: 'url',
Cell: ({ value }) => (<span title={ this.props.t('delete_table_action') } className='remove-icon fe fe-trash-2' onClick={() => this.props.removeFilter(value)}/>),
Cell: ({ value }) => (
<button
type="button"
className="btn btn-icon btn-outline-secondary btn-sm"
onClick={() => this.handleDelete(value)}
title={this.props.t('delete_table_action')}
>
<svg className="icons">
<use xlinkHref="#delete" />
</svg>
</button>
),
className: 'text-center',
width: 80,
sortable: false,

View File

@@ -16,11 +16,13 @@
stroke: #9aa0ac;
}
.nav-tabs .nav-link.active .nav-icon {
.nav-tabs .nav-link.active .nav-icon,
.nav-tabs .nav-item.show .nav-icon {
stroke: #66b574;
}
.nav-tabs .nav-link.active:hover .nav-icon {
.nav-tabs .nav-link.active:hover .nav-icon,
.nav-tabs .nav-item.show:hover .nav-icon {
stroke: #58a273;
}
@@ -73,7 +75,18 @@
}
.nav-version__value {
max-width: 110px;
font-weight: 600;
text-overflow: ellipsis;
white-space: nowrap;
overflow: hidden;
}
@media screen and (min-width: 992px) {
.nav-version__value {
max-width: 100%;
overflow: visible;
}
}
.nav-version__link {
@@ -83,10 +96,22 @@
cursor: pointer;
}
.nav-version__text {
display: flex;
align-items: center;
justify-content: flex-end;
}
.header-brand-img {
height: 32px;
}
.nav-tabs .nav-item.show .nav-link {
color: #66b574;
background-color: #fff;
border-bottom-color: #66b574;
}
@media screen and (min-width: 992px) {
.header {
padding: 0;

View File

@@ -5,6 +5,9 @@ import enhanceWithClickOutside from 'react-click-outside';
import classnames from 'classnames';
import { Trans, withNamespaces } from 'react-i18next';
import { SETTINGS_URLS } from '../../helpers/constants';
import Dropdown from '../ui/Dropdown';
class Menu extends Component {
handleClickOutside = () => {
this.props.closeMenu();
@@ -14,49 +17,86 @@ class Menu extends Component {
this.props.toggleMenuOpen();
};
getActiveClassForSettings = () => {
const { pathname } = this.props.location;
const isSettingsPage = SETTINGS_URLS.some(item => item === pathname);
return isSettingsPage ? 'active' : '';
};
render() {
const menuClass = classnames({
'col-lg-6 mobile-menu': true,
'mobile-menu--active': this.props.isMenuOpen,
});
const dropdownControlClass = `nav-link ${this.getActiveClassForSettings()}`;
return (
<Fragment>
<div className={menuClass}>
<ul className="nav nav-tabs border-0 flex-column flex-lg-row flex-nowrap">
<li className="nav-item border-bottom d-lg-none" onClick={this.toggleMenu}>
<div className="nav-link nav-link--back">
<svg className="nav-icon" fill="none" height="24" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2" viewBox="0 0 24 24" width="24" xmlns="http://www.w3.org/2000/svg"><path d="m19 12h-14"/><path d="m12 19-7-7 7-7"/></svg>
<svg className="nav-icon">
<use xlinkHref="#back" />
</svg>
<Trans>back</Trans>
</div>
</li>
<li className="nav-item">
<NavLink to="/" exact={true} className="nav-link">
<svg className="nav-icon" fill="none" height="24" stroke="#9aa0ac" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2" viewBox="0 0 24 24" width="24" xmlns="http://www.w3.org/2000/svg"><path d="m3 9 9-7 9 7v11a2 2 0 0 1 -2 2h-14a2 2 0 0 1 -2-2z"/><path d="m9 22v-10h6v10"/></svg>
<svg className="nav-icon">
<use xlinkHref="#dashboard" />
</svg>
<Trans>dashboard</Trans>
</NavLink>
</li>
<li className="nav-item">
<NavLink to="/settings" className="nav-link">
<svg className="nav-icon" fill="none" height="24" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2" viewBox="0 0 24 24" width="24" xmlns="http://www.w3.org/2000/svg"><circle cx="12" cy="12" r="3"/><path d="m19.4 15a1.65 1.65 0 0 0 .33 1.82l.06.06a2 2 0 0 1 0 2.83 2 2 0 0 1 -2.83 0l-.06-.06a1.65 1.65 0 0 0 -1.82-.33 1.65 1.65 0 0 0 -1 1.51v.17a2 2 0 0 1 -2 2 2 2 0 0 1 -2-2v-.09a1.65 1.65 0 0 0 -1.08-1.51 1.65 1.65 0 0 0 -1.82.33l-.06.06a2 2 0 0 1 -2.83 0 2 2 0 0 1 0-2.83l.06-.06a1.65 1.65 0 0 0 .33-1.82 1.65 1.65 0 0 0 -1.51-1h-.17a2 2 0 0 1 -2-2 2 2 0 0 1 2-2h.09a1.65 1.65 0 0 0 1.51-1.08 1.65 1.65 0 0 0 -.33-1.82l-.06-.06a2 2 0 0 1 0-2.83 2 2 0 0 1 2.83 0l.06.06a1.65 1.65 0 0 0 1.82.33h.08a1.65 1.65 0 0 0 1-1.51v-.17a2 2 0 0 1 2-2 2 2 0 0 1 2 2v.09a1.65 1.65 0 0 0 1 1.51 1.65 1.65 0 0 0 1.82-.33l.06-.06a2 2 0 0 1 2.83 0 2 2 0 0 1 0 2.83l-.06.06a1.65 1.65 0 0 0 -.33 1.82v.08a1.65 1.65 0 0 0 1.51 1h.17a2 2 0 0 1 2 2 2 2 0 0 1 -2 2h-.09a1.65 1.65 0 0 0 -1.51 1z"/></svg>
<Trans>settings</Trans>
</NavLink>
</li>
<Dropdown
label={this.props.t('settings')}
baseClassName="dropdown nav-item"
controlClassName={dropdownControlClass}
icon="settings"
>
<Fragment>
<NavLink to="/settings" className="dropdown-item">
<Trans>general_settings</Trans>
</NavLink>
<NavLink to="/dns" className="dropdown-item">
<Trans>dns_settings</Trans>
</NavLink>
<NavLink to="/encryption" className="dropdown-item">
<Trans>encryption_settings</Trans>
</NavLink>
<NavLink to="/clients" className="dropdown-item">
<Trans>client_settings</Trans>
</NavLink>
<NavLink to="/dhcp" className="dropdown-item">
<Trans>dhcp_settings</Trans>
</NavLink>
</Fragment>
</Dropdown>
<li className="nav-item">
<NavLink to="/filters" className="nav-link">
<svg className="nav-icon" fill="none" height="24" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2" viewBox="0 0 24 24" width="24" xmlns="http://www.w3.org/2000/svg"><path d="m22 3h-20l8 9.46v6.54l4 2v-8.54z"/></svg>
<svg className="nav-icon">
<use xlinkHref="#filters" />
</svg>
<Trans>filters</Trans>
</NavLink>
</li>
<li className="nav-item">
<NavLink to="/logs" className="nav-link">
<svg className="nav-icon" fill="none" height="24" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2" viewBox="0 0 24 24" width="24" xmlns="http://www.w3.org/2000/svg"><path d="m14 2h-8a2 2 0 0 0 -2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2v-12z"/><path d="m14 2v6h6"/><path d="m16 13h-8"/><path d="m16 17h-8"/><path d="m10 9h-1-1"/></svg>
<svg className="nav-icon">
<use xlinkHref="#log" />
</svg>
<Trans>query_log</Trans>
</NavLink>
</li>
<li className="nav-item">
<NavLink to="/guide" href="/guide" className="nav-link">
<svg className="nav-icon" xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="#66b574" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><circle cx="12" cy="12" r="10"></circle><path d="M9.09 9a3 3 0 0 1 5.83 1c0 2-3 3-3 3"></path><line x1="12" y1="17" x2="12" y2="17"></line></svg>
<NavLink to="/guide" className="nav-link">
<svg className="nav-icon">
<use xlinkHref="#setup" />
</svg>
<Trans>setup_guide</Trans>
</NavLink>
</li>
@@ -71,6 +111,8 @@ Menu.propTypes = {
isMenuOpen: PropTypes.bool,
closeMenu: PropTypes.func,
toggleMenuOpen: PropTypes.func,
location: PropTypes.object,
t: PropTypes.func,
};
export default withNamespaces()(enhanceWithClickOutside(Menu));

View File

@@ -2,14 +2,26 @@ import React from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import { getDnsAddress } from '../../helpers/helpers';
const Version = (props) => {
const {
dnsVersion, dnsAddresses, processingVersion, t,
} = props;
function Version(props) {
const { dnsVersion, dnsAddresses, dnsPort } = props;
return (
<div className="nav-version">
<div className="nav-version__text">
<Trans>version</Trans>: <span className="nav-version__value">{dnsVersion}</span>
<Trans>version</Trans>:&nbsp;<span className="nav-version__value" title={dnsVersion}>{dnsVersion}</span>
<button
type="button"
className="btn btn-icon btn-icon-sm btn-outline-primary btn-sm ml-2"
onClick={() => props.getVersion(true)}
disabled={processingVersion}
title={t('check_updates_now')}
>
<svg className="icons">
<use xlinkHref="#refresh" />
</svg>
</button>
</div>
<div className="nav-version__link">
<div className="popover__trigger popover__trigger--address">
@@ -17,20 +29,21 @@ function Version(props) {
</div>
<div className="popover__body popover__body--address">
<div className="popover__list">
{dnsAddresses
.map(ip => <li key={ip}>{getDnsAddress(ip, dnsPort)}</li>)
}
{dnsAddresses.map(ip => <li key={ip}>{ip}</li>)}
</div>
</div>
</div>
</div>
);
}
};
Version.propTypes = {
dnsVersion: PropTypes.string.isRequired,
dnsAddresses: PropTypes.array.isRequired,
dnsPort: PropTypes.number.isRequired,
getVersion: PropTypes.func.isRequired,
processingVersion: PropTypes.bool.isRequired,
t: PropTypes.func.isRequired,
};
export default withNamespaces()(Version);

View File

@@ -23,7 +23,7 @@ class Header extends Component {
};
render() {
const { dashboard } = this.props;
const { dashboard, getVersion, location } = this.props;
const { isMenuOpen } = this.state;
const badgeClass = classnames({
'badge dns-status': true,
@@ -51,7 +51,7 @@ class Header extends Component {
</div>
</div>
<Menu
location={this.props.location}
location={location}
isMenuOpen={isMenuOpen}
toggleMenuOpen={this.toggleMenuOpen}
closeMenu={this.closeMenu}
@@ -59,7 +59,8 @@ class Header extends Component {
{!dashboard.processing &&
<div className="col col-sm-6 col-lg-3">
<Version
{ ...this.props.dashboard }
{ ...dashboard }
getVersion={getVersion}
/>
</div>
}
@@ -71,8 +72,9 @@ class Header extends Component {
}
Header.propTypes = {
dashboard: PropTypes.object,
location: PropTypes.object,
dashboard: PropTypes.object.isRequired,
location: PropTypes.object.isRequired,
getVersion: PropTypes.func.isRequired,
};
export default withNamespaces()(Header);

View File

@@ -5,10 +5,25 @@
min-height: 26px;
}
.logs__row--center {
justify-content: center;
}
.logs__row--overflow {
overflow: hidden;
}
.logs__row--column {
flex-direction: column;
align-items: flex-start;
overflow: hidden;
}
.logs__row--icons {
max-width: 180px;
flex-flow: row wrap;
}
.logs__row .list-unstyled {
margin-bottom: 0;
overflow: hidden;
@@ -16,6 +31,7 @@
.logs__text,
.logs__row .list-unstyled li {
padding: 0 1px;
text-overflow: ellipsis;
white-space: nowrap;
overflow: hidden;

View File

@@ -5,8 +5,10 @@ import { saveAs } from 'file-saver/FileSaver';
import escapeRegExp from 'lodash/escapeRegExp';
import endsWith from 'lodash/endsWith';
import { Trans, withNamespaces } from 'react-i18next';
import { HashLink as Link } from 'react-router-hash-link';
import { formatTime, getClientName } from '../../helpers/helpers';
import { SERVICES } from '../../helpers/constants';
import { getTrackerData } from '../../helpers/trackers/trackers';
import PageTitle from '../ui/PageTitle';
import Card from '../ui/Card';
@@ -21,6 +23,7 @@ class Logs extends Component {
componentDidMount() {
this.getLogs();
this.props.getFilteringStatus();
this.props.getClients();
}
componentDidUpdate(prevProps) {
@@ -37,12 +40,8 @@ class Logs extends Component {
}
}
renderTooltip(isFiltered, rule, filter) {
if (rule) {
return (isFiltered && <PopoverFiltered rule={rule} filter={filter}/>);
}
return '';
}
renderTooltip = (isFiltered, rule, filter, service) =>
isFiltered && <PopoverFiltered rule={rule} filter={filter} service={service} />;
toggleBlocking = (type, domain) => {
const { userRules } = this.props.filtering;
@@ -124,6 +123,7 @@ class Logs extends Component {
const rule = row && row.original && row.original.rule;
const { filterId } = row.original;
const { filters } = this.props.filtering;
const isRewrite = reason && reason === 'Rewrite';
let filterName = '';
if (reason === 'FilteredBlackList' || reason === 'NotFilteredWhiteList') {
@@ -143,6 +143,21 @@ class Logs extends Component {
}
}
if (reason === 'FilteredBlockedService') {
const getService = SERVICES
.find(service => service.id === row.original.serviceName);
const serviceName = getService && getService.name;
return (
<div className="logs__row">
<span className="logs__text" title={parsedFilteredReason}>
{parsedFilteredReason}
</span>
{this.renderTooltip(isFiltered, '', '', serviceName)}
</div>
);
}
if (isFiltered) {
return (
<div className="logs__row">
@@ -160,14 +175,16 @@ class Logs extends Component {
const isRenderTooltip = reason === 'NotFilteredWhiteList';
return (
<div className="logs__row">
<div className={`logs__row ${isRewrite && 'logs__row--column'}`}>
{isRewrite && <strong><Trans>rewrite_applied</Trans></strong>}
<ul className="list-unstyled">{liNodes}</ul>
{this.renderTooltip(isRenderTooltip, rule, filterName)}
</div>
);
}
return (
<div className="logs__row">
<div className={`logs__row ${isRewrite && 'logs__row--column'}`}>
{isRewrite && <strong><Trans>rewrite_applied</Trans></strong>}
<span><Trans>empty_response_status</Trans></span>
{this.renderTooltip(isFiltered, rule, filterName)}
</div>
@@ -196,7 +213,9 @@ class Logs extends Component {
Cell: (row) => {
const { reason } = row.original;
const isFiltered = row ? reason.indexOf('Filtered') === 0 : false;
const clientName = getClientName(dashboard.clients, row.value);
const isRewrite = reason && reason === 'Rewrite';
const clientName = getClientName(dashboard.clients, row.value)
|| getClientName(dashboard.autoClients, row.value);
let client;
if (clientName) {
@@ -205,6 +224,21 @@ class Logs extends Component {
client = row.value;
}
if (isRewrite) {
return (
<Fragment>
<div className="logs__row">
{client}
</div>
<div className="logs__action">
<Link to="/dns#rewrites" className="btn btn-sm btn-outline-primary">
<Trans>configure</Trans>
</Link>
</div>
</Fragment>
);
}
return (
<Fragment>
<div className="logs__row">
@@ -259,6 +293,10 @@ class Logs extends Component {
return {
className: 'green',
};
} else if (rowInfo.original.reason === 'Rewrite') {
return {
className: 'blue',
};
}
return {
@@ -355,6 +393,7 @@ Logs.propTypes = {
processingRules: PropTypes.bool,
logStatusProcessing: PropTypes.bool,
t: PropTypes.func,
getClients: PropTypes.func.isRequired,
};
export default withNamespaces()(Logs);

View File

@@ -0,0 +1,118 @@
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import { withNamespaces } from 'react-i18next';
import ReactTable from 'react-table';
import { CLIENT_ID } from '../../../helpers/constants';
import Card from '../../ui/Card';
class AutoClients extends Component {
getClient = (name, clients) => {
const client = clients.find(item => name === item.name);
if (client) {
const identifier = client.mac ? CLIENT_ID.MAC : CLIENT_ID.IP;
return {
identifier,
use_global_settings: true,
...client,
};
}
return {
identifier: 'ip',
use_global_settings: true,
};
};
getStats = (ip, stats) => {
if (stats && stats.top_clients) {
return stats.top_clients[ip];
}
return '';
};
cellWrap = ({ value }) => (
<div className="logs__row logs__row--overflow">
<span className="logs__text" title={value}>
{value}
</span>
</div>
);
columns = [
{
Header: this.props.t('table_client'),
accessor: 'ip',
Cell: this.cellWrap,
},
{
Header: this.props.t('table_name'),
accessor: 'name',
Cell: this.cellWrap,
},
{
Header: this.props.t('source_label'),
accessor: 'source',
Cell: this.cellWrap,
},
{
Header: this.props.t('table_statistics'),
accessor: 'statistics',
Cell: (row) => {
const clientIP = row.original.ip;
const clientStats = clientIP && this.getStats(clientIP, this.props.topStats);
if (clientStats) {
return (
<div className="logs__row">
<div className="logs__text" title={clientStats}>
{clientStats}
</div>
</div>
);
}
return '';
},
},
];
render() {
const { t, autoClients } = this.props;
return (
<Card
title={t('auto_clients_title')}
subtitle={t('auto_clients_desc')}
bodyType="card-body box-body--settings"
>
<ReactTable
data={autoClients || []}
columns={this.columns}
className="-striped -highlight card-table-overflow"
showPagination={true}
defaultPageSize={10}
minRows={5}
previousText={t('previous_btn')}
nextText={t('next_btn')}
loadingText={t('loading_table_status')}
pageText={t('page_table_footer_text')}
ofText={t('of_table_footer_text')}
rowsText={t('rows_table_footer_text')}
noDataText={t('clients_not_found')}
/>
</Card>
);
}
}
AutoClients.propTypes = {
t: PropTypes.func.isRequired,
autoClients: PropTypes.array.isRequired,
topStats: PropTypes.object.isRequired,
};
export default withNamespaces()(AutoClients);

View File

@@ -0,0 +1,292 @@
import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import ReactTable from 'react-table';
import { MODAL_TYPE, CLIENT_ID } from '../../../helpers/constants';
import Card from '../../ui/Card';
import Modal from './Modal';
class ClientsTable extends Component {
handleFormAdd = (values) => {
this.props.addClient(values);
};
handleFormUpdate = (values, name) => {
this.props.updateClient(values, name);
};
handleSubmit = (values) => {
let config = values;
if (values && values.blocked_services) {
const blocked_services = Object
.keys(values.blocked_services)
.filter(service => values.blocked_services[service]);
config = { ...values, blocked_services };
}
if (this.props.modalType === MODAL_TYPE.EDIT) {
this.handleFormUpdate(config, this.props.modalClientName);
} else {
this.handleFormAdd(config);
}
};
cellWrap = ({ value }) => (
<div className="logs__row logs__row--overflow">
<span className="logs__text" title={value}>
{value}
</span>
</div>
);
getClient = (name, clients) => {
const client = clients.find(item => name === item.name);
if (client) {
const identifier = client.mac ? CLIENT_ID.MAC : CLIENT_ID.IP;
return {
identifier,
use_global_settings: true,
use_global_blocked_services: true,
...client,
};
}
return {
identifier: CLIENT_ID.IP,
use_global_settings: true,
use_global_blocked_services: true,
};
};
getStats = (ip, stats) => {
if (stats && stats.top_clients) {
return stats.top_clients[ip];
}
return '';
};
handleDelete = (data) => {
// eslint-disable-next-line no-alert
if (window.confirm(this.props.t('client_confirm_delete', { key: data.name }))) {
this.props.deleteClient(data);
}
};
columns = [
{
Header: this.props.t('table_client'),
accessor: 'ip',
Cell: (row) => {
if (row.original && row.original.mac) {
return (
<div className="logs__row logs__row--overflow">
<span className="logs__text" title={row.original.mac}>
{row.original.mac} <em>(MAC)</em>
</span>
</div>
);
} else if (row.value) {
return (
<div className="logs__row logs__row--overflow">
<span className="logs__text" title={row.value}>
{row.value} <em>(IP)</em>
</span>
</div>
);
}
return '';
},
},
{
Header: this.props.t('table_name'),
accessor: 'name',
Cell: this.cellWrap,
},
{
Header: this.props.t('settings'),
accessor: 'use_global_settings',
Cell: ({ value }) => {
const title = value ? (
<Trans>settings_global</Trans>
) : (
<Trans>settings_custom</Trans>
);
return (
<div className="logs__row logs__row--overflow">
<div className="logs__text" title={title}>
{title}
</div>
</div>
);
},
},
{
Header: this.props.t('blocked_services'),
accessor: 'blocked_services',
Cell: (row) => {
const { value, original } = row;
if (original.use_global_blocked_services) {
return <Trans>settings_global</Trans>;
}
return (
<div className="logs__row logs__row--icons">
{value && value.length > 0 ? value.map(service => (
<svg className="service__icon service__icon--table" title={service} key={service}>
<use xlinkHref={`#service_${service}`} />
</svg>
)) : ''}
</div>
);
},
},
{
Header: this.props.t('table_statistics'),
accessor: 'statistics',
Cell: (row) => {
const clientIP = row.original.ip;
const clientStats = clientIP && this.getStats(clientIP, this.props.topStats);
if (clientStats) {
return (
<div className="logs__row">
<div className="logs__text" title={clientStats}>
{clientStats}
</div>
</div>
);
}
return '';
},
},
{
Header: this.props.t('actions_table_header'),
accessor: 'actions',
maxWidth: 150,
Cell: (row) => {
const clientName = row.original.name;
const {
toggleClientModal, processingDeleting, processingUpdating, t,
} = this.props;
return (
<div className="logs__row logs__row--center">
<button
type="button"
className="btn btn-icon btn-outline-primary btn-sm mr-2"
onClick={() =>
toggleClientModal({
type: MODAL_TYPE.EDIT,
name: clientName,
})
}
disabled={processingUpdating}
title={t('edit_table_action')}
>
<svg className="icons">
<use xlinkHref="#edit" />
</svg>
</button>
<button
type="button"
className="btn btn-icon btn-outline-secondary btn-sm"
onClick={() => this.handleDelete({ name: clientName })}
disabled={processingDeleting}
title={t('delete_table_action')}
>
<svg className="icons">
<use xlinkHref="#delete" />
</svg>
</button>
</div>
);
},
},
];
render() {
const {
t,
clients,
isModalOpen,
modalType,
modalClientName,
toggleClientModal,
processingAdding,
processingUpdating,
} = this.props;
const currentClientData = this.getClient(modalClientName, clients);
return (
<Card
title={t('clients_title')}
subtitle={t('clients_desc')}
bodyType="card-body box-body--settings"
>
<Fragment>
<ReactTable
data={clients || []}
columns={this.columns}
className="-striped -highlight card-table-overflow"
showPagination={true}
defaultPageSize={10}
minRows={5}
previousText={t('previous_btn')}
nextText={t('next_btn')}
loadingText={t('loading_table_status')}
pageText={t('page_table_footer_text')}
ofText={t('of_table_footer_text')}
rowsText={t('rows_table_footer_text')}
noDataText={t('clients_not_found')}
/>
<button
type="button"
className="btn btn-success btn-standard mt-3"
onClick={() => toggleClientModal(MODAL_TYPE.ADD)}
disabled={processingAdding}
>
<Trans>client_add</Trans>
</button>
<Modal
isModalOpen={isModalOpen}
modalType={modalType}
toggleClientModal={toggleClientModal}
currentClientData={currentClientData}
handleSubmit={this.handleSubmit}
processingAdding={processingAdding}
processingUpdating={processingUpdating}
/>
</Fragment>
</Card>
);
}
}
ClientsTable.propTypes = {
t: PropTypes.func.isRequired,
clients: PropTypes.array.isRequired,
topStats: PropTypes.object.isRequired,
toggleClientModal: PropTypes.func.isRequired,
deleteClient: PropTypes.func.isRequired,
addClient: PropTypes.func.isRequired,
updateClient: PropTypes.func.isRequired,
isModalOpen: PropTypes.bool.isRequired,
modalType: PropTypes.string.isRequired,
modalClientName: PropTypes.string.isRequired,
processingAdding: PropTypes.bool.isRequired,
processingDeleting: PropTypes.bool.isRequired,
processingUpdating: PropTypes.bool.isRequired,
};
export default withNamespaces()(ClientsTable);

View File

@@ -0,0 +1,257 @@
import React from 'react';
import { connect } from 'react-redux';
import PropTypes from 'prop-types';
import { Field, reduxForm, formValueSelector } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import Tabs from '../../ui/Tabs';
import { toggleAllServices } from '../../../helpers/helpers';
import { renderField, renderRadioField, renderSelectField, renderServiceField, ipv4, mac, required } from '../../../helpers/form';
import { CLIENT_ID, SERVICES } from '../../../helpers/constants';
import './Service.css';
const settingsCheckboxes = [
{
name: 'use_global_settings',
placeholder: 'client_global_settings',
},
{
name: 'filtering_enabled',
placeholder: 'block_domain_use_filters_and_hosts',
},
{
name: 'safebrowsing_enabled',
placeholder: 'use_adguard_browsing_sec',
},
{
name: 'parental_enabled',
placeholder: 'use_adguard_parental',
},
{
name: 'safesearch_enabled',
placeholder: 'enforce_safe_search',
},
];
let Form = (props) => {
const {
t,
handleSubmit,
reset,
change,
pristine,
submitting,
clientIdentifier,
useGlobalSettings,
useGlobalServices,
toggleClientModal,
processingAdding,
processingUpdating,
} = props;
return (
<form onSubmit={handleSubmit}>
<div className="modal-body">
<div className="form__group">
<div className="form__inline mb-2">
<strong className="mr-3">
<Trans>client_identifier</Trans>
</strong>
<div className="custom-controls-stacked">
<Field
name="identifier"
component={renderRadioField}
type="radio"
className="form-control mr-2"
value="ip"
placeholder={t('ip_address')}
/>
<Field
name="identifier"
component={renderRadioField}
type="radio"
className="form-control mr-2"
value="mac"
placeholder="MAC"
/>
</div>
</div>
<div className="row">
<div className="col col-sm-6">
{clientIdentifier === CLIENT_ID.IP && (
<div className="form__group">
<Field
id="ip"
name="ip"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_enter_ip')}
validate={[ipv4, required]}
/>
</div>
)}
{clientIdentifier === CLIENT_ID.MAC && (
<div className="form__group">
<Field
id="mac"
name="mac"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_enter_mac')}
validate={[mac, required]}
/>
</div>
)}
</div>
<div className="col col-sm-6">
<Field
id="name"
name="name"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_client_name')}
validate={[required]}
/>
</div>
</div>
<div className="form__desc">
<Trans
components={[
<a href="#dhcp" key="0">
link
</a>,
]}
>
client_identifier_desc
</Trans>
</div>
</div>
<Tabs controlClass="form">
<div label="settings" title={props.t('main_settings')}>
{settingsCheckboxes.map(setting => (
<div className="form__group" key={setting.name}>
<Field
name={setting.name}
type="checkbox"
component={renderSelectField}
placeholder={t(setting.placeholder)}
disabled={setting.name !== 'use_global_settings' ? useGlobalSettings : false}
/>
</div>
))}
</div>
<div label="services" title={props.t('block_services')}>
<div className="form__group">
<Field
name="use_global_blocked_services"
type="checkbox"
component={renderServiceField}
placeholder={t('blocked_services_global')}
modifier="service--global"
/>
<div className="row mb-4">
<div className="col-6">
<button
type="button"
className="btn btn-secondary btn-block"
disabled={useGlobalServices}
onClick={() => toggleAllServices(SERVICES, change, true)}
>
<Trans>block_all</Trans>
</button>
</div>
<div className="col-6">
<button
type="button"
className="btn btn-secondary btn-block"
disabled={useGlobalServices}
onClick={() => toggleAllServices(SERVICES, change, false)}
>
<Trans>unblock_all</Trans>
</button>
</div>
</div>
<div className="services">
{SERVICES.map(service => (
<Field
key={service.id}
icon={`service_${service.id}`}
name={`blocked_services.${service.id}`}
type="checkbox"
component={renderServiceField}
placeholder={service.name}
disabled={useGlobalServices}
/>
))}
</div>
</div>
</div>
</Tabs>
</div>
<div className="modal-footer">
<div className="btn-list">
<button
type="button"
className="btn btn-secondary btn-standard"
disabled={submitting}
onClick={() => {
reset();
toggleClientModal();
}}
>
<Trans>cancel_btn</Trans>
</button>
<button
type="submit"
className="btn btn-success btn-standard"
disabled={submitting || pristine || processingAdding || processingUpdating}
>
<Trans>save_btn</Trans>
</button>
</div>
</div>
</form>
);
};
Form.propTypes = {
pristine: PropTypes.bool.isRequired,
handleSubmit: PropTypes.func.isRequired,
reset: PropTypes.func.isRequired,
change: PropTypes.func.isRequired,
submitting: PropTypes.bool.isRequired,
toggleClientModal: PropTypes.func.isRequired,
clientIdentifier: PropTypes.string,
useGlobalSettings: PropTypes.bool,
useGlobalServices: PropTypes.bool,
t: PropTypes.func.isRequired,
processingAdding: PropTypes.bool.isRequired,
processingUpdating: PropTypes.bool.isRequired,
};
const selector = formValueSelector('clientForm');
Form = connect((state) => {
const clientIdentifier = selector(state, 'identifier');
const useGlobalSettings = selector(state, 'use_global_settings');
const useGlobalServices = selector(state, 'use_global_blocked_services');
return {
clientIdentifier,
useGlobalSettings,
useGlobalServices,
};
})(Form);
export default flow([
withNamespaces(),
reduxForm({
form: 'clientForm',
enableReinitialize: true,
}),
])(Form);

View File

@@ -0,0 +1,81 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import ReactModal from 'react-modal';
import { MODAL_TYPE } from '../../../helpers/constants';
import Form from './Form';
const getInitialData = (initial) => {
if (initial && initial.blocked_services) {
const { blocked_services } = initial;
const blocked = {};
blocked_services.forEach((service) => {
blocked[service] = true;
});
return {
...initial,
blocked_services: blocked,
};
}
return initial;
};
const Modal = (props) => {
const {
isModalOpen,
modalType,
currentClientData,
handleSubmit,
toggleClientModal,
processingAdding,
processingUpdating,
} = props;
const initialData = getInitialData(currentClientData);
return (
<ReactModal
className="Modal__Bootstrap modal-dialog modal-dialog-centered modal-dialog--clients"
closeTimeoutMS={0}
isOpen={isModalOpen}
onRequestClose={() => toggleClientModal()}
>
<div className="modal-content">
<div className="modal-header">
<h4 className="modal-title">
{modalType === MODAL_TYPE.EDIT ? (
<Trans>client_edit</Trans>
) : (
<Trans>client_new</Trans>
)}
</h4>
<button type="button" className="close" onClick={() => toggleClientModal()}>
<span className="sr-only">Close</span>
</button>
</div>
<Form
initialValues={{ ...initialData }}
onSubmit={handleSubmit}
toggleClientModal={toggleClientModal}
processingAdding={processingAdding}
processingUpdating={processingUpdating}
/>
</div>
</ReactModal>
);
};
Modal.propTypes = {
isModalOpen: PropTypes.bool.isRequired,
modalType: PropTypes.string.isRequired,
currentClientData: PropTypes.object.isRequired,
handleSubmit: PropTypes.func.isRequired,
toggleClientModal: PropTypes.func.isRequired,
processingAdding: PropTypes.bool.isRequired,
processingUpdating: PropTypes.bool.isRequired,
};
export default withNamespaces()(Modal);

View File

@@ -0,0 +1,79 @@
.service {
display: flex;
flex-direction: row-reverse;
align-items: center;
margin-bottom: 15px;
padding: 10px 15px;
border: 1px solid #eee;
border-radius: 4px;
cursor: pointer;
}
@media screen and (min-width: 768px) {
.services {
display: flex;
flex-flow: row wrap;
}
.service {
flex-grow: 0;
flex-shrink: 0;
flex-basis: calc(99.9% * 4/12 - (30px - 30px * 4/12));
max-width: calc(99.9% * 4/12 - (30px - 30px * 4/12));
width: calc(99.9% * 4/12 - (30px - 30px * 4/12));
}
.service--global {
flex-basis: 1;
max-width: 100%;
width: 100%;
}
.service:nth-child(1n) {
margin-right: 30px;
margin-left: 0;
}
.service:nth-child(3n) {
margin-right: 0;
margin-left: auto;
}
}
.service__icon {
width: 20px;
height: 20px;
flex-shrink: 0;
margin-right: 10px;
color: #495057;
}
.service--global .service__icon {
display: none;
}
.service__icon--table {
margin-bottom: 3px;
color: #9aa0ac;
}
.service__switch {
margin-left: auto;
border: 1px solid rgba(150, 150, 150, 0.12);
}
.custom-switch-input:checked ~ .service__switch {
background-color: #cd201f;
}
.custom-switch-input:focus ~ .service__switch {
box-shadow: 0 0 0 2px #cd201f3b;
border-color: #ec4241;
}
.custom-switch-input:disabled ~ .service__switch,
.custom-switch-input:disabled ~ .service__text,
.custom-switch-input:disabled ~ .service__icon {
opacity: 0.5;
cursor: pointer;
}

View File

@@ -0,0 +1,71 @@
import React, { Component, Fragment } from 'react';
import { withNamespaces } from 'react-i18next';
import PropTypes from 'prop-types';
import ClientsTable from './ClientsTable';
import AutoClients from './AutoClients';
import PageTitle from '../../ui/PageTitle';
import Loading from '../../ui/Loading';
class Clients extends Component {
componentDidMount() {
this.props.getClients();
this.props.getTopStats();
}
render() {
const {
t,
dashboard,
clients,
addClient,
updateClient,
deleteClient,
toggleClientModal,
} = this.props;
return (
<Fragment>
<PageTitle title={t('client_settings')} />
{(dashboard.processingTopStats || dashboard.processingClients) && <Loading />}
{!dashboard.processingTopStats && !dashboard.processingClients && (
<Fragment>
<ClientsTable
clients={dashboard.clients}
topStats={dashboard.topStats}
isModalOpen={clients.isModalOpen}
modalClientName={clients.modalClientName}
modalType={clients.modalType}
addClient={addClient}
updateClient={updateClient}
deleteClient={deleteClient}
toggleClientModal={toggleClientModal}
processingAdding={clients.processingAdding}
processingDeleting={clients.processingDeleting}
processingUpdating={clients.processingUpdating}
/>
<AutoClients
autoClients={dashboard.autoClients}
topStats={dashboard.topStats}
/>
</Fragment>
)}
</Fragment>
);
}
}
Clients.propTypes = {
t: PropTypes.func.isRequired,
dashboard: PropTypes.object.isRequired,
clients: PropTypes.object.isRequired,
toggleClientModal: PropTypes.func.isRequired,
deleteClient: PropTypes.func.isRequired,
addClient: PropTypes.func.isRequired,
updateClient: PropTypes.func.isRequired,
getClients: PropTypes.func.isRequired,
getTopStats: PropTypes.func.isRequired,
topStats: PropTypes.object,
};
export default withNamespaces()(Clients);

View File

@@ -1,22 +1,97 @@
import React from 'react';
import { connect } from 'react-redux';
import PropTypes from 'prop-types';
import { Field, reduxForm } from 'redux-form';
import { withNamespaces } from 'react-i18next';
import { Field, reduxForm, formValueSelector } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { renderField, required, ipv4, isPositive, toNumber } from '../../../helpers/form';
const Form = (props) => {
const renderInterfaces = (interfaces => (
Object.keys(interfaces).map((item) => {
const option = interfaces[item];
const { name } = option;
const onlyIPv6 = option.ip_addresses.every(ip => ip.includes(':'));
let interfaceIP = option.ip_addresses[0];
if (!onlyIPv6) {
option.ip_addresses.forEach((ip) => {
if (!ip.includes(':')) {
interfaceIP = ip;
}
});
}
return (
<option value={name} key={name} disabled={onlyIPv6}>
{name} - {interfaceIP}
</option>
);
})
));
const renderInterfaceValues = (interfaceValues => (
<ul className="list-unstyled mt-1 mb-0">
<li>
<span className="interface__title">MTU: </span>
{interfaceValues.mtu}
</li>
<li>
<span className="interface__title"><Trans>dhcp_hardware_address</Trans>: </span>
{interfaceValues.hardware_address}
</li>
<li>
<span className="interface__title"><Trans>dhcp_ip_addresses</Trans>: </span>
{
interfaceValues.ip_addresses
.map(ip => <span key={ip} className="interface__ip">{ip}</span>)
}
</li>
</ul>
));
let Form = (props) => {
const {
t,
handleSubmit,
submitting,
invalid,
enabled,
interfaces,
interfaceValue,
processingConfig,
processingInterfaces,
} = props;
return (
<form onSubmit={handleSubmit}>
{!processingInterfaces && interfaces &&
<div className="row">
<div className="col-sm-12 col-md-6">
<div className="form__group form__group--settings">
<label>{t('dhcp_interface_select')}</label>
<Field
name="interface_name"
component="select"
className="form-control custom-select"
validate={[required]}
>
<option value="" disabled={enabled}>
{t('dhcp_interface_select')}
</option>
{renderInterfaces(interfaces)}
</Field>
</div>
</div>
{interfaceValue &&
<div className="col-sm-12 col-md-6">
{interfaces[interfaceValue] &&
renderInterfaceValues(interfaces[interfaceValue])}
</div>
}
</div>
}
<hr/>
<div className="row">
<div className="col-lg-6">
<div className="form__group form__group--settings">
@@ -101,11 +176,24 @@ Form.propTypes = {
submitting: PropTypes.bool,
invalid: PropTypes.bool,
interfaces: PropTypes.object,
interfaceValue: PropTypes.string,
initialValues: PropTypes.object,
processingConfig: PropTypes.bool,
processingInterfaces: PropTypes.bool,
enabled: PropTypes.bool,
t: PropTypes.func,
};
const selector = formValueSelector('dhcpForm');
Form = connect((state) => {
const interfaceValue = selector(state, 'interface_name');
return {
interfaceValue,
};
})(Form);
export default flow([
withNamespaces(),
reduxForm({ form: 'dhcpForm' }),

View File

@@ -1,114 +0,0 @@
import React from 'react';
import { connect } from 'react-redux';
import PropTypes from 'prop-types';
import { Field, reduxForm, formValueSelector } from 'redux-form';
import { withNamespaces, Trans } from 'react-i18next';
import flow from 'lodash/flow';
const renderInterfaces = (interfaces => (
Object.keys(interfaces).map((item) => {
const option = interfaces[item];
const { name } = option;
const onlyIPv6 = option.ip_addresses.every(ip => ip.includes(':'));
let interfaceIP = option.ip_addresses[0];
if (!onlyIPv6) {
option.ip_addresses.forEach((ip) => {
if (!ip.includes(':')) {
interfaceIP = ip;
}
});
}
return (
<option value={name} key={name} disabled={onlyIPv6}>
{name} - {interfaceIP}
</option>
);
})
));
const renderInterfaceValues = (interfaceValues => (
<ul className="list-unstyled mt-1 mb-0">
<li>
<span className="interface__title">MTU: </span>
{interfaceValues.mtu}
</li>
<li>
<span className="interface__title"><Trans>dhcp_hardware_address</Trans>: </span>
{interfaceValues.hardware_address}
</li>
<li>
<span className="interface__title"><Trans>dhcp_ip_addresses</Trans>: </span>
{
interfaceValues.ip_addresses
.map(ip => <span key={ip} className="interface__ip">{ip}</span>)
}
</li>
</ul>
));
let Interface = (props) => {
const {
t,
handleChange,
interfaces,
processing,
interfaceValue,
enabled,
} = props;
return (
<form>
{!processing && interfaces &&
<div className="row">
<div className="col-sm-12 col-md-6">
<div className="form__group form__group--settings">
<label>{t('dhcp_interface_select')}</label>
<Field
name="interface_name"
component="select"
className="form-control custom-select"
onChange={handleChange}
>
<option value="" disabled={enabled}>{t('dhcp_interface_select')}</option>
{renderInterfaces(interfaces)}
</Field>
</div>
</div>
{interfaceValue &&
<div className="col-sm-12 col-md-6">
{interfaces[interfaceValue] &&
renderInterfaceValues(interfaces[interfaceValue])}
</div>
}
</div>
}
<hr/>
</form>
);
};
Interface.propTypes = {
handleChange: PropTypes.func,
interfaces: PropTypes.object,
processing: PropTypes.bool,
interfaceValue: PropTypes.string,
initialValues: PropTypes.object,
enabled: PropTypes.bool,
t: PropTypes.func,
};
const selector = formValueSelector('dhcpInterface');
Interface = connect((state) => {
const interfaceValue = selector(state, 'interface_name');
return {
interfaceValue,
};
})(Interface);
export default flow([
withNamespaces(),
reduxForm({ form: 'dhcpInterface' }),
])(Interface);

View File

@@ -0,0 +1,96 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Field, reduxForm } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { renderField, ipv4, mac, required } from '../../../../helpers/form';
const Form = (props) => {
const {
t,
handleSubmit,
reset,
pristine,
submitting,
toggleLeaseModal,
processingAdding,
} = props;
return (
<form onSubmit={handleSubmit}>
<div className="modal-body">
<div className="form__group">
<Field
id="mac"
name="mac"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_enter_mac')}
validate={[required, mac]}
/>
</div>
<div className="form__group">
<Field
id="ip"
name="ip"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_enter_ip')}
validate={[required, ipv4]}
/>
</div>
<div className="form__group">
<Field
id="hostname"
name="hostname"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_enter_hostname')}
/>
</div>
</div>
<div className="modal-footer">
<div className="btn-list">
<button
type="button"
className="btn btn-secondary btn-standard"
disabled={submitting}
onClick={() => {
reset();
toggleLeaseModal();
}}
>
<Trans>cancel_btn</Trans>
</button>
<button
type="submit"
className="btn btn-success btn-standard"
disabled={submitting || pristine || processingAdding}
>
<Trans>save_btn</Trans>
</button>
</div>
</div>
</form>
);
};
Form.propTypes = {
pristine: PropTypes.bool.isRequired,
handleSubmit: PropTypes.func.isRequired,
reset: PropTypes.func.isRequired,
submitting: PropTypes.bool.isRequired,
toggleLeaseModal: PropTypes.func.isRequired,
processingAdding: PropTypes.bool.isRequired,
t: PropTypes.func.isRequired,
};
export default flow([
withNamespaces(),
reduxForm({ form: 'leaseForm' }),
])(Form);

View File

@@ -0,0 +1,49 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import ReactModal from 'react-modal';
import Form from './Form';
const Modal = (props) => {
const {
isModalOpen,
handleSubmit,
toggleLeaseModal,
processingAdding,
} = props;
return (
<ReactModal
className="Modal__Bootstrap modal-dialog modal-dialog-centered modal-dialog--clients"
closeTimeoutMS={0}
isOpen={isModalOpen}
onRequestClose={() => toggleLeaseModal()}
>
<div className="modal-content">
<div className="modal-header">
<h4 className="modal-title">
<Trans>dhcp_new_static_lease</Trans>
</h4>
<button type="button" className="close" onClick={() => toggleLeaseModal()}>
<span className="sr-only">Close</span>
</button>
</div>
<Form
onSubmit={handleSubmit}
toggleLeaseModal={toggleLeaseModal}
processingAdding={processingAdding}
/>
</div>
</ReactModal>
);
};
Modal.propTypes = {
isModalOpen: PropTypes.bool.isRequired,
handleSubmit: PropTypes.func.isRequired,
toggleLeaseModal: PropTypes.func.isRequired,
processingAdding: PropTypes.bool.isRequired,
};
export default withNamespaces()(Modal);

View File

@@ -0,0 +1,112 @@
import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types';
import ReactTable from 'react-table';
import { Trans, withNamespaces } from 'react-i18next';
import Modal from './Modal';
class StaticLeases extends Component {
cellWrap = ({ value }) => (
<div className="logs__row logs__row--overflow">
<span className="logs__text" title={value}>
{value}
</span>
</div>
);
handleSubmit = (data) => {
this.props.addStaticLease(data);
}
handleDelete = (ip, mac, hostname = '') => {
const name = hostname || ip;
// eslint-disable-next-line no-alert
if (window.confirm(this.props.t('delete_confirm', { key: name }))) {
this.props.removeStaticLease({ ip, mac, hostname });
}
}
render() {
const {
isModalOpen,
toggleLeaseModal,
processingAdding,
processingDeleting,
staticLeases,
t,
} = this.props;
return (
<Fragment>
<ReactTable
data={staticLeases || []}
columns={[
{
Header: 'MAC',
accessor: 'mac',
Cell: this.cellWrap,
},
{
Header: 'IP',
accessor: 'ip',
Cell: this.cellWrap,
},
{
Header: <Trans>dhcp_table_hostname</Trans>,
accessor: 'hostname',
Cell: this.cellWrap,
},
{
Header: <Trans>actions_table_header</Trans>,
accessor: 'actions',
maxWidth: 150,
Cell: (row) => {
const { ip, mac, hostname } = row.original;
return (
<div className="logs__row logs__row--center">
<button
type="button"
className="btn btn-icon btn-outline-secondary btn-sm"
title={t('delete_table_action')}
disabled={processingDeleting}
onClick={() =>
this.handleDelete(ip, mac, hostname)
}
>
<svg className="icons">
<use xlinkHref="#delete" />
</svg>
</button>
</div>
);
},
},
]}
showPagination={false}
noDataText={t('dhcp_static_leases_not_found')}
className="-striped -highlight card-table-overflow"
minRows={6}
/>
<Modal
isModalOpen={isModalOpen}
toggleLeaseModal={toggleLeaseModal}
handleSubmit={this.handleSubmit}
processingAdding={processingAdding}
/>
</Fragment>
);
}
}
StaticLeases.propTypes = {
staticLeases: PropTypes.array.isRequired,
isModalOpen: PropTypes.bool.isRequired,
toggleLeaseModal: PropTypes.func.isRequired,
removeStaticLease: PropTypes.func.isRequired,
addStaticLease: PropTypes.func.isRequired,
processingAdding: PropTypes.bool.isRequired,
processingDeleting: PropTypes.bool.isRequired,
t: PropTypes.func.isRequired,
};
export default withNamespaces()(StaticLeases);

View File

@@ -6,18 +6,27 @@ import { Trans, withNamespaces } from 'react-i18next';
import { DHCP_STATUS_RESPONSE } from '../../../helpers/constants';
import Form from './Form';
import Leases from './Leases';
import Interface from './Interface';
import StaticLeases from './StaticLeases/index';
import Card from '../../ui/Card';
import Accordion from '../../ui/Accordion';
import PageTitle from '../../ui/PageTitle';
import Loading from '../../ui/Loading';
class Dhcp extends Component {
componentDidMount() {
this.props.getDhcpStatus();
this.props.getDhcpInterfaces();
}
handleFormSubmit = (values) => {
this.props.setDhcpConfig(values);
if (values.interface_name) {
this.props.setDhcpConfig(values);
}
};
handleToggle = (config) => {
this.props.toggleDhcp(config);
}
};
getToggleDhcpButton = () => {
const {
@@ -52,17 +61,13 @@ class Dhcp extends Component {
className="btn btn-standard mr-2 btn-success"
onClick={() => this.handleToggle(config)}
disabled={
!filledConfig
|| !check
|| otherDhcpFound
|| processingDhcp
|| processingConfig
!filledConfig || !check || otherDhcpFound || processingDhcp || processingConfig
}
>
<Trans>dhcp_enable</Trans>
</button>
);
}
};
getActiveDhcpMessage = (t, check) => {
const { found } = check.otherServer;
@@ -93,7 +98,7 @@ class Dhcp extends Component {
)}
</div>
);
}
};
getDhcpWarning = (check) => {
if (check.otherServer.found === DHCP_STATUS_RESPONSE.NO) {
@@ -105,7 +110,7 @@ class Dhcp extends Component {
<Trans>dhcp_warning</Trans>
</div>
);
}
};
getStaticIpWarning = (t, check, interfaceName) => {
if (check.staticIP.static === DHCP_STATUS_RESPONSE.ERROR) {
@@ -119,21 +124,19 @@ class Dhcp extends Component {
</Accordion>
</div>
</div>
<hr className="mt-4 mb-4"/>
<hr className="mt-4 mb-4" />
</Fragment>
);
} else if (
check.staticIP.static === DHCP_STATUS_RESPONSE.NO
&& check.staticIP.ip
&& interfaceName
check.staticIP.static === DHCP_STATUS_RESPONSE.NO &&
check.staticIP.ip &&
interfaceName
) {
return (
<Fragment>
<div className="text-secondary mb-2">
<Trans
components={[
<strong key="0">example</strong>,
]}
components={[<strong key="0">example</strong>]}
values={{
interfaceName,
ipAddress: check.staticIP.ip,
@@ -142,13 +145,13 @@ class Dhcp extends Component {
dhcp_dynamic_ip_found
</Trans>
</div>
<hr className="mt-4 mb-4"/>
<hr className="mt-4 mb-4" />
</Fragment>
);
}
return '';
}
};
render() {
const { t, dhcp } = this.props;
@@ -156,69 +159,101 @@ class Dhcp extends Component {
'btn btn-primary btn-standard': true,
'btn btn-primary btn-standard btn-loading': dhcp.processingStatus,
});
const {
enabled,
interface_name,
...values
} = dhcp.config;
const { enabled, interface_name, ...values } = dhcp.config;
return (
<Fragment>
<Card title={ t('dhcp_title') } subtitle={ t('dhcp_description') } bodyType="card-body box-body--settings">
<div className="dhcp">
{!dhcp.processing &&
<Fragment>
<Interface
onChange={this.handleFormSubmit}
initialValues={{ interface_name }}
interfaces={dhcp.interfaces}
processing={dhcp.processingInterfaces}
enabled={dhcp.config.enabled}
/>
<Form
onSubmit={this.handleFormSubmit}
initialValues={{ ...values }}
interfaces={dhcp.interfaces}
processingConfig={dhcp.processingConfig}
/>
<hr/>
<div className="card-actions mb-3">
{this.getToggleDhcpButton()}
<button
type="button"
className={statusButtonClass}
onClick={() =>
this.props.findActiveDhcp(dhcp.config.interface_name)
}
disabled={
dhcp.config.enabled
|| !dhcp.config.interface_name
|| dhcp.processingConfig
}
>
<Trans>check_dhcp_servers</Trans>
</button>
</div>
{!enabled && dhcp.check &&
<Fragment>
{this.getStaticIpWarning(t, dhcp.check, interface_name)}
{this.getActiveDhcpMessage(t, dhcp.check)}
{this.getDhcpWarning(dhcp.check)}
</Fragment>
}
</Fragment>
}
</div>
</Card>
{!dhcp.processing && dhcp.config.enabled &&
<Card title={ t('dhcp_leases') } bodyType="card-body box-body--settings">
<div className="row">
<div className="col">
<Leases leases={dhcp.leases} />
<PageTitle title={t('dhcp_settings')} />
{(dhcp.processing || dhcp.processingInterfaces) && <Loading />}
{!dhcp.processing && !dhcp.processingInterfaces && (
<Fragment>
<Card
title={t('dhcp_title')}
subtitle={t('dhcp_description')}
bodyType="card-body box-body--settings"
>
<div className="dhcp">
<Fragment>
<Form
onSubmit={this.handleFormSubmit}
initialValues={{
interface_name,
...values,
}}
interfaces={dhcp.interfaces}
processingConfig={dhcp.processingConfig}
processingInterfaces={dhcp.processingInterfaces}
enabled={enabled}
/>
<hr />
<div className="card-actions mb-3">
{this.getToggleDhcpButton()}
<button
type="button"
className={statusButtonClass}
onClick={() =>
this.props.findActiveDhcp(interface_name)
}
disabled={
enabled || !interface_name || dhcp.processingConfig
}
>
<Trans>check_dhcp_servers</Trans>
</button>
</div>
{!enabled && dhcp.check && (
<Fragment>
{this.getStaticIpWarning(t, dhcp.check, interface_name)}
{this.getActiveDhcpMessage(t, dhcp.check)}
{this.getDhcpWarning(dhcp.check)}
</Fragment>
)}
</Fragment>
</div>
</div>
</Card>
}
</Card>
{dhcp.config.enabled && (
<Fragment>
<Card
title={t('dhcp_leases')}
bodyType="card-body box-body--settings"
>
<div className="row">
<div className="col">
<Leases leases={dhcp.leases} />
</div>
</div>
</Card>
<Card
title={t('dhcp_static_leases')}
bodyType="card-body box-body--settings"
>
<div className="row">
<div className="col-12">
<StaticLeases
staticLeases={dhcp.staticLeases}
isModalOpen={dhcp.isModalOpen}
addStaticLease={this.props.addStaticLease}
removeStaticLease={this.props.removeStaticLease}
toggleLeaseModal={this.props.toggleLeaseModal}
processingAdding={dhcp.processingAdding}
processingDeleting={dhcp.processingDeleting}
/>
</div>
<div className="col-12">
<button
type="button"
className="btn btn-success btn-standard mt-3"
onClick={() => this.props.toggleLeaseModal()}
>
<Trans>dhcp_add_static_lease</Trans>
</button>
</div>
</div>
</Card>
</Fragment>
)}
</Fragment>
)}
</Fragment>
);
}
@@ -230,7 +265,10 @@ Dhcp.propTypes = {
getDhcpStatus: PropTypes.func,
setDhcpConfig: PropTypes.func,
findActiveDhcp: PropTypes.func,
handleSubmit: PropTypes.func,
addStaticLease: PropTypes.func,
removeStaticLease: PropTypes.func,
toggleLeaseModal: PropTypes.func,
getDhcpInterfaces: PropTypes.func,
t: PropTypes.func,
};

View File

@@ -0,0 +1,80 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Field, reduxForm } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
const Form = (props) => {
const { handleSubmit, submitting, invalid } = props;
return (
<form onSubmit={handleSubmit}>
<div className="form__group mb-5">
<label className="form__label form__label--with-desc" htmlFor="allowed_clients">
<Trans>access_allowed_title</Trans>
</label>
<div className="form__desc form__desc--top">
<Trans>access_allowed_desc</Trans>
</div>
<Field
id="allowed_clients"
name="allowed_clients"
component="textarea"
type="text"
className="form-control form-control--textarea"
/>
</div>
<div className="form__group mb-5">
<label className="form__label form__label--with-desc" htmlFor="disallowed_clients">
<Trans>access_disallowed_title</Trans>
</label>
<div className="form__desc form__desc--top">
<Trans>access_disallowed_desc</Trans>
</div>
<Field
id="disallowed_clients"
name="disallowed_clients"
component="textarea"
type="text"
className="form-control form-control--textarea"
/>
</div>
<div className="form__group mb-5">
<label className="form__label form__label--with-desc" htmlFor="blocked_hosts">
<Trans>access_blocked_title</Trans>
</label>
<div className="form__desc form__desc--top">
<Trans>access_blocked_desc</Trans>
</div>
<Field
id="blocked_hosts"
name="blocked_hosts"
component="textarea"
type="text"
className="form-control form-control--textarea"
/>
</div>
<div className="card-actions">
<div className="btn-list">
<button
type="submit"
className="btn btn-success btn-standard"
disabled={submitting || invalid}
>
<Trans>save_config</Trans>
</button>
</div>
</div>
</form>
);
};
Form.propTypes = {
handleSubmit: PropTypes.func,
submitting: PropTypes.bool,
invalid: PropTypes.bool,
initialValues: PropTypes.object,
t: PropTypes.func,
};
export default flow([withNamespaces(), reduxForm({ form: 'accessForm' })])(Form);

View File

@@ -0,0 +1,43 @@
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import { withNamespaces } from 'react-i18next';
import Form from './Form';
import Card from '../../../ui/Card';
class Access extends Component {
handleFormSubmit = (values) => {
this.props.setAccessList(values);
};
render() {
const { t, access } = this.props;
const {
processing,
processingSet,
...values
} = access;
return (
<Card
title={t('access_title')}
subtitle={t('access_desc')}
bodyType="card-body box-body--settings"
>
<Form
initialValues={values}
onSubmit={this.handleFormSubmit}
/>
</Card>
);
}
}
Access.propTypes = {
access: PropTypes.object.isRequired,
setAccessList: PropTypes.func.isRequired,
t: PropTypes.func.isRequired,
};
export default withNamespaces()(Access);

View File

@@ -0,0 +1,89 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Field, reduxForm } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { renderField, required, domain, answer } from '../../../../helpers/form';
const Form = (props) => {
const {
t,
handleSubmit,
reset,
pristine,
submitting,
toggleRewritesModal,
processingAdd,
} = props;
return (
<form onSubmit={handleSubmit}>
<div className="modal-body">
<div className="form__group">
<Field
id="domain"
name="domain"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_domain')}
validate={[required, domain]}
/>
</div>
<div className="form__group">
<Field
id="answer"
name="answer"
component={renderField}
type="text"
className="form-control"
placeholder={t('form_answer')}
validate={[required, answer]}
/>
</div>
</div>
<div className="modal-footer">
<div className="btn-list">
<button
type="button"
className="btn btn-secondary btn-standard"
disabled={submitting || processingAdd}
onClick={() => {
reset();
toggleRewritesModal();
}}
>
<Trans>cancel_btn</Trans>
</button>
<button
type="submit"
className="btn btn-success btn-standard"
disabled={submitting || pristine || processingAdd}
>
<Trans>save_btn</Trans>
</button>
</div>
</div>
</form>
);
};
Form.propTypes = {
pristine: PropTypes.bool.isRequired,
handleSubmit: PropTypes.func.isRequired,
reset: PropTypes.func.isRequired,
toggleRewritesModal: PropTypes.func.isRequired,
submitting: PropTypes.bool.isRequired,
processingAdd: PropTypes.bool.isRequired,
t: PropTypes.func.isRequired,
};
export default flow([
withNamespaces(),
reduxForm({
form: 'rewritesForm',
enableReinitialize: true,
}),
])(Form);

View File

@@ -0,0 +1,52 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import ReactModal from 'react-modal';
import Form from './Form';
const Modal = (props) => {
const {
isModalOpen,
handleSubmit,
toggleRewritesModal,
processingAdd,
processingDelete,
} = props;
return (
<ReactModal
className="Modal__Bootstrap modal-dialog modal-dialog-centered"
closeTimeoutMS={0}
isOpen={isModalOpen}
onRequestClose={() => toggleRewritesModal()}
>
<div className="modal-content">
<div className="modal-header">
<h4 className="modal-title">
<Trans>Add DNS rewrite</Trans>
</h4>
<button type="button" className="close" onClick={() => toggleRewritesModal()}>
<span className="sr-only">Close</span>
</button>
</div>
<Form
onSubmit={handleSubmit}
toggleRewritesModal={toggleRewritesModal}
processingAdd={processingAdd}
processingDelete={processingDelete}
/>
</div>
</ReactModal>
);
};
Modal.propTypes = {
isModalOpen: PropTypes.bool.isRequired,
handleSubmit: PropTypes.func.isRequired,
toggleRewritesModal: PropTypes.func.isRequired,
processingAdd: PropTypes.bool.isRequired,
processingDelete: PropTypes.bool.isRequired,
};
export default withNamespaces()(Modal);

View File

@@ -0,0 +1,87 @@
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import ReactTable from 'react-table';
import { withNamespaces } from 'react-i18next';
class Table extends Component {
cellWrap = ({ value }) => (
<div className="logs__row logs__row--overflow">
<span className="logs__text" title={value}>
{value}
</span>
</div>
);
columns = [
{
Header: 'Domain',
accessor: 'domain',
Cell: this.cellWrap,
},
{
Header: 'Answer',
accessor: 'answer',
Cell: this.cellWrap,
},
{
Header: this.props.t('actions_table_header'),
accessor: 'actions',
maxWidth: 100,
Cell: value => (
<div className="logs__row logs__row--center">
<button
type="button"
className="btn btn-icon btn-outline-secondary btn-sm"
onClick={() =>
this.props.handleDelete({
answer: value.row.answer,
domain: value.row.domain,
})
}
title={this.props.t('delete_table_action')}
>
<svg className="icons">
<use xlinkHref="#delete" />
</svg>
</button>
</div>
),
},
];
render() {
const {
t, list, processing, processingAdd, processingDelete,
} = this.props;
return (
<ReactTable
data={list || []}
columns={this.columns}
loading={processing || processingAdd || processingDelete}
className="-striped -highlight card-table-overflow"
showPagination={true}
defaultPageSize={10}
minRows={5}
previousText={t('previous_btn')}
nextText={t('next_btn')}
loadingText={t('loading_table_status')}
pageText={t('page_table_footer_text')}
ofText={t('of_table_footer_text')}
rowsText={t('rows_table_footer_text')}
noDataText={t('rewrite_not_found')}
/>
);
}
}
Table.propTypes = {
t: PropTypes.func.isRequired,
list: PropTypes.array.isRequired,
processing: PropTypes.bool.isRequired,
processingAdd: PropTypes.bool.isRequired,
processingDelete: PropTypes.bool.isRequired,
handleDelete: PropTypes.func.isRequired,
};
export default withNamespaces()(Table);

View File

@@ -0,0 +1,83 @@
import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import Table from './Table';
import Modal from './Modal';
import Card from '../../../ui/Card';
class Rewrites extends Component {
handleSubmit = (values) => {
this.props.addRewrite(values);
};
handleDelete = (values) => {
// eslint-disable-next-line no-alert
if (window.confirm(this.props.t('rewrite_confirm_delete', { key: values.domain }))) {
this.props.deleteRewrite(values);
}
};
render() {
const {
t,
rewrites,
toggleRewritesModal,
} = this.props;
const {
list,
isModalOpen,
processing,
processingAdd,
processingDelete,
} = rewrites;
return (
<Card
id="rewrites"
title={t('dns_rewrites')}
subtitle={t('rewrite_desc')}
bodyType="card-body box-body--settings"
>
<Fragment>
<Table
list={list}
processing={processing}
processingAdd={processingAdd}
processingDelete={processingDelete}
handleDelete={this.handleDelete}
/>
<button
type="button"
className="btn btn-success btn-standard mt-3"
onClick={() => toggleRewritesModal()}
disabled={processingAdd}
>
<Trans>rewrite_add</Trans>
</button>
<Modal
isModalOpen={isModalOpen}
toggleRewritesModal={toggleRewritesModal}
handleSubmit={this.handleSubmit}
processingAdd={processingAdd}
processingDelete={processingDelete}
/>
</Fragment>
</Card>
);
}
}
Rewrites.propTypes = {
t: PropTypes.func.isRequired,
getRewritesList: PropTypes.func.isRequired,
toggleRewritesModal: PropTypes.func.isRequired,
addRewrite: PropTypes.func.isRequired,
deleteRewrite: PropTypes.func.isRequired,
rewrites: PropTypes.object.isRequired,
};
export default withNamespaces()(Rewrites);

View File

@@ -4,17 +4,38 @@ import { Trans, withNamespaces } from 'react-i18next';
const Examples = props => (
<div className="list leading-loose">
<p>
<Trans
components={[
<a
href="https://kb.adguard.com/general/dns-providers"
target="_blank"
rel="noopener noreferrer"
key="0"
>
DNS providers
</a>,
]}
>
dns_providers
</Trans>
</p>
<Trans>examples_title</Trans>:
<ol className="leading-loose">
<li>
<code>1.1.1.1</code> - { props.t('example_upstream_regular') }
<code>1.1.1.1</code> - {props.t('example_upstream_regular')}
</li>
<li>
<code>tls://1dot1dot1dot1.cloudflare-dns.com</code> &nbsp;
<span>
<Trans
components={[
<a href="https://en.wikipedia.org/wiki/DNS_over_TLS" target="_blank" rel="noopener noreferrer" key="0">
<a
href="https://en.wikipedia.org/wiki/DNS_over_TLS"
target="_blank"
rel="noopener noreferrer"
key="0"
>
DNS-over-TLS
</a>,
]}
@@ -28,7 +49,12 @@ const Examples = props => (
<span>
<Trans
components={[
<a href="https://en.wikipedia.org/wiki/DNS_over_HTTPS" target="_blank" rel="noopener noreferrer" key="0">
<a
href="https://en.wikipedia.org/wiki/DNS_over_HTTPS"
target="_blank"
rel="noopener noreferrer"
key="0"
>
DNS-over-HTTPS
</a>,
]}
@@ -45,13 +71,28 @@ const Examples = props => (
<span>
<Trans
components={[
<a href="https://dnscrypt.info/stamps/" target="_blank" rel="noopener noreferrer" key="0">
<a
href="https://dnscrypt.info/stamps/"
target="_blank"
rel="noopener noreferrer"
key="0"
>
DNS Stamps
</a>,
<a href="https://dnscrypt.info/" target="_blank" rel="noopener noreferrer" key="1">
<a
href="https://dnscrypt.info/"
target="_blank"
rel="noopener noreferrer"
key="1"
>
DNSCrypt
</a>,
<a href="https://en.wikipedia.org/wiki/DNS_over_HTTPS" target="_blank" rel="noopener noreferrer" key="2">
<a
href="https://en.wikipedia.org/wiki/DNS_over_HTTPS"
target="_blank"
rel="noopener noreferrer"
key="2"
>
DNS-over-HTTPS
</a>,
]}
@@ -65,7 +106,12 @@ const Examples = props => (
<span>
<Trans
components={[
<a href="https://github.com/AdguardTeam/AdGuardHome/wiki/Configuration#upstreams-for-domains" target="_blank" rel="noopener noreferrer" key="0">
<a
href="https://github.com/AdguardTeam/AdGuardHome/wiki/Configuration#upstreams-for-domains"
target="_blank"
rel="noopener noreferrer"
key="0"
>
Link
</a>,
]}

View File

@@ -6,7 +6,7 @@ import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import classnames from 'classnames';
import { renderSelectField } from '../../../helpers/form';
import { renderSelectField } from '../../../../helpers/form';
import Examples from './Examples';
let Form = (props) => {
@@ -58,11 +58,11 @@ let Form = (props) => {
</div>
<div className="col-12">
<Examples />
<hr/>
<hr />
</div>
<div className="col-12">
<div className="form__group">
<label className="form__label" htmlFor="bootstrap_dns">
<label className="form__label form__label--with-desc" htmlFor="bootstrap_dns">
<Trans>bootstrap_dns</Trans>
</label>
<div className="form__desc form__desc--top">
@@ -84,11 +84,13 @@ let Form = (props) => {
<button
type="button"
className={testButtonClass}
onClick={() => testUpstream({
upstream_dns: upstreamDns,
bootstrap_dns: bootstrapDns,
all_servers: allServers,
})}
onClick={() =>
testUpstream({
upstream_dns: upstreamDns,
bootstrap_dns: bootstrapDns,
all_servers: allServers,
})
}
disabled={!upstreamDns || processingTestUpstream}
>
<Trans>test_upstream_btn</Trans>
@@ -97,10 +99,7 @@ let Form = (props) => {
type="submit"
className="btn btn-success btn-standard"
disabled={
submitting
|| invalid
|| processingSetUpstream
|| processingTestUpstream
submitting || invalid || processingSetUpstream || processingTestUpstream
}
>
<Trans>apply_btn</Trans>
@@ -140,5 +139,7 @@ Form = connect((state) => {
export default flow([
withNamespaces(),
reduxForm({ form: 'upstreamForm' }),
reduxForm({
form: 'upstreamForm',
}),
])(Form);

View File

@@ -3,7 +3,7 @@ import PropTypes from 'prop-types';
import { withNamespaces } from 'react-i18next';
import Form from './Form';
import Card from '../../ui/Card';
import Card from '../../../ui/Card';
class Upstream extends Component {
handleSubmit = (values) => {
@@ -12,7 +12,7 @@ class Upstream extends Component {
handleTest = (values) => {
this.props.testUpstream(values);
}
};
render() {
const {
@@ -26,8 +26,8 @@ class Upstream extends Component {
return (
<Card
title={ t('upstream_dns') }
subtitle={ t('upstream_dns_hint') }
title={t('upstream_dns')}
subtitle={t('upstream_dns_hint')}
bodyType="card-body box-body--settings"
>
<div className="row">

View File

@@ -0,0 +1,79 @@
import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types';
import { withNamespaces } from 'react-i18next';
import Upstream from './Upstream';
import Access from './Access';
import Rewrites from './Rewrites';
import PageTitle from '../../ui/PageTitle';
import Loading from '../../ui/Loading';
class Dns extends Component {
componentDidMount() {
this.props.getAccessList();
this.props.getRewritesList();
}
render() {
const {
t,
dashboard,
settings,
access,
rewrites,
setAccessList,
testUpstream,
setUpstream,
getRewritesList,
addRewrite,
deleteRewrite,
toggleRewritesModal,
} = this.props;
return (
<Fragment>
<PageTitle title={t('dns_settings')} />
{(dashboard.processing || access.processing) && <Loading />}
{!dashboard.processing && !access.processing && (
<Fragment>
<Upstream
upstreamDns={dashboard.upstreamDns}
bootstrapDns={dashboard.bootstrapDns}
allServers={dashboard.allServers}
processingTestUpstream={settings.processingTestUpstream}
processingSetUpstream={settings.processingSetUpstream}
setUpstream={setUpstream}
testUpstream={testUpstream}
/>
<Access access={access} setAccessList={setAccessList} />
<Rewrites
rewrites={rewrites}
getRewritesList={getRewritesList}
addRewrite={addRewrite}
deleteRewrite={deleteRewrite}
toggleRewritesModal={toggleRewritesModal}
/>
</Fragment>
)}
</Fragment>
);
}
}
Dns.propTypes = {
dashboard: PropTypes.object.isRequired,
settings: PropTypes.object.isRequired,
setUpstream: PropTypes.func.isRequired,
testUpstream: PropTypes.func.isRequired,
getAccessList: PropTypes.func.isRequired,
setAccessList: PropTypes.func.isRequired,
access: PropTypes.object.isRequired,
rewrites: PropTypes.object.isRequired,
getRewritesList: PropTypes.func.isRequired,
addRewrite: PropTypes.func.isRequired,
deleteRewrite: PropTypes.func.isRequired,
toggleRewritesModal: PropTypes.func.isRequired,
t: PropTypes.func.isRequired,
};
export default withNamespaces()(Dns);

View File

@@ -6,7 +6,7 @@ import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import format from 'date-fns/format';
import { renderField, renderSelectField, toNumber, port, isSafePort } from '../../../helpers/form';
import { renderField, renderSelectField, toNumber, port, portTLS, isSafePort } from '../../../helpers/form';
import { EMPTY_DATE } from '../../../helpers/constants';
import i18n from '../../../i18n';
@@ -66,14 +66,15 @@ let Form = (props) => {
setTlsConfig,
} = props;
const isSavingDisabled = invalid
|| submitting
|| processingConfig
|| processingValidate
|| (isEnabled && (!privateKey || !certificateChain))
|| (privateKey && !valid_key)
|| (certificateChain && !valid_cert)
|| (privateKey && certificateChain && !valid_pair);
const isSavingDisabled =
invalid ||
submitting ||
processingConfig ||
processingValidate ||
(isEnabled && (!privateKey || !certificateChain)) ||
(privateKey && !valid_key) ||
(certificateChain && !valid_cert) ||
(privateKey && certificateChain && !valid_pair);
return (
<form onSubmit={handleSubmit}>
@@ -91,7 +92,7 @@ let Form = (props) => {
<div className="form__desc">
<Trans>encryption_enable_desc</Trans>
</div>
<hr/>
<hr />
</div>
<div className="col-12">
<label className="form__label" htmlFor="server_name">
@@ -166,7 +167,7 @@ let Form = (props) => {
type="number"
className="form-control"
placeholder={t('encryption_dot')}
validate={[port]}
validate={[portTLS]}
normalize={toNumber}
onChange={handleChange}
disabled={!isEnabled}
@@ -180,13 +181,20 @@ let Form = (props) => {
<div className="row">
<div className="col-12">
<div className="form__group form__group--settings">
<label className="form__label form__label--bold" htmlFor="certificate_chain">
<label
className="form__label form__label--bold"
htmlFor="certificate_chain"
>
<Trans>encryption_certificates</Trans>
</label>
<div className="form__desc form__desc--top">
<Trans
values={{ link: 'letsencrypt.org' }}
components={[<a href="https://letsencrypt.org/" key="0">link</a>]}
components={[
<a href="https://letsencrypt.org/" key="0">
link
</a>,
]}
>
encryption_certificates_desc
</Trans>
@@ -202,49 +210,52 @@ let Form = (props) => {
disabled={!isEnabled}
/>
<div className="form__status">
{certificateChain &&
{certificateChain && (
<Fragment>
<div className="form__label form__label--bold">
<Trans>encryption_status</Trans>:
</div>
<ul className="encryption__list">
<li className={valid_chain ? 'text-success' : 'text-danger'}>
{valid_chain ?
<li
className={valid_chain ? 'text-success' : 'text-danger'}
>
{valid_chain ? (
<Trans>encryption_chain_valid</Trans>
: <Trans>encryption_chain_invalid</Trans>
}
) : (
<Trans>encryption_chain_invalid</Trans>
)}
</li>
{valid_cert &&
{valid_cert && (
<Fragment>
{subject &&
{subject && (
<li>
<Trans>encryption_subject</Trans>:&nbsp;
{subject}
</li>
}
{issuer &&
)}
{issuer && (
<li>
<Trans>encryption_issuer</Trans>:&nbsp;
{issuer}
</li>
}
{not_after && not_after !== EMPTY_DATE &&
)}
{not_after && not_after !== EMPTY_DATE && (
<li>
<Trans>encryption_expire</Trans>:&nbsp;
{format(not_after, 'YYYY-MM-DD HH:mm:ss')}
</li>
}
{dns_names &&
)}
{dns_names && (
<li>
<Trans>encryption_hostnames</Trans>:&nbsp;
{dns_names}
</li>
}
)}
</Fragment>
}
)}
</ul>
</Fragment>
}
)}
</div>
</div>
</div>
@@ -266,35 +277,34 @@ let Form = (props) => {
disabled={!isEnabled}
/>
<div className="form__status">
{privateKey &&
{privateKey && (
<Fragment>
<div className="form__label form__label--bold">
<Trans>encryption_status</Trans>:
</div>
<ul className="encryption__list">
<li className={valid_key ? 'text-success' : 'text-danger'}>
{valid_key ?
{valid_key ? (
<Trans values={{ type: key_type }}>
encryption_key_valid
</Trans>
: <Trans values={{ type: key_type }}>
) : (
<Trans values={{ type: key_type }}>
encryption_key_invalid
</Trans>
}
)}
</li>
</ul>
</Fragment>
}
)}
</div>
</div>
</div>
{warning_validation &&
{warning_validation && (
<div className="col-12">
<p className="text-danger">
{warning_validation}
</p>
<p className="text-danger">{warning_validation}</p>
</div>
}
)}
</div>
<div className="btn-list mt-2">

View File

@@ -6,11 +6,15 @@ import debounce from 'lodash/debounce';
import { DEBOUNCE_TIMEOUT } from '../../../helpers/constants';
import Form from './Form';
import Card from '../../ui/Card';
import PageTitle from '../../ui/PageTitle';
import Loading from '../../ui/Loading';
class Encryption extends Component {
componentDidMount() {
if (this.props.encryption.enabled) {
this.props.validateTlsConfig(this.props.encryption);
const { validateTlsConfig, encryption } = this.props;
if (encryption.enabled) {
validateTlsConfig(encryption);
}
}
@@ -36,7 +40,9 @@ class Encryption extends Component {
return (
<div className="encryption">
{encryption &&
<PageTitle title={t('encryption_settings')} />
{encryption.processing && <Loading />}
{!encryption.processing && (
<Card
title={t('encryption_title')}
subtitle={t('encryption_desc')}
@@ -58,7 +64,7 @@ class Encryption extends Component {
{...this.props.encryption}
/>
</Card>
}
)}
</div>
);
}

View File

@@ -0,0 +1,90 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Field, reduxForm } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { toggleAllServices } from '../../../helpers/helpers';
import { renderServiceField } from '../../../helpers/form';
import { SERVICES } from '../../../helpers/constants';
const Form = (props) => {
const {
handleSubmit,
change,
pristine,
submitting,
processing,
processingSet,
} = props;
return (
<form onSubmit={handleSubmit}>
<div className="form__group">
<div className="row mb-4">
<div className="col-6">
<button
type="button"
className="btn btn-secondary btn-block"
disabled={processing || processingSet}
onClick={() => toggleAllServices(SERVICES, change, true)}
>
<Trans>block_all</Trans>
</button>
</div>
<div className="col-6">
<button
type="button"
className="btn btn-secondary btn-block"
disabled={processing || processingSet}
onClick={() => toggleAllServices(SERVICES, change, false)}
>
<Trans>unblock_all</Trans>
</button>
</div>
</div>
<div className="services">
{SERVICES.map(service => (
<Field
key={service.id}
icon={`service_${service.id}`}
name={`blocked_services.${service.id}`}
type="checkbox"
component={renderServiceField}
placeholder={service.name}
disabled={processing || processingSet}
/>
))}
</div>
</div>
<div className="btn-list">
<button
type="submit"
className="btn btn-success btn-standard btn-large"
disabled={submitting || pristine || processing || processingSet}
>
<Trans>save_btn</Trans>
</button>
</div>
</form>
);
};
Form.propTypes = {
pristine: PropTypes.bool.isRequired,
handleSubmit: PropTypes.func.isRequired,
change: PropTypes.func.isRequired,
submitting: PropTypes.bool.isRequired,
processing: PropTypes.bool.isRequired,
processingSet: PropTypes.bool.isRequired,
t: PropTypes.func.isRequired,
};
export default flow([
withNamespaces(),
reduxForm({
form: 'servicesForm',
enableReinitialize: true,
}),
])(Form);

View File

@@ -0,0 +1,69 @@
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import { withNamespaces } from 'react-i18next';
import Form from './Form';
import Card from '../../ui/Card';
class Services extends Component {
handleSubmit = (values) => {
let config = values;
if (values && values.blocked_services) {
const blocked_services = Object
.keys(values.blocked_services)
.filter(service => values.blocked_services[service]);
config = blocked_services;
}
this.props.setBlockedServices(config);
};
getInitialDataForServices = (initial) => {
if (initial) {
const blocked = {};
initial.forEach((service) => {
blocked[service] = true;
});
return {
blocked_services: blocked,
};
}
return initial;
};
render() {
const { services, t } = this.props;
const initialData = this.getInitialDataForServices(services.list);
return (
<Card
title={t('blocked_services')}
subtitle={t('Allows to quickly block popular sites.')}
bodyType="card-body box-body--settings"
>
<div className="form">
<Form
initialValues={{ ...initialData }}
processing={services.processing}
processingSet={services.processingSet}
onSubmit={this.handleSubmit}
/>
</div>
</Card>
);
}
}
Services.propTypes = {
t: PropTypes.func.isRequired,
services: PropTypes.object.isRequired,
setBlockedServices: PropTypes.func.isRequired,
};
export default withNamespaces()(Services);

View File

@@ -11,11 +11,20 @@
margin-bottom: 20px;
}
.form__inline {
display: flex;
justify-content: flex-start;
}
.btn-standard {
padding-left: 20px;
padding-right: 20px;
}
.btn-large {
min-width: 150px;
}
.form-control--textarea {
min-height: 110px;
}
@@ -63,6 +72,10 @@
font-weight: 700;
}
.form__label--with-desc {
margin-bottom: 0;
}
.form__status {
margin-top: 10px;
font-size: 14px;
@@ -76,3 +89,18 @@
.encryption__list li {
list-style: inside;
}
.btn-icon {
display: inline-flex;
align-items: center;
justify-content: center;
width: 30px;
height: 30px;
}
.btn-icon-sm {
width: 23px;
height: 23px;
min-width: 23px;
padding: 5px;
}

View File

@@ -1,13 +1,13 @@
import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types';
import { withNamespaces, Trans } from 'react-i18next';
import Upstream from './Upstream';
import Dhcp from './Dhcp';
import Encryption from './Encryption';
import Services from './Services';
import Checkbox from '../ui/Checkbox';
import Loading from '../ui/Loading';
import PageTitle from '../ui/PageTitle';
import Card from '../ui/Card';
import './Settings.css';
class Settings extends Component {
@@ -36,9 +36,7 @@ class Settings extends Component {
componentDidMount() {
this.props.initSettings(this.settings);
this.props.getDhcpStatus();
this.props.getDhcpInterfaces();
this.props.getTlsStatus();
this.props.getBlockedServices();
}
renderSettings = (settings) => {
@@ -46,58 +44,49 @@ class Settings extends Component {
return Object.keys(settings).map((key) => {
const setting = settings[key];
const { enabled } = setting;
return (<Checkbox
key={key}
{...settings[key]}
handleChange={() => this.props.toggleSetting(key, enabled)}
/>);
return (
<Checkbox
key={key}
{...settings[key]}
handleChange={() => this.props.toggleSetting(key, enabled)}
/>
);
});
}
return (
<div><Trans>no_settings</Trans></div>
<div>
<Trans>no_settings</Trans>
</div>
);
}
};
render() {
const { settings, dashboard, t } = this.props;
const {
settings, services, setBlockedServices, t,
} = this.props;
return (
<Fragment>
<PageTitle title={ t('settings') } />
<PageTitle title={t('general_settings')} />
{settings.processing && <Loading />}
{!settings.processing &&
{!settings.processing && (
<div className="content">
<div className="row">
<div className="col-md-12">
<Card title={ t('general_settings') } bodyType="card-body box-body--settings">
<Card bodyType="card-body box-body--settings">
<div className="form">
{this.renderSettings(settings.settingsList)}
</div>
</Card>
<Upstream
upstreamDns={dashboard.upstreamDns}
bootstrapDns={dashboard.bootstrapDns}
allServers={dashboard.allServers}
setUpstream={this.props.setUpstream}
testUpstream={this.props.testUpstream}
processingTestUpstream={settings.processingTestUpstream}
processingSetUpstream={settings.processingSetUpstream}
/>
<Encryption
encryption={this.props.encryption}
setTlsConfig={this.props.setTlsConfig}
validateTlsConfig={this.props.validateTlsConfig}
/>
<Dhcp
dhcp={this.props.dhcp}
toggleDhcp={this.props.toggleDhcp}
getDhcpStatus={this.props.getDhcpStatus}
findActiveDhcp={this.props.findActiveDhcp}
setDhcpConfig={this.props.setDhcpConfig}
</div>
<div className="col-md-12">
<Services
services={services}
setBlockedServices={setBlockedServices}
/>
</div>
</div>
</div>
}
)}
</Fragment>
);
}
@@ -108,8 +97,6 @@ Settings.propTypes = {
settings: PropTypes.object,
settingsList: PropTypes.object,
toggleSetting: PropTypes.func,
handleUpstreamChange: PropTypes.func,
setUpstream: PropTypes.func,
t: PropTypes.func,
};

View File

@@ -2,8 +2,6 @@ import React from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import { getDnsAddress } from '../../helpers/helpers';
import Guide from '../ui/Guide';
import Card from '../ui/Card';
import PageTitle from '../ui/PageTitle';
@@ -13,7 +11,6 @@ const SetupGuide = ({
t,
dashboard: {
dnsAddresses,
dnsPort,
},
}) => (
<div className="guide">
@@ -28,12 +25,10 @@ const SetupGuide = ({
<Trans>install_devices_address</Trans>:
</div>
<div className="mt-2 font-weight-bold">
{dnsAddresses
.map(ip => <li key={ip}>{getDnsAddress(ip, dnsPort)}</li>)
}
{dnsAddresses.map(ip => <li key={ip}>{ip}</li>)}
</div>
</div>
<Guide />
<Guide dnsAddresses={dnsAddresses} />
</Card>
</div>
);

View File

@@ -2,7 +2,7 @@
position: fixed;
right: 24px;
bottom: 24px;
z-index: 103;
z-index: 105;
width: 345px;
}
@@ -32,6 +32,12 @@
overflow: hidden;
}
.toast__content a {
font-weight: 600;
color: #fff;
text-decoration: underline;
}
.toast__dismiss {
display: block;
flex: 0 0 auto;

View File

@@ -4,7 +4,7 @@ import { Trans, withNamespaces } from 'react-i18next';
class Toast extends Component {
componentDidMount() {
const timeout = this.props.type === 'error' ? 30000 : 5000;
const timeout = this.props.type === 'success' ? 5000 : 30000;
setTimeout(() => {
this.props.removeToast(this.props.id);
@@ -15,13 +15,25 @@ class Toast extends Component {
return false;
}
showMessage(t, type, message) {
if (type === 'notice') {
return <span dangerouslySetInnerHTML={{ __html: t(message) }} />;
}
return <Trans>{message}</Trans>;
}
render() {
const {
type, id, t, message,
} = this.props;
return (
<div className={`toast toast--${this.props.type}`}>
<div className={`toast toast--${type}`}>
<p className="toast__content">
<Trans>{this.props.message}</Trans>
{this.showMessage(t, type, message)}
</p>
<button className="toast__dismiss" onClick={() => this.props.removeToast(this.props.id)}>
<button className="toast__dismiss" onClick={() => this.props.removeToast(id)}>
<svg stroke="#fff" fill="none" width="20" height="20" strokeWidth="2" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><path d="m18 6-12 12"/><path d="m6 6 12 12"/></svg>
</button>
</div>
@@ -30,6 +42,7 @@ class Toast extends Component {
}
Toast.propTypes = {
t: PropTypes.func.isRequired,
id: PropTypes.string.isRequired,
message: PropTypes.string.isRequired,
type: PropTypes.string.isRequired,

View File

@@ -33,21 +33,6 @@
text-align: center;
}
.card-refresh {
height: 26px;
width: 26px;
background-size: 14px;
background-position: center;
background-repeat: no-repeat;
background-image: url("data:image/svg+xml;base64,PHN2ZyBmaWxsPSJub25lIiBoZWlnaHQ9IjI0IiBzdHJva2U9IiM0NjdmY2YiIHN0cm9rZS1saW5lY2FwPSJyb3VuZCIgc3Ryb2tlLWxpbmVqb2luPSJyb3VuZCIgc3Ryb2tlLXdpZHRoPSIyIiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48cGF0aCBkPSJtMjMgNHY2aC02Ii8+PHBhdGggZD0ibTEgMjB2LTZoNiIvPjxwYXRoIGQ9Im0zLjUxIDlhOSA5IDAgMCAxIDE0Ljg1LTMuMzZsNC42NCA0LjM2bS0yMiA0IDQuNjQgNC4zNmE5IDkgMCAwIDAgMTQuODUtMy4zNiIvPjwvc3ZnPg==");
}
.card-refresh:hover,
.card-refresh:not(:disabled):not(.disabled):active,
.card-refresh:focus:active {
background-image: url("data:image/svg+xml;base64,PHN2ZyBmaWxsPSJub25lIiBoZWlnaHQ9IjI0IiBzdHJva2U9IiNmZmYiIHN0cm9rZS1saW5lY2FwPSJyb3VuZCIgc3Ryb2tlLWxpbmVqb2luPSJyb3VuZCIgc3Ryb2tlLXdpZHRoPSIyIiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48cGF0aCBkPSJtMjMgNHY2aC02Ii8+PHBhdGggZD0ibTEgMjB2LTZoNiIvPjxwYXRoIGQ9Im0zLjUxIDlhOSA5IDAgMCAxIDE0Ljg1LTMuMzZsNC42NCA0LjM2bS0yMiA0IDQuNjQgNC4zNmE5IDkgMCAwIDAgMTQuODUtMy4zNiIvPjwvc3ZnPg==");
}
.card-title-stats {
font-size: 13px;
color: #9aa0ac;

View File

@@ -4,7 +4,7 @@ import PropTypes from 'prop-types';
import './Card.css';
const Card = props => (
<div className={props.type ? `card ${props.type}` : 'card'}>
<div className={props.type ? `card ${props.type}` : 'card'} id={props.id ? props.id : ''}>
{props.title &&
<div className="card-header with-border">
<div className="card-inner">
@@ -30,6 +30,7 @@ const Card = props => (
);
Card.propTypes = {
id: PropTypes.string,
title: PropTypes.string,
subtitle: PropTypes.string,
bodyType: PropTypes.string,

View File

@@ -0,0 +1,8 @@
.dropdown-item.active,
.dropdown-item:active {
background-color: #66b574;
}
.dropdown-menu {
cursor: default;
}

View File

@@ -0,0 +1,89 @@
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import classnames from 'classnames';
import { withNamespaces } from 'react-i18next';
import enhanceWithClickOutside from 'react-click-outside';
import './Dropdown.css';
class Dropdown extends Component {
state = {
isOpen: false,
};
toggleDropdown = () => {
this.setState(prevState => ({ isOpen: !prevState.isOpen }));
};
hideDropdown = () => {
this.setState({ isOpen: false });
};
handleClickOutside = () => {
if (this.state.isOpen) {
this.hideDropdown();
}
};
render() {
const {
label,
controlClassName,
menuClassName,
baseClassName,
icon,
children,
} = this.props;
const { isOpen } = this.state;
const dropdownClass = classnames({
[baseClassName]: true,
show: isOpen,
});
const dropdownMenuClass = classnames({
[menuClassName]: true,
show: isOpen,
});
const ariaSettings = isOpen ? 'true' : 'false';
return (
<div className={dropdownClass}>
<a
className={controlClassName}
aria-expanded={ariaSettings}
onClick={this.toggleDropdown}
>
{icon && (
<svg className="nav-icon">
<use xlinkHref={`#${icon}`} />
</svg>
)}
{label}
</a>
<div className={dropdownMenuClass} onClick={this.hideDropdown}>
{children}
</div>
</div>
);
}
}
Dropdown.defaultProps = {
baseClassName: 'dropdown',
menuClassName: 'dropdown-menu dropdown-menu-arrow',
controlClassName: '',
};
Dropdown.propTypes = {
label: PropTypes.string.isRequired,
children: PropTypes.node.isRequired,
controlClassName: PropTypes.node.isRequired,
menuClassName: PropTypes.string.isRequired,
baseClassName: PropTypes.string.isRequired,
icon: PropTypes.string,
};
export default withNamespaces()(enhanceWithClickOutside(Dropdown));

View File

@@ -18,7 +18,7 @@ const EncryptionTopline = (props) => {
if (isExpired) {
return (
<Topline type="danger">
<Trans components={[<a href="#settings" key="0">link</a>]}>
<Trans components={[<a href="#encryption" key="0">link</a>]}>
topline_expired_certificate
</Trans>
</Topline>
@@ -26,7 +26,7 @@ const EncryptionTopline = (props) => {
} else if (isAboutExpire) {
return (
<Topline type="warning">
<Trans components={[<a href="#settings" key="0">link</a>]}>
<Trans components={[<a href="#encryption" key="0">link</a>]}>
topline_expiring_certificate
</Trans>
</Topline>

View File

@@ -1,83 +1,373 @@
import React from 'react';
import React, { Fragment } from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import Tabs from '../ui/Tabs';
import Icons from '../ui/Icons';
const Guide = () => (
<div>
<Icons />
<Tabs>
<div label="Router">
<div className="tab__title">
<Trans>install_devices_router</Trans>
const Guide = (props) => {
const { dnsAddresses } = props;
const tlsAddress = (dnsAddresses && dnsAddresses.filter(item => item.includes('tls://'))) || '';
const httpsAddress =
(dnsAddresses && dnsAddresses.filter(item => item.includes('https://'))) || '';
const showDnsPrivacyNotice = httpsAddress.length < 1 && tlsAddress.length < 1;
return (
<div>
<Icons />
<Tabs>
<div label="Router">
<div className="tab__title">
<Trans>install_devices_router</Trans>
</div>
<div className="tab__text">
<p>
<Trans>install_devices_router_desc</Trans>
</p>
<ol>
<li>
<Trans>install_devices_router_list_1</Trans>
</li>
<li>
<Trans>install_devices_router_list_2</Trans>
</li>
<li>
<Trans>install_devices_router_list_3</Trans>
</li>
</ol>
</div>
</div>
<div className="tab__text">
<p><Trans>install_devices_router_desc</Trans></p>
<ol>
<li><Trans>install_devices_router_list_1</Trans></li>
<li><Trans>install_devices_router_list_2</Trans></li>
<li><Trans>install_devices_router_list_3</Trans></li>
</ol>
<div label="Windows">
<div className="tab__title">Windows</div>
<div className="tab__text">
<ol>
<li>
<Trans>install_devices_windows_list_1</Trans>
</li>
<li>
<Trans>install_devices_windows_list_2</Trans>
</li>
<li>
<Trans>install_devices_windows_list_3</Trans>
</li>
<li>
<Trans>install_devices_windows_list_4</Trans>
</li>
<li>
<Trans>install_devices_windows_list_5</Trans>
</li>
<li>
<Trans>install_devices_windows_list_6</Trans>
</li>
</ol>
</div>
</div>
</div>
<div label="Windows">
<div className="tab__title">
Windows
<div label="macOS">
<div className="tab__title">macOS</div>
<div className="tab__text">
<ol>
<li>
<Trans>install_devices_macos_list_1</Trans>
</li>
<li>
<Trans>install_devices_macos_list_2</Trans>
</li>
<li>
<Trans>install_devices_macos_list_3</Trans>
</li>
<li>
<Trans>install_devices_macos_list_4</Trans>
</li>
</ol>
</div>
</div>
<div className="tab__text">
<ol>
<li><Trans>install_devices_windows_list_1</Trans></li>
<li><Trans>install_devices_windows_list_2</Trans></li>
<li><Trans>install_devices_windows_list_3</Trans></li>
<li><Trans>install_devices_windows_list_4</Trans></li>
<li><Trans>install_devices_windows_list_5</Trans></li>
<li><Trans>install_devices_windows_list_6</Trans></li>
</ol>
<div label="Android">
<div className="tab__title">Android</div>
<div className="tab__text">
<ol>
<li>
<Trans>install_devices_android_list_1</Trans>
</li>
<li>
<Trans>install_devices_android_list_2</Trans>
</li>
<li>
<Trans>install_devices_android_list_3</Trans>
</li>
<li>
<Trans>install_devices_android_list_4</Trans>
</li>
<li>
<Trans>install_devices_android_list_5</Trans>
</li>
</ol>
</div>
</div>
</div>
<div label="macOS">
<div className="tab__title">
macOS
<div label="iOS">
<div className="tab__title">iOS</div>
<div className="tab__text">
<ol>
<li>
<Trans>install_devices_ios_list_1</Trans>
</li>
<li>
<Trans>install_devices_ios_list_2</Trans>
</li>
<li>
<Trans>install_devices_ios_list_3</Trans>
</li>
<li>
<Trans>install_devices_ios_list_4</Trans>
</li>
</ol>
</div>
</div>
<div className="tab__text">
<ol>
<li><Trans>install_devices_macos_list_1</Trans></li>
<li><Trans>install_devices_macos_list_2</Trans></li>
<li><Trans>install_devices_macos_list_3</Trans></li>
<li><Trans>install_devices_macos_list_4</Trans></li>
</ol>
<div label="dns_privacy" title={props.t('dns_privacy')}>
<div className="tab__title">
<Trans>dns_privacy</Trans>
</div>
<div className="tab__text">
{tlsAddress && tlsAddress.length > 0 && (
<div className="tab__paragraph">
<Trans
values={{ address: tlsAddress[0] }}
components={[
<strong key="0">text</strong>,
<code key="1">text</code>,
]}
>
setup_dns_privacy_1
</Trans>
</div>
)}
{httpsAddress && httpsAddress.length > 0 && (
<div className="tab__paragraph">
<Trans
values={{ address: httpsAddress[0] }}
components={[
<strong key="0">text</strong>,
<code key="1">text</code>,
]}
>
setup_dns_privacy_2
</Trans>
</div>
)}
{showDnsPrivacyNotice && (
<div className="tab__paragraph">
<Trans
components={[
<a
href="https://github.com/AdguardTeam/AdguardHome/wiki/Encryption"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<code key="1">text</code>,
]}
>
setup_dns_notice
</Trans>
</div>
)}
{!showDnsPrivacyNotice && (
<Fragment>
<div className="tab__paragraph">
<Trans components={[<p key="0">text</p>]}>
setup_dns_privacy_3
</Trans>
</div>
<div className="tab__paragraph">
<strong>Android</strong>
<ul>
<li>
<Trans>setup_dns_privacy_android_1</Trans>
</li>
<li>
<Trans
components={[
<a
href="https://adguard.com/adguard-android/overview.html"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<code key="1">text</code>,
]}
>
setup_dns_privacy_android_2
</Trans>
</li>
<li>
<Trans
components={[
<a
href="https://getintra.org/"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<code key="1">text</code>,
]}
>
setup_dns_privacy_android_3
</Trans>
</li>
</ul>
</div>
<div className="tab__paragraph">
<strong>iOS</strong>
<ul>
<li>
<Trans
components={[
<a
href="https://itunes.apple.com/app/id1452162351"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<code key="1">text</code>,
<a
href="https://dnscrypt.info/stamps"
target="_blank"
rel="noopener noreferrer"
key="2"
>
link
</a>,
]}
>
setup_dns_privacy_ios_1
</Trans>
</li>
<li>
<Trans
components={[
<a
href="https://adguard.com/adguard-ios/overview.html"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<code key="1">text</code>,
]}
>
setup_dns_privacy_ios_2
</Trans>
</li>
</ul>
</div>
<div className="tab__paragraph">
<strong>
<Trans>setup_dns_privacy_other_title</Trans>
</strong>
<ul>
<li>
<Trans>setup_dns_privacy_other_1</Trans>
</li>
<li>
<Trans
components={[
<a
href="https://github.com/AdguardTeam/dnsproxy"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
]}
>
setup_dns_privacy_other_2
</Trans>
</li>
<li>
<Trans
components={[
<a
href="https://github.com/jedisct1/dnscrypt-proxy"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<code key="1">text</code>,
]}
>
setup_dns_privacy_other_3
</Trans>
</li>
<li>
<Trans
components={[
<a
href="https://www.mozilla.org/firefox/"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<code key="1">text</code>,
]}
>
setup_dns_privacy_other_4
</Trans>
</li>
<li>
<Trans
components={[
<a
href="https://dnscrypt.info/implementations"
target="_blank"
rel="noopener noreferrer"
key="0"
>
link
</a>,
<a
href="https://dnsprivacy.org/wiki/display/DP/DNS+Privacy+Clients"
target="_blank"
rel="noopener noreferrer"
key="1"
>
link
</a>,
]}
>
setup_dns_privacy_other_5
</Trans>
</li>
</ul>
</div>
</Fragment>
)}
</div>
</div>
</div>
<div label="Android">
<div className="tab__title">
Android
</div>
<div className="tab__text">
<ol>
<li><Trans>install_devices_android_list_1</Trans></li>
<li><Trans>install_devices_android_list_2</Trans></li>
<li><Trans>install_devices_android_list_3</Trans></li>
<li><Trans>install_devices_android_list_4</Trans></li>
<li><Trans>install_devices_android_list_5</Trans></li>
</ol>
</div>
</div>
<div label="iOS">
<div className="tab__title">
iOS
</div>
<div className="tab__text">
<ol>
<li><Trans>install_devices_ios_list_1</Trans></li>
<li><Trans>install_devices_ios_list_2</Trans></li>
<li><Trans>install_devices_ios_list_3</Trans></li>
<li><Trans>install_devices_ios_list_4</Trans></li>
</ol>
</div>
</div>
</Tabs>
</div>
);
</Tabs>
</div>
);
};
Guide.defaultProps = {
dnsAddresses: [],
};
Guide.propTypes = {
dnsAddresses: PropTypes.array,
t: PropTypes.func.isRequired,
};
export default withNamespaces()(Guide);

View File

@@ -0,0 +1,5 @@
.icons {
display: inline-block;
vertical-align: middle;
height: 100%;
}

View File

@@ -1,5 +1,7 @@
import React from 'react';
import './Icons.css';
const Icons = () => (
<svg xmlns="http://www.w3.org/2000/svg" className="hidden">
<symbol id="android" viewBox="0 0 14 16" fill="currentColor">
@@ -21,6 +23,110 @@ const Icons = () => (
<symbol id="router" viewBox="0 0 30 30" fill="currentColor">
<path d="M17.646 2.332a1 1 0 0 0-.697 1.719 6.984 6.984 0 0 1 0 9.898 1 1 0 1 0 1.414 1.414c3.507-3.506 3.507-9.22 0-12.726a1 1 0 0 0-.717-.305zm-12.662.654A1 1 0 0 0 4 4v14a2 2 0 0 0-2 2v4a2 2 0 0 0 2 2h22a2 2 0 0 0 2-2v-4a2 2 0 0 0-2-2H12V9a1 1 0 0 0-1.016-1.014A1 1 0 0 0 10 9v9H6V4a1 1 0 0 0-1.016-1.014zm9.834 2.176a1 1 0 0 0-.697 1.717 2.985 2.985 0 0 1 0 4.242 1 1 0 1 0 1.414 1.414 5.014 5.014 0 0 0 0-7.07 1 1 0 0 0-.717-.303zM5 21a1 1 0 1 1 0 2 1 1 0 0 1 0-2zm4 0a1 1 0 1 1 0 2 1 1 0 0 1 0-2z" />
</symbol>
<symbol id="edit" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M11 4H4a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2v-7"/><path d="M18.5 2.5a2.121 2.121 0 0 1 3 3L12 15l-4 1 1-4 9.5-9.5z"/>
</symbol>
<symbol id="delete" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="m3 6h2 16"/><path d="m19 6v14a2 2 0 0 1 -2 2h-10a2 2 0 0 1 -2-2v-14m3 0v-2a2 2 0 0 1 2-2h4a2 2 0 0 1 2 2v2"/><path d="m10 11v6"/><path d="m14 11v6"/>
</symbol>
<symbol id="back" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="m19 12h-14"/><path d="m12 19-7-7 7-7"/>
</symbol>
<symbol id="dashboard" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="m3 9 9-7 9 7v11a2 2 0 0 1 -2 2h-14a2 2 0 0 1 -2-2z"/><path d="m9 22v-10h6v10"/>
</symbol>
<symbol id="filters" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="m22 3h-20l8 9.46v6.54l4 2v-8.54z"/>
</symbol>
<symbol id="log" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="m14 2h-8a2 2 0 0 0 -2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2v-12z"/><path d="m14 2v6h6"/><path d="m16 13h-8"/><path d="m16 17h-8"/><path d="m10 9h-1-1"/>
</symbol>
<symbol id="setup" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<circle cx="12" cy="12" r="10"></circle><path d="M9.09 9a3 3 0 0 1 5.83 1c0 2-3 3-3 3"></path><line x1="12" y1="17" x2="12" y2="17"></line>
</symbol>
<symbol id="settings" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<circle cx="12" cy="12" r="3"/><path d="m19.4 15a1.65 1.65 0 0 0 .33 1.82l.06.06a2 2 0 0 1 0 2.83 2 2 0 0 1 -2.83 0l-.06-.06a1.65 1.65 0 0 0 -1.82-.33 1.65 1.65 0 0 0 -1 1.51v.17a2 2 0 0 1 -2 2 2 2 0 0 1 -2-2v-.09a1.65 1.65 0 0 0 -1.08-1.51 1.65 1.65 0 0 0 -1.82.33l-.06.06a2 2 0 0 1 -2.83 0 2 2 0 0 1 0-2.83l.06-.06a1.65 1.65 0 0 0 .33-1.82 1.65 1.65 0 0 0 -1.51-1h-.17a2 2 0 0 1 -2-2 2 2 0 0 1 2-2h.09a1.65 1.65 0 0 0 1.51-1.08 1.65 1.65 0 0 0 -.33-1.82l-.06-.06a2 2 0 0 1 0-2.83 2 2 0 0 1 2.83 0l.06.06a1.65 1.65 0 0 0 1.82.33h.08a1.65 1.65 0 0 0 1-1.51v-.17a2 2 0 0 1 2-2 2 2 0 0 1 2 2v.09a1.65 1.65 0 0 0 1 1.51 1.65 1.65 0 0 0 1.82-.33l.06-.06a2 2 0 0 1 2.83 0 2 2 0 0 1 0 2.83l-.06.06a1.65 1.65 0 0 0 -.33 1.82v.08a1.65 1.65 0 0 0 1.51 1h.17a2 2 0 0 1 2 2 2 2 0 0 1 -2 2h-.09a1.65 1.65 0 0 0 -1.51 1z"/>
</symbol>
<symbol id="refresh" viewBox="0 0 24 24" stroke="currentColor" fill="none" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M23 4v6h-6M1 20v-6h6"/><path d="M3.51 9a9 9 0 0 1 14.85-3.36L23 10M1 14l4.64 4.36A9 9 0 0 0 20.49 15"/>
</symbol>
<symbol id="dns_privacy" viewBox="0 0 30 30" stroke="none" fill="currentColor" strokeLinecap="round" strokeLinejoin="round">
<path d="M15 3C10.57 3 6.701 5.419 4.623 9h2.39a10.063 10.063 0 0 1 4.05-3.19c-.524.89-.961 1.973-1.3 3.19h2.108c.79-2.459 1.998-4 3.129-4s2.339 1.541 3.129 4h2.107c-.338-1.217-.774-2.3-1.299-3.19A10.062 10.062 0 0 1 22.989 9h2.389C23.298 5.419 19.43 3 15 3zm7.035 9.129c-1.372 0-2.264.73-2.264 1.842 0 .896.538 1.463 1.579 1.66l.75.15c.65.13.898.3.898.615 0 .375-.37.635-.91.635-.6 0-1.014-.265-1.049-.68h-1.38c.023 1.097.93 1.776 2.37 1.776 1.491 0 2.399-.717 2.399-1.904 0-.903-.504-1.412-1.63-1.63l-.734-.142c-.6-.118-.851-.3-.851-.611 0-.378.336-.62.844-.62.509 0 .891.28.923.682h1.336c-.024-1.053-.948-1.773-2.28-1.773zm-16.185.148v5.696h2.39c1.712 0 2.662-1.033 2.662-2.903 0-1.779-.966-2.793-2.662-2.793H5.85zm6.933.004v5.692h1.373v-3.235h.076l2.377 3.235h1.149V12.28h-1.373v3.203h-.076l-2.372-3.203h-1.154zm-5.486 1.16h.682c.912 0 1.449.596 1.449 1.657 0 1.128-.51 1.713-1.45 1.713h-.681v-3.37zM4.623 21C6.701 24.581 10.57 27 15 27c4.43 0 8.299-2.419 10.377-6h-2.389a10.063 10.063 0 0 1-4.049 3.19c.524-.89.96-1.973 1.297-3.19H18.13c-.79 2.459-1.996 4-3.127 4-1.131 0-2.339-1.541-3.129-4h-2.11c.339 1.217.776 2.3 1.3 3.19A10.056 10.056 0 0 1 7.013 21h-2.39z"></path>
</symbol>
<symbol id="service_youtube" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M19.695 4.04S15.348 3.2 12 3.2s-7.695.84-7.695.84L1.602 7.2v9.6l2.703 3.16s4.347.84 7.695.84 7.695-.84 7.695-.84l2.703-3.16V12 7.2zM9.602 15.68V8.32L16 12zm0 0"/><path d="M19.2 4a3.198 3.198 0 1 0 0 6.398c1.769 0 3.198-1.43 3.198-3.199C22.398 5.434 20.968 4 19.2 4zm0 9.602a3.198 3.198 0 1 0 0 6.398c1.769 0 3.198-1.434 3.198-3.2 0-1.769-1.43-3.198-3.199-3.198zM1.601 7.199c0 1.77 1.43 3.2 3.199 3.2 1.765 0 2.398-1.43 2.398-3.2C7.2 5.434 6.566 4 4.801 4 3.03 4 1.6 5.434 1.6 7.2zM4.8 13.602c-1.77 0-3.2 1.43-3.2 3.199A3.198 3.198 0 1 0 8 16.8c0-1.77-1.434-3.2-3.2-3.2zm0 0" />
</symbol>
<symbol id="service_discord" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M20.098 5.559C18.156 4 15.09 3.734 14.96 3.723a.493.493 0 0 0-.484.285c-.004.008-.172.504-.34.984 2.254.395 3.785 1.27 3.867 1.317a.8.8 0 1 1-.805 1.382C17.176 7.68 14.93 6.398 12 6.398c-2.93 0-5.176 1.282-5.2 1.293a.8.8 0 0 1-.805-1.383c.083-.046 1.622-.925 3.88-1.32-.172-.484-.348-.972-.352-.98a.487.487 0 0 0-.484-.285c-.129.011-3.195.273-5.16 1.855C2.852 6.528.8 12.074.8 16.871c0 .082.02.164.062.238 1.418 2.489 5.282 3.141 6.16 3.168h.016c.156 0 .3-.074.395-.199l.949-1.289c-2.086-.504-3.192-1.293-3.258-1.344a.799.799 0 0 1-.168-1.117.794.794 0 0 1 1.113-.172c.032.016 2.067 1.446 5.93 1.446 3.879 0 5.91-1.434 5.93-1.45a.8.8 0 0 1 .945 1.293c-.066.047-1.164.836-3.246 1.34l.937 1.293c.094.125.239.2.395.2h.016c.882-.028 4.742-.68 6.16-3.169a.477.477 0 0 0 .062-.242c0-4.793-2.05-10.34-3.101-11.308zM8.8 15.199c-.887 0-1.602-.894-1.602-2 0-1.105.715-2 1.602-2 .883 0 1.597.895 1.597 2 0 1.106-.714 2-1.597 2zm6.398 0c-.883 0-1.597-.894-1.597-2 0-1.105.714-2 1.597-2 .887 0 1.602.895 1.602 2 0 1.106-.715 2-1.602 2zm0 0"/>
</symbol>
<symbol id="service_twitch" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M4.8 3.2L3.2 6.397V19.2h4v2.403h3.198l2.403-2.403H16l4.8-4.8v-11.2zm14.4 10.402L16.8 16H12l-2.398 2.398V16H6.398V4.8H19.2zm0 0" /><path d="M15.2 12.8h-1.598V7.2h1.597zm-3.2 0h-1.602V7.2H12zm0 0" />
</symbol>
<symbol id="service_messenger" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M5.602 22.398L10.398 20l-4.796-2.398zm0 0" /><path d="M12 2.398c-5.3 0-9.602 4.122-9.602 9.204C2.398 16.68 6.7 20.8 12 20.8c5.3 0 9.602-4.121 9.602-9.2 0-5.081-4.301-9.203-9.602-9.203zm.91 11.844l-2.305-2.48-4.328 2.422 4.813-5.098 2.36 2.363 4.218-2.363zm0 0" />
</symbol>
<symbol id="service_snapchat" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M12.176 4c.715 0 3.136.191 4.277 2.668.383.828.285 2.273.211 3.437l-.004.051c-.008.164-.02.32-.027.469.015.02.164.156.492.168.25-.012.54-.086.855-.23a.784.784 0 0 1 .57.008h.005c.254.09.422.261.425.44.004.173-.128.43-.789.68a2.694 2.694 0 0 1-.25.082c-.375.118-.945.293-1.117.692-.097.215-.066.48.09.785 0 .004.004.008.004.012.047.105 1.187 2.62 3.73 3.027.094.016.16.094.153.188a.24.24 0 0 1-.024.101c-.105.238-.578.574-2.234.824-.133.02-.188.188-.266.547-.03.13-.058.258-.101.39-.035.118-.11.173-.235.173h-.02a2.34 2.34 0 0 1-.37-.043 4.986 4.986 0 0 0-.996-.102c-.23 0-.473.02-.715.059-.496.078-.918.367-1.363.672-.653.445-1.32.902-2.364.902-.047 0-.09 0-.136-.004-.028.004-.055.004-.086.004-1.043 0-1.711-.457-2.36-.902-.445-.305-.867-.594-1.363-.672a4.533 4.533 0 0 0-.719-.059c-.418 0-.75.063-.992.106a2.02 2.02 0 0 1-.371.054c-.102 0-.211-.023-.258-.18-.039-.136-.07-.269-.101-.394-.075-.328-.125-.531-.266-.55-1.656-.247-2.129-.587-2.234-.825-.012-.035-.024-.066-.024-.101a.182.182 0 0 1 .156-.188c2.54-.406 3.68-2.922 3.727-3.031.004 0 .004-.004.004-.008.156-.305.187-.57.094-.79-.176-.398-.747-.57-1.122-.687a3.147 3.147 0 0 1-.25-.082c-.75-.289-.812-.582-.785-.734.051-.254.407-.434.692-.434a.49.49 0 0 1 .207.04c.336.152.64.23.906.23.363 0 .52-.148.54-.168-.009-.164-.02-.34-.032-.52-.074-1.164-.168-2.609.21-3.433 1.138-2.477 3.555-2.668 4.27-2.668L12.133 4h.043m0-1.602h-.043l-.313.008v-.004c-.953 0-4.187.262-5.722 3.598-.387.844-.45 1.887-.422 2.922-.922.02-2 .625-2.215 1.726-.082.407-.184 1.786 1.781 2.54.012.003.02.007.031.011-.39.559-1.113 1.34-2.168 1.508-.902.14-1.55.941-1.5 1.86.016.226.067.44.153.64.41.938 1.406 1.363 2.543 1.613a1.83 1.83 0 0 0 1.785 1.305c.246 0 .465-.043.66-.078a3.44 3.44 0 0 1 .703-.082c.149 0 .305.012.465.039.14.023.457.238.711.41.73.5 1.727 1.184 3.266 1.184h.101c.04 0 .078.004.121.004 1.532 0 2.528-.68 3.258-1.176.281-.192.582-.399.723-.422.156-.024.312-.04.46-.04.259 0 .458.032.696.075.266.05.477.074.668.074.852 0 1.543-.508 1.785-1.293 1.137-.25 2.129-.672 2.535-1.593.094-.22.149-.43.16-.649a1.783 1.783 0 0 0-1.496-1.871c-1.054-.168-1.78-.95-2.172-1.508l.036-.011c1.601-.618 1.824-1.645 1.816-2.204-.02-.855-.594-1.601-1.477-1.918a2.37 2.37 0 0 0-.777-.156c.027-1.015-.039-2.078-.422-2.914-1.539-3.336-4.773-3.598-5.73-3.598zm0 0" />
</symbol>
<symbol id="service_twitter" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M22.398 5.55a8.583 8.583 0 0 1-2.449.673 4.252 4.252 0 0 0 1.875-2.364 8.66 8.66 0 0 1-2.71 1.04A4.251 4.251 0 0 0 16 3.546a4.27 4.27 0 0 0-4.266 4.27c0 .335.036.66.11.972a12.126 12.126 0 0 1-8.797-4.46 4.259 4.259 0 0 0-.578 2.148c0 1.48.754 2.785 1.898 3.55a4.273 4.273 0 0 1-1.933-.535v.055a4.27 4.27 0 0 0 3.425 4.183c-.359.098-.734.149-1.125.149-.273 0-.543-.027-.804-.074a4.276 4.276 0 0 0 3.988 2.965 8.562 8.562 0 0 1-5.3 1.824 8.82 8.82 0 0 1-1.02-.059 12.088 12.088 0 0 0 6.543 1.918c7.851 0 12.14-6.504 12.14-12.144 0-.184-.004-.368-.011-.551a8.599 8.599 0 0 0 2.128-2.207zm0 0" />
</symbol>
<symbol id="service_instagram" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M12 8.8A3.2 3.2 0 0 0 8.8 12a3.2 3.2 0 0 0 3.2 3.2 3.2 3.2 0 0 0 3.2-3.2A3.2 3.2 0 0 0 12 8.8zm0 0" /><path d="M16 2.398H8A5.609 5.609 0 0 0 2.398 8v8A5.609 5.609 0 0 0 8 21.602h8A5.609 5.609 0 0 0 21.602 16V8A5.609 5.609 0 0 0 16 2.398zm-4 14.403A4.805 4.805 0 0 1 7.2 12c0-2.648 2.152-4.8 4.8-4.8 2.648 0 4.8 2.152 4.8 4.8 0 2.648-2.152 4.8-4.8 4.8zm5.602-9.602a.799.799 0 1 1 0 0zm0 0" />
</symbol>
<symbol id="service_whatsapp" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M3.836 16.668l-1.352 4.934 5.047-1.329zm0 0" /><path d="M12 2.398C6.7 2.398 2.398 6.7 2.398 12c0 5.3 4.301 9.602 9.602 9.602 5.3 0 9.602-4.301 9.602-9.602 0-5.3-4.301-9.602-9.602-9.602zm4.738 12.915c-.195.554-1.168 1.093-1.601 1.128-.442.043-.852.2-2.856-.59-2.418-.953-3.945-3.433-4.062-3.593-.121-.156-.969-1.285-.969-2.453 0-1.172.613-1.746.828-1.985a.875.875 0 0 1 .637-.297c.156 0 .316 0 .453.004.172.004.36.016.535.41.215.47.676 1.645.735 1.766.058.117.101.262.019.418-.078.156-.121.254-.234.399-.121.136-.25.308-.36.41-.117.12-.242.25-.101.488.136.238.613 1.016 1.32 1.645.906.812 1.672 1.062 1.91 1.18.238.12.38.1.516-.06.14-.156.594-.69.754-.93.156-.237.316-.198.531-.12.219.078 1.39.656 1.629.773.238.121.394.18.453.278.063.097.063.574-.137 1.129zm0 0" />
</symbol>
<symbol id="service_facebook" viewBox="0 0 27 27" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M12 0C5.371 0 0 5.371 0 12c0 6.016 4.434 10.984 10.207 11.852V15.18H7.238v-3.153h2.969V9.926c0-3.473 1.691-5 4.578-5 1.387 0 2.117.105 2.461.148v2.754h-1.969c-1.226 0-1.652 1.164-1.652 2.473v1.726h3.594l-.489 3.153h-3.105v8.699C19.48 23.082 24 18.074 24 12c0-6.629-5.371-12-12-12zm0 0" />
</symbol>
<symbol id="service_netflix" viewBox="0 0 450 600" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M83.5 72.814V512l17.432-2.865a955.35 955.35 0 0 1 88.604-10.312l13.965-.966V338.206L83.5 72.814z"/><path d="M308.5 0L308.5 172.328 428.5 438.914 428.5 0z"/><path d="M308.5 245.415l-10.87-24.149L198.03 0H83.501l168.12 371.813 57.024 126.112 8.852.566a955.65 955.65 0 0 1 93.572 10.644L428.5 512l-120-266.585z"/>
</symbol>
<symbol id="service_vk" viewBox="0 0 24 24" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M12 .96C5.914.96.96 5.915.96 12c0 6.086 4.954 11.04 11.04 11.04 6.086 0 11.04-4.954 11.04-11.04C23.04 5.914 18.085.96 12 .96zm4.785 13.216c1.074.953 1.3 1.293 1.336 1.351.445.707-.492.793-.492.793h-1.98s-.481.004-.891-.27c-.672-.437-1.375-1.288-1.867-1.14-.414.125-.41.684-.41 1.16 0 .172-.149.25-.481.25h-.617c-1.086 0-2.262-.363-3.434-1.59-1.656-1.734-3.113-5.222-3.113-5.222s-.086-.176.008-.281c.105-.122.394-.106.394-.106h1.918s.18.031.309.125c.11.074.168.219.168.219s.32 1.062.734 1.742c.801 1.32 1.172 1.355 1.445 1.215.399-.207.266-1.617.266-1.617s.02-.602-.187-.871c-.16-.211-.465-.32-.598-.336-.11-.016.07-.203.3-.313.31-.137.727-.172 1.446-.164.563.004.723.04.941.09.665.152.5.555.5 1.969 0 .453-.062 1.09.278 1.3.148.09.652.204 1.55-1.257.43-.692.77-1.84.77-1.84s.067-.125.176-.188c.113-.066.11-.062.262-.062.152 0 1.683-.012 2.02-.012.335 0 .651-.004.702.191.078.282-.246 1.25-1.07 2.305-1.355 1.723-1.504 1.563-.383 2.559zm0 0" />
</symbol>
<symbol id="service_ok" viewBox="0 0 96 96" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M50 28c-3.313 0-6 2.688-6 6 0 3.313 2.688 6 6 6 3.313 0 6-2.688 6-6 0-3.313-2.688-6-6-6zm0 0" /><path d="M50 4C24.637 4 4 24.637 4 50s20.637 46 46 46 46-20.637 46-46S75.363 4 50 4zm0 16c7.73 0 14 6.27 14 14s-6.27 14-14 14-14-6.27-14-14 6.27-14 14-14zm14.828 49.172A3.999 3.999 0 0 1 62 76a3.987 3.987 0 0 1-2.828-1.172L50 65.656l-9.172 9.172a3.999 3.999 0 0 1-5.656 0 3.999 3.999 0 0 1 0-5.656l6.43-6.43c-1.836-.539-3.618-1.207-5.29-2.066A4.302 4.302 0 0 1 34 56.859c0-2.98 3.172-4.761 5.809-3.375A21.767 21.767 0 0 0 50 56c3.684 0 7.148-.91 10.191-2.516C62.828 52.098 66 53.88 66 56.86c0 1.602-.89 3.078-2.313 3.813-1.671.863-3.453 1.531-5.289 2.07zm0 0" />
</symbol>
<symbol id="service_steam" viewBox="0 0 22 22" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M14.398 7.2a2.4 2.4 0 1 0 .003 4.799 2.4 2.4 0 0 0-.003-4.8zm0 0" fill="none" strokeWidth="1.6" stroke="currentColor" strokeMiterlimit="10"/><path d="M8 14c-.629 0-1.18.297-1.547.75l1.758.48c.426.114.68.555.562.98a.804.804 0 0 1-.984.563l-1.762-.48A1.998 1.998 0 0 0 10 16c0-1.105-.895-2-2-2zm0 0" /><path d="M19.2 3.2H4.8c-.886 0-1.6.714-1.6 1.6v9.063l2.027.551a3.213 3.213 0 0 1 2.289-1.566l2.136-2.567a4.799 4.799 0 1 1 4.066 4.066l-2.566 2.137A3.195 3.195 0 0 1 8 19.2 3.2 3.2 0 0 1 4.8 16c0-.016.005-.027.005-.043l-1.606-.437v3.68c0 .886.715 1.6 1.602 1.6h14.398c.887 0 1.602-.714 1.602-1.6V4.8c0-.886-.715-1.6-1.602-1.6zm0 0" />
</symbol>
<symbol id="service_skype" viewBox="0 0 26 26" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M23.363 14.387c.153-.739.23-1.5.23-2.266C23.594 5.883 18.45.805 12.122.805c-.594 0-1.191.047-1.781.136A6.891 6.891 0 0 0 6.852 0C3.074 0 0 3.035 0 6.762c0 1.144.293 2.27.852 3.265-.133.688-.2 1.391-.2 2.094 0 6.238 5.149 11.316 11.47 11.316.648 0 1.3-.054 1.94-.164.95.477 2.012.727 3.086.727C20.926 24 24 20.969 24 17.238c0-1.004-.215-1.96-.637-2.851zM17.758 17.3c-.508.707-1.258 1.27-2.23 1.668-.966.394-2.122.593-3.434.593-1.578 0-2.903-.273-3.934-.812a5.074 5.074 0 0 1-1.808-1.582c-.47-.664-.707-1.324-.707-1.961 0-.395.156-.738.457-1.023.304-.278.687-.418 1.148-.418.379 0 .703.109.969.332.254.21.469.523.644.93.192.437.407.808.633 1.1.211.282.524.52.918.704.399.188.938.281 1.598.281.91 0 1.652-.191 2.215-.57.546-.367.812-.813.812-1.352 0-.43-.14-.765-.422-1.027-.3-.277-.699-.492-1.176-.637-.5-.152-1.18-.32-2.015-.496-1.14-.238-2.11-.523-2.88-.847-.788-.332-1.425-.79-1.89-1.364-.472-.582-.71-1.312-.71-2.172 0-.816.253-1.554.75-2.191.488-.633 1.206-1.125 2.132-1.46.91-.333 1.996-.5 3.223-.5.98 0 1.844.108 2.566.331.723.223 1.336.524 1.813.89.484.376.843.774 1.07 1.188.227.418.344.832.344 1.235 0 .386-.153.738-.453 1.046-.297.31-.68.465-1.125.465-.41 0-.727-.097-.95-.289-.207-.18-.418-.46-.656-.863-.273-.516-.605-.918-.984-1.203-.371-.277-.989-.418-1.836-.418-.79 0-1.43.156-1.902.465-.461.293-.684.633-.684 1.039 0 .246.07.449.219.629.156.187.379.351.656.488.289.145.586.258.883.34.308.082.82.207 1.523.367.887.191 1.707.398 2.43.625.73.234 1.363.516 1.879.848.527.34.941.773 1.238 1.293.297.52.445 1.16.445 1.91a4.07 4.07 0 0 1-.77 2.418zm0 0"/>
</symbol>
<symbol id="service_mail_ru" viewBox="0 0 512 512" fill="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<path d="M256 141.176c-63.306 0-114.809 51.503-114.809 114.809S192.694 370.795 256 370.795s114.809-51.503 114.809-114.809S319.306 141.176 256 141.176zm0 188.254c-40.498 0-73.445-32.947-73.445-73.445 0-40.498 32.947-73.445 73.445-73.445 40.499 0 73.445 32.947 73.445 73.445 0 40.498-32.946 73.445-73.445 73.445z"/><path d="M437.008 74.97C388.656 26.623 324.375 0 256 0h-.017C187.603.004 123.318 26.637 74.97 74.992 26.62 123.347-.005 187.637 0 256.017c.004 68.379 26.637 132.666 74.992 181.014C123.344 485.377 187.625 512.001 256 512h.017c55.945-.004 111.216-18.738 155.631-52.752 9.07-6.945 10.792-19.927 3.846-28.995-6.945-9.069-19.926-10.794-28.995-3.846-37.24 28.518-83.58 44.224-130.486 44.228h-.014c-57.324 0-111.224-22.324-151.761-62.856-40.542-40.536-62.871-94.435-62.875-151.766-.006-118.35 96.273-214.641 214.623-214.649H256c118.34 0 214.628 96.279 214.636 214.622v23.532c0 27.523-22.39 49.913-49.913 49.913-27.523 0-49.913-22.391-49.913-49.913v-23.532c0-11.422-9.259-20.682-20.682-20.682s-20.682 9.26-20.682 20.682v23.532c0 50.33 40.947 91.278 91.278 91.278S512 329.848 512 279.518v-23.534c-.005-68.38-26.638-132.666-74.992-181.014z"/>
</symbol>
<symbol id="question" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="2">
<circle cx="12" cy="12" r="10" /><path d="M9.09 9a3 3 0 0 1 5.83 1c0 2-3 3-3 3" /><line x1="12" y1="17" x2="12" y2="17" />
</symbol>
</svg>
);

View File

@@ -5,7 +5,7 @@
overflow-x: hidden;
overflow-y: auto;
background-color: rgba(0, 0, 0, 0.5);
z-index: 1;
z-index: 104;
}
.ReactModal__Overlay--after-open {
@@ -38,3 +38,9 @@
border: none;
background-color: transparent;
}
@media (min-width: 576px) {
.modal-dialog--clients {
max-width: 650px;
}
}

View File

@@ -0,0 +1,40 @@
.overlay {
display: none;
position: fixed;
top: 0;
left: 0;
z-index: 110;
width: 100%;
height: 100%;
flex-direction: column;
align-items: center;
justify-content: center;
padding: 20px;
font-size: 28px;
font-weight: 600;
text-align: center;
background-color: rgba(255, 255, 255, 0.8);
}
.overlay--visible {
display: flex;
}
.overlay__loading {
width: 40px;
height: 40px;
margin-bottom: 20px;
background-image: url("data:image/svg+xml;charset=utf-8,%3Csvg%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%20viewBox%3D%220%200%2047.6%2047.6%22%20height%3D%22100%25%22%20width%3D%22100%25%22%3E%3Cpath%20opacity%3D%22.235%22%20fill%3D%22%23979797%22%20d%3D%22M44.4%2011.9l-5.2%203c1.5%202.6%202.4%205.6%202.4%208.9%200%209.8-8%2017.8-17.8%2017.8-6.6%200-12.3-3.6-15.4-8.9l-5.2%203C7.3%2042.8%2015%2047.6%2023.8%2047.6c13.1%200%2023.8-10.7%2023.8-23.8%200-4.3-1.2-8.4-3.2-11.9z%22%2F%3E%3Cpath%20fill%3D%22%2366b574%22%20d%3D%22M3.2%2035.7C0%2030.2-.8%2023.8.8%2017.6%202.5%2011.5%206.4%206.4%2011.9%203.2%2017.4%200%2023.8-.8%2030%20.8c6.1%201.6%2011.3%205.6%2014.4%2011.1l-5.2%203c-2.4-4.1-6.2-7.1-10.8-8.3C23.8%205.4%2019%206%2014.9%208.4s-7.1%206.2-8.3%2010.8c-1.2%204.6-.6%209.4%201.8%2013.5l-5.2%203z%22%2F%3E%3C%2Fsvg%3E");
will-change: transform;
animation: clockwise 2s linear infinite;
}
@keyframes clockwise {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}

View File

@@ -109,9 +109,11 @@
width: 20px;
height: 20px;
stroke: #9aa0ac;
color: #9aa0ac;
}
.popover__icon--green {
color: #66b574;
stroke: #66b574;
}

View File

@@ -6,19 +6,36 @@ import './Popover.css';
class PopoverFilter extends Component {
render() {
const { rule, filter, service } = this.props;
if (!rule && !service) {
return '';
}
return (
<div className="popover-wrap">
<div className="popover__trigger popover__trigger--filter">
<svg className="popover__icon popover__icon--green" xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><circle cx="12" cy="12" r="10"></circle><path d="M9.09 9a3 3 0 0 1 5.83 1c0 2-3 3-3 3"></path><line x1="12" y1="17" x2="12" y2="17"></line></svg>
<svg className="popover__icon popover__icon--green">
<use xlinkHref="#question" />
</svg>
</div>
<div className="popover__body popover__body--filter">
<div className="popover__list">
<div className="popover__list-item popover__list-item--nowrap">
<Trans>rule_label</Trans>: <strong>{this.props.rule}</strong>
</div>
{this.props.filter && <div className="popover__list-item popover__list-item--nowrap">
<Trans>filter_label</Trans>: <strong>{this.props.filter}</strong>
</div>}
{rule && (
<div className="popover__list-item popover__list-item--nowrap">
<Trans>rule_label</Trans>: <strong>{rule}</strong>
</div>
)}
{filter && (
<div className="popover__list-item popover__list-item--nowrap">
<Trans>filter_label</Trans>: <strong>{filter}</strong>
</div>
)}
{service && (
<div className="popover__list-item popover__list-item--nowrap">
<Trans>blocked_service</Trans>: <strong>{service}</strong>
</div>
)}
</div>
</div>
</div>
@@ -27,8 +44,9 @@ class PopoverFilter extends Component {
}
PopoverFilter.propTypes = {
rule: PropTypes.string.isRequired,
rule: PropTypes.string,
filter: PropTypes.string,
service: PropTypes.string,
};
export default withNamespaces()(PopoverFilter);

View File

@@ -15,3 +15,7 @@
.rt-tr-group .green {
background-color: #f1faf3;
}
.rt-tr-group .blue {
background-color: #ecf7ff;
}

View File

@@ -11,6 +11,7 @@ class Tab extends Component {
const {
activeTab,
label,
title,
} = this.props;
const tabClass = classnames({
@@ -26,7 +27,7 @@ class Tab extends Component {
<svg className="tab__icon">
<use xlinkHref={`#${label.toLowerCase()}`} />
</svg>
{label}
{title || label}
</div>
);
}
@@ -36,6 +37,7 @@ Tab.propTypes = {
activeTab: PropTypes.string.isRequired,
label: PropTypes.string.isRequired,
onClick: PropTypes.func.isRequired,
title: PropTypes.string,
};
export default Tab;

View File

@@ -6,6 +6,20 @@
border-bottom: 1px solid #e8e8e8;
}
.tabs__controls--form {
justify-content: flex-start;
}
.tabs__controls--form .tab__control {
min-width: initial;
margin-right: 25px;
font-size: 14px;
}
.tabs__controls--form .tab__icon {
display: none;
}
.tab__control {
display: flex;
flex-direction: column;
@@ -49,3 +63,12 @@
.tab__text p {
margin-bottom: 5px;
}
.tab__text ul,
.tab__text ol {
padding-left: 25px;
}
.tab__paragraph {
margin-bottom: 10px;
}

View File

@@ -1,5 +1,6 @@
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import classnames from 'classnames';
import Tab from './Tab';
import './Tabs.css';
@@ -16,6 +17,7 @@ class Tabs extends Component {
render() {
const {
props: {
controlClass,
children,
},
state: {
@@ -23,16 +25,22 @@ class Tabs extends Component {
},
} = this;
const getControlClass = classnames({
tabs__controls: true,
[`tabs__controls--${controlClass}`]: controlClass,
});
return (
<div className="tabs">
<div className="tabs__controls">
<div className={getControlClass}>
{children.map((child) => {
const { label } = child.props;
const { label, title } = child.props;
return (
<Tab
key={label}
label={label}
title={title}
activeTab={activeTab}
onClick={this.onClickTabControl}
/>
@@ -53,6 +61,7 @@ class Tabs extends Component {
}
Tabs.propTypes = {
controlClass: PropTypes.string,
children: PropTypes.array.isRequired,
};

View File

@@ -0,0 +1,26 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
import classnames from 'classnames';
import './Overlay.css';
const UpdateOverlay = (props) => {
const overlayClass = classnames({
overlay: true,
'overlay--visible': props.processingUpdate,
});
return (
<div className={overlayClass}>
<div className="overlay__loading"></div>
<Trans>processing_update</Trans>
</div>
);
};
UpdateOverlay.propTypes = {
processingUpdate: PropTypes.bool,
};
export default withNamespaces()(UpdateOverlay);

View File

@@ -1,4 +1,4 @@
import React from 'react';
import React, { Fragment } from 'react';
import PropTypes from 'prop-types';
import { Trans, withNamespaces } from 'react-i18next';
@@ -6,22 +6,37 @@ import Topline from './Topline';
const UpdateTopline = props => (
<Topline type="info">
<Trans
values={{ version: props.version }}
components={[
<a href={props.url} target="_blank" rel="noopener noreferrer" key="0">
Click here
</a>,
]}
>
update_announcement
</Trans>
<Fragment>
<Trans
values={{ version: props.version }}
components={[
<a href={props.url} target="_blank" rel="noopener noreferrer" key="0">
Click here
</a>,
]}
>
update_announcement
</Trans>
{props.canAutoUpdate &&
<button
type="button"
className="btn btn-sm btn-primary ml-3"
onClick={props.getUpdate}
disabled={props.processingUpdate}
>
<Trans>update_now</Trans>
</button>
}
</Fragment>
</Topline>
);
UpdateTopline.propTypes = {
version: PropTypes.string.isRequired,
version: PropTypes.string,
url: PropTypes.string.isRequired,
canAutoUpdate: PropTypes.bool,
getUpdate: PropTypes.func,
processingUpdate: PropTypes.bool,
};
export default withNamespaces()(UpdateTopline);

View File

@@ -0,0 +1,27 @@
import { connect } from 'react-redux';
import { getClients, getTopStats } from '../actions';
import { addClient, updateClient, deleteClient, toggleClientModal } from '../actions/clients';
import Clients from '../components/Settings/Clients';
const mapStateToProps = (state) => {
const { dashboard, clients } = state;
const props = {
dashboard,
clients,
};
return props;
};
const mapDispatchToProps = {
getClients,
getTopStats,
addClient,
updateClient,
deleteClient,
toggleClientModal,
};
export default connect(
mapStateToProps,
mapDispatchToProps,
)(Clients);

View File

@@ -0,0 +1,36 @@
import { connect } from 'react-redux';
import {
toggleDhcp,
getDhcpStatus,
getDhcpInterfaces,
setDhcpConfig,
findActiveDhcp,
toggleLeaseModal,
addStaticLease,
removeStaticLease,
} from '../actions';
import Dhcp from '../components/Settings/Dhcp';
const mapStateToProps = (state) => {
const { dhcp } = state;
const props = {
dhcp,
};
return props;
};
const mapDispatchToProps = {
toggleDhcp,
getDhcpStatus,
getDhcpInterfaces,
setDhcpConfig,
findActiveDhcp,
toggleLeaseModal,
addStaticLease,
removeStaticLease,
};
export default connect(
mapStateToProps,
mapDispatchToProps,
)(Dhcp);

Some files were not shown because too many files have changed in this diff Show More