Twee heel verschillende taken vallen onder de naam programmatische VPN, en slechts één ervan is beschikbaar voor een gewone app op een van de twee mobiele platforms. De eerste is een profiel aanzetten dat de gebruiker al heeft opgeslagen; de tweede is een tunnel bouwen binnen je eigen proces. Android geeft je de tweede via VpnService en iOS geeft je de tweede via het recht Network Extension, terwijl de eerste bij het systeem, een apparaateigenaar of een MDM-server blijft. Uitzoeken welke je echt nodig hebt maakt het project meestal kleiner.

Twee taken met dezelfde naam

Een opgeslagen profiel activeren betekent tegen een bestaande tunnel zeggen dat hij omhoog moet: een host, een inloggegeven, een protocol, alles al geconfigureerd op een plek die de gebruiker kan zien. Een tunnel bouwen betekent dat je code de interface, de pakketlus en het protocol bezit. Ze lijken op elkaar in een productbacklog en delen bijna geen implementatie.

Geen van beide mobiele platforms stelt de eerste open voor een SDK-app. Een verbinding die verschijnt zonder dat de gebruiker iets doet, is niet te onderscheiden van malware, dus zetten beide systemen een toestemmingspoort voor elke app die verkeer draagt.

Android: een toestemmingspoort en geen profiel-API

VpnService bestaat sinds Android 4.0 en laat een app een tun-interface maken en vervolgens pakketten lezen en schrijven. De dienst moet worden gedeclareerd met BIND_VPN_SERVICE, en VpnService.prepare() maakt de systeemdialoog die de gebruiker om toestemming vraagt. Het platformvoorbeeld ToyVpn is de duidelijkste uitspraak over de bedoelde vorm: je code bezit de interface en alles wat erdoorheen stroomt.

Wat het niet doet, is een vermelding toevoegen aan het VPN-instellingenscherm van het systeem. Daar is geen openbare API voor, en de app Instellingen houdt zijn profielen in een opslag die een gewone app niet kan bereiken. Aanroepen van de verborgen klassen vanuit een normale toepassing leveren profielen op die het systeem nooit vermeldt, waardoor code die in de ene build leek te werken in de volgende stil stopt.

Het beheerde pad is apart. Een apparaat- of profieleigenaar kan een altijd aanstaand VPN-pakket aanwijzen via de apparaatbeleid-API's, en een bedrijfshulpmiddel kan een profiel pushen dat de gebruiker daarna goedkeurt. Dat is bevoegdheid voor apparaatbeheer, geen toestemming die een app bij installatie vraagt. Als je klant een organisatie is, is dit het pad waarvoor je moet plannen; als je klant iemand is die uit een winkel installeert, is het helemaal niet beschikbaar.

iOS: het recht is de grens

iOS verdeelt hetzelfde werk anders. Een VPN-client implementeert een pakkettunnelprovider of een app-proxy binnen het Network Extension-framework, en het bijbehorende recht moet aan het ontwikkelaarsaccount worden toegekend. Een persoonlijke VPN-configuratie via NEVPNManager bestaat voor het eenvoudiger geval, en draait nog steeds binnen hetzelfde toestemmingsmodel. Apple documenteert het hele oppervlak in de Network Extension-referentie, die het lezen waard is voordat je het werk afbakent.

Er is geen ondersteunde manier om het VPN-instellingenscherm te openen, de opgeslagen configuraties van de gebruiker te lezen of er een te starten. Wat een client kan doen, is een configuratieprofiel leveren dat de gebruiker installeert, en dan de resulterende tunnel gebruiken via gewone netwerkaanroepen. Tunneling per app wordt toegewezen door een MDM-server via een on-demand-regel, niet door de app gekozen tijdens runtime.

Een VPN-client van een grote leverancier is geen bewijs dat jouw account hetzelfde kan leveren. Die rechten worden per ontwikkelaarsaccount aangevraagd en beoordeeld, dus het planningsrisico ligt bij Apple, niet bij je sprintplan.

De desktop reikt verder, maar eigenaarschap blijft gelijk

Windows is het toestemmende geval. Add-VpnConnection maakt een telefoonboekvermelding vanuit een verhoogde PowerShell-sessie, en rasdial verbindt of verbreekt die vanuit een script. Een app kan ook een leveranciersclient aansturen via de gedocumenteerde commandoregel. Het profiel aanmaken blijft een administratieve handeling, omdat de vermelding in een opslag voor de hele machine staat.

macOS gedraagt zich hetzelfde met andere hulpmiddelen. scutil --nc start en stop werken op diensten die al bestaan, terwijl er een aanmaken een systeembeheertaak is. Het proces op een laptop bezitten maakt je geen eigenaar van de configuratie.

Wat je in plaats daarvan moet bouwen

Als de echte eis is dat je app een interne API bereikt, is de tunnel die de gebruiker al draait genoeg. Doe gewone HTTPS-verzoeken, laat het systeem het pad kiezen, en stop met proberen de tunnel te beheersen. Als de eis is dat alleen het verkeer van je app de tunnel gebruikt, vraag dan om VPN per app via het beheerkanaal, of beëindig TLS in de app tegen een dienst die zonder bereikbaar is.

Verborgen API's zijn geen snelweg die het waard is. Ze veranderen tussen releases, ze falen bij de app-beoordeling, en de fouten die ze veroorzaken zien er voor wie de code erft uit als gewone netwerkfouten. De vergelijking is niet Android tegen iOS; het is een tunnel bezitten tegen het platform vragen verkeer te routeren, en alleen het eerste is aan jou om te bouwen.

Gerelateerde artikelen