Jak ověřit stav VPN bez ping na Androidu, iOS a Windows
Ping dokazuje jen to, že jeden host odpověděl, ne že tunel běží. Zeptejte se na stav přes API Androidu, iOS a Windows a pak ověřte trasu, kterou vaše aplikace skutečně potřebuje.
Ping na 192.0.2.10 vám řekne, že jedna adresa odpověděla na ICMP echo, a to je vše. V síti bez tunelu může přesto uspět, protože adresa může ležet v lokální podsíti; se zdravým tunelem může selhat, protože server zahazuje ICMP, zatímco obsluhuje HTTPS. Kontrola, kterou váš skript potřebuje, je dotaz na stav platformy plus test trasy k cíli, který aplikace používá. Berte je jako dvě samostatná pole, nikdy jako jeden boolean.
Co odpověď na echo skutečně dokazuje
ICMP je protokol dostupnosti, který nezná rozhraní ani tunely. Když odpověď dorazí, jádro hlásí, že host odpověděl; nehlásí, která trasa nesla požadavek nebo která nesla odpověď. Filtrování dělá signál ještě zašuměnějším, protože firewall, který blokuje echo požadavky, nic neříká o portech za sebou. A profil s rozděleným tunelem může testovanou adresu záměrně vyloučit, zatímco všechny ostatní cíle fungují.
Co skutečně chcete vědět, je, zda je konkrétní služba použitelná po cestě, kterou aplikace jde. Vyberte hostitele a port, které aplikace volá, a pak vyžadujte odpověď na aplikační vrstvě.
Dostupnost a stav tunelu jsou různé skutečnosti a kterákoli z nich může být pravdivá, zatímco druhá ne. Když je držíte odděleně, víte, čí je selhání. Když je slijete do jedné kontroly, vznikne tiket, který nikdo nedokáže nasměrovat.
Ptejte se Androidu na transport, ne na ping
Android odpovídá na otázku stavu přímo přes ConnectivityManager. Schopnosti aktivní sítě nesou příznak VPN transportu, který se nastaví, když provoz jde přes rozhraní VPN. Volání je lokální, levné a nezávislé na tom, zda nějaký vzdálený host odpovídá.
Tato verze v Javě vrací false místo vyhození výjimky, když není aktivní síť. Protože čte aktivní síť, odráží profil, který si uživatel zvolil v Nastavení.
ConnectivityManager cm = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE);
NetworkCapabilities caps = cm.getNetworkCapabilities(cm.getActiveNetwork());
boolean tunnel = caps != null && caps.hasTransport(NetworkCapabilities.TRANSPORT_VPN);
Pro oznámení o změnách zaregistrujte NetworkCallback místo dotazování na časovači. Nezaměňujte to s VpnService.prepare, který hlásí jen to, zda uživatel povolil VPN, ne zda packety tečou. Odvolání přichází přes VpnService.onRevoke, ale zapomenutí profilu v Nastavení nevyvolá žádné vysílání.
iOS: názvy rozhraní jsou heuristika, ne smlouva
Mnohé úryvky pro iOS zkoumají nastavení proxy, najdou slovník __SCOPED__ a hledají klíče rozhraní jako tap, tun, utun2, ppp nebo ipsec. Tento přístup je konvence pojmenování, ne dokumentovaná záruka, takže aktualizace systému, která rozhraní přejmenuje, ho může rozbít. Také má tendenci hlásit pravdu pro zastaralé záznamy, které přežijí tunel.
Když konfiguraci vlastní vaše aplikace, NEVPNManager vám dá skutečný stav. Popisuje tunel, který vaše aplikace spustila; u VPN pro jednotlivé aplikace mohou jiné aplikace zůstat zcela mimo tento tunel.
Před čtením stavu znovu načtěte předvolby, protože hodnota se mění, jak tunel vzniká a zaniká:
let manager = NEVPNManager.shared()
manager.loadFromPreferences { error in
let up = manager.connection.status == .connected
print(up)
}
Příznak stavu platformy stále nedokazuje, že provoz dosáhne protějšku. Právě tuto mezeru pokrývá test trasy, a proto jeden boolean pro podporu nestačí.
Profily Windows vystavují skutečné pole stavu
Windows sleduje profily VPN odděleně od adaptérů a Get-VpnConnection vystavuje ConnectionStatus pro každý profil, který zná. Profily vytvořené klientem Windows nebo provisioning balíčkem se zde objeví. Tento cmdlet není obecný detektor tunelů.
Čtěte pole pro pojmenovaný profil a přidejte -AllUserConnection, když profil patří všem uživatelům:
Get-VpnConnection -Name "Fabrikam" | Select-Object Name, ConnectionStatus, ServerAddress
Klienti třetích stran často zůstávají pro tento cmdlet neviditelní, i když jejich tunel běží, takže prázdný výsledek znamená neznámo, ne odpojeno. Výpisy adaptérů klamou stejně: adaptér výrobce může přetrvávat, i když je nečinný, a některé adaptéry existují jen během relace. Pro profil, který Windows vlastní, rasdial hlásí návratový kód, na který lze větvit. Všechno to popisuje lokální přesvědčení, ne dostupnost protějšku.
Stav plus trasa: kontrola ve dvou částech
Připojený profil nic neříká o tom, kam packety jdou. Rozdělený tunel může držet tunel nahoru, zatímco vylučuje cíl, na kterém vám záleží. Profily always-on zůstávají připojené k mrtvému serveru a kill switch záměrně blokuje provoz, když tunel spadne.
Testujte obě vrstvy: ověřte, že je aktivní VPN transport nebo profil, a pak že se cíl přeloží a odpovídá po této cestě. Na Linuxu se zeptejte jádra, které rozhraní by použilo:
ip route get 192.0.2.10
resolvectl query intranet.example.test
Když je klient mimo vaši kontrolu, zaznamenejte oba výsledky a nechte vzorec ukázat na vrstvu. Připojeno plus neúspěšný test trasy naznačuje rozdělený tunel, DNS nebo politiku. Odpojeno plus fungující test trasy znamená, že provoz nese jiná cesta.
Test, který můžete spustit popořadě
Nejprve zaznamenejte stav platformy, než změníte jakýkoli stav sítě. Přeložte jméno hostitele a poznamenejte rodinu adres, protože záznam AAAA může jít jinou cestou než záznam A. Otevřete port služby a žádejte odpověď aplikace, ne holý handshake. Každé pozorování držte ve vlastním poli logu.
Na Linuxu s dig a curl pokrývají tři příkazy překlad, trasu i samotnou službu. Spusťte je s tunelem nahoru a znovu s tunelem dole:
dig +short intranet.example.test
ip route get 198.51.100.20
curl -sS -o /dev/null -w "%{http_code}" --max-time 8 https://intranet.example.test/health
Čtyři samostatná pole porážejí jeden boolean, protože stav, DNS, trasa a politika selhávají nezávisle a padají na různé týmy. Ping v terminálu zůstává dobrá ruční kontrola. Je to ale slabá definice připojení pro automatizaci, kde na skutečnou otázku odpovídá API platformy a test trasy.