Tarvitset yhden näkymän, joka käyttäytyy toisin, kun tunneli on päällä, eikä ole kutsua, joka kertoisi sen sinulle. Se on julkaisun rajoite: macOS:ssä mikään julkinen kehys ei raportoi, onko mielivaltainen VPN yhdistetty, ja iOS:ssä tila kuuluu sovellukselle, joka asensi määrityksen. Alla olevat tarkistukset kulkevat tästä rajasta johonkin, jonka voit julkaista, ja mikä tahansa niistä voi päättää etsinnän aikaisin.

Tarkistus 1: voiko kysymykseen ylipäätään vastata?

Sandbox ratkaisee kysymyksen ennen kuin mikään API ehtii. Kolmannen osapuolen prosessi ei voi luetella toisen toimittajan laajennusta eikä lukea sen laajennuksen määritystä, joten kysyttävää tuettua oliota ei ole.

Jokainen kiertotie törmää samaan seinään. Liittymäluettelot, scutil --nc list ja suorat järjestelmämäärityksen luennot joko vaativat oikeuksia, jotka sandbox pidättää, tai riippuvat käyttäytymisestä, jota Apple ei koskaan luvannut. Jos suunnitelma tarvitsee jonkin näistä, ongelma on suunnitelmassa. Dokumentoimattomaan yksityiskohtaan rakennettu ominaisuus on tukipyyntö, jolla on toimituspäivä.

Tarkistus 2: hallitseeko sovelluksesi tunnelia itse?

Jos hallitsee, sinulla on tuettu vastaus omaan määritykseesi. Lataa asetukset, käsittele virhe, lue sitten tila ja tilaa muutokset sen sijaan että kyselisit:

vpnManager.loadFromPreferences { error in
    // handle a load failure before reading status
}

NotificationCenter.default.addObserver(
    forName: .NEVPNStatusDidChange,
    object: nil,
    queue: nil
) { note in
    let status = (note.object as? NEVPNConnection)?.status
}

Ole täsmällinen siitä, mitä tämä palauttaa: asentamasi tunnelin tila. Toista asiakasohjelmaa käyttävä käyttäjä näkyy irrotettuna, eikä se ole virhe koodissasi. Päätä, kumpaa näistä kahdesta kysymyksestä ominaisuutesi oikeasti kysyy, ennen kuin rakennat vastauksen varaan.

Tarkistus 3: mitä heuristiikka oikeasti kertoisi sinulle?

Laajalti kopioitu lähestymistapa kysyy järjestelmän välityspalvelimen sanakirjalta sen rajattuja merkintöjä ja lukee avaimet, jotka sattuvat olemaan liittymänimiä:

let settings = CFNetworkCopySystemProxySettings()?.takeRetainedValue() as NSDictionary?
let scoped = settings?["__SCOPED__"] as? [String: Any]
let names = scoped?.keys ?? []

Avain, joka alkaa tap, tun, ppp, ipsec tai utun tarkoittaa, että tunnelin rajaama liittymä on läsnä. Koko nimen sovittaminen epäonnistuu heti, koska iOS 12 toi utun1:n ja utun2:n ja jotkin profiilit näkyvät muodossa ipsec4, ppp0 tai utun0. Vertaa sen sijaan etuliitteitä.

Siitä huolimatta nimi ei yksilöi omistajaa. Järjestelmäominaisuudet ja muiden toimittajien laajennukset luovat myös utun-liittymiä, ja sellainen voi olla olemassa kuljettamatta mitään liikennettäsi. Lue se vihjeeksi siitä, että lähellä on jotain tunnelin muotoista, ei enempää. Väärä positiivinen on täällä halpa, jos rajaat vain yhden ominaisuuden, ja kallis, jos rajaat kirjautumisnäkymän.

Tarkistus 4: voisitko sen sijaan testata kohdetta?

Jos sovellus tarvitsee vain tietää, onko sisäinen palvelu tavoitettavissa, testaa sitä palvelua. Lyhyt aikakatkaisulla varustettu kokeilu vastaa kysymykseen, josta ominaisuus oikeasti riippuu, ja se toimii edelleen, kun käyttäjä vaihtaa asiakasohjelmaa tai tunneli muuttaa muotoaan.

Tavoitettavuus on havainto reitistäsi. Liittymänimi on päätelmä jostakin reittisi vieressä olevasta, minkä vuoksi heuristiikka tuottaa väittelyitä virheraporteissa ja kokeilu tuottaa todisteita. Jos kokeilu epäonnistuu, kun käyttäjä väittää VPN:n olevan päällä, sinulla on nyt konkreettinen reitti virheenjäljitykseen: nimien selvitys, reitti tai palvelun käyttöoikeus.

Tarkistus 5: voiko alusta pakottaa sen, mitä tarvitset?

Kun vaatimus on tae siitä, ettei mikään karkaa tunnelista, profiili on oikea paikka, ei ilmaisin. includeAllNetworks päälle kytkeminen täystunnelin määrityksessä iOS 14:ssä tai uudemmassa muuttaa alustan käyttäytymistä sen sijaan, että sovelluksesi joutuisi päättelemään sen. Lippu on dokumentoitu NEVPNProtocol-viitteessä.

Se on erilainen vastaus: pakottaminen havainnoinnin sijaan. Se koskee myös vain profiileja, joita hallitset, joten siitä ei ole apua kuluttajasovellukselle, joka seuraa jonkun toisen tunnelia.

Tarkistus 6: tee epäonnistumisesta turvallinen ja havaittava

Kytke pois vain se kyvykkyys, joka tarvitsee tunnelin, ja jätä muu sovellus käyttökelpoiseksi. Ilmaisin, joka piilottaa koko käyttöliittymän aina epävarmana, valmistaa katkoksen jokaiselle, jonka tunneli käyttää nimeä, jota et koskaan odottanut. Palaa sen sijaan konservatiiviseen käyttäytymiseen: paikalliset ominaisuudet toimivat edelleen ja vain se etäkutsu, joka todella tarvitsee tunnelin, poistetaan käytöstä. Tämä valinta on tuotepäätös, ja se ansaitsee tulla kirjatuksi heuristiikan viereen.

Kirjaa, mitä havaitsit: liittymänimet, alustan version ja yhden kokeilun tuloksen. Se muuttaa seuraavan raportin väittelystä tarkistukseksi. Suosi sitten tuettua julistusta, kun sinulla on sellainen, koska hallittu määritys voi kantaa aikomuksen eksplisiittisesti ja poistaa suurimman osan syystä tutkia nimiä lainkaan.

Jos tarkistukset 1–5 jättivät sinut ilman tuettua vastausta, julkaise kokeilu ja nimeä tulos rehellisesti. Dokumentoitu parhaan yrityksen signaali on parempi tuotepäätös kuin yksityinen API, joka hajoaa seuraavassa julkaisussa.

Aiheeseen liittyvät artikkelit