Du trycker på VPN-raden i Inställningar, ser en profil som någon annan har installerat och börjar leta efter anropet som lägger till en. Det finns inget sådant anrop. En app kan öppna sin egen tunnel via VpnService, men posterna i listan tillhör plattformen och den klient som skapade dem. Att veta exakt var gränsen går sparar dig en vecka av jakt på dolda klasser.

Börja med det som skärmen Inställningar visar

VPN-listan är ett register över profiler som systemet eller en leverantörsklient har installerat: PPTP, L2TP/IPsec, IKEv2 och de rader som en OEM-app eller en MDM har skjutit in. Varje rad bär en serveradress, inloggningsuppgifter och en protokollimplementering som lever utanför din process. När användaren trycker på Anslut där är det plattformens klient som reser tunneln, inte din kod. Därför överlever raden en omstart, och därför tar avinstallationen av din app aldrig bort den.

Från användarens sida ser listan ut som en API-yta, en plats där det att lägga till en VPN borde vara en intent bort. Det är den inte. De enda offentliga ingångspunkterna som rör den är navigeringsintents, och allt som skriver till den tillhör plattformen eller en privilegierad komponent.

Praktisk konsekvens: om en supporttext säger åt användarna att lägga till profilen i Inställningar är din app inte en del av det flödet alls.

Vad VpnService faktiskt ger dig

VpnService och VpnService.Builder beskriver en tunnel som din app äger. Du lägger till adresser, rutter, DNS-servrar och en MTU, avgränsar trafiken med addAllowedApplication() eller addDisallowedApplication(), och sedan returnerar establish() en ParcelFileDescriptor för ett TUN-gränssnitt. Från den punkten läser appen IP-paket och skriver svar, vilket betyder att protokollet är ditt att implementera eller bädda in: OpenVPN, WireGuard, en egen transport.

Ingenting i den sekvensen talar PPTP, L2TP/IPsec eller IKEv2. Builder har ingen strömbrytare som säger använd systemets L2TP-klient, och det finns ingen callback som låter dig styra en profil som plattformen redan äger. Det är den verkliga gränsen, och det är en designgräns, inte ett hål i behörigheterna.

Så en app kan absolut vara en VPN-klient på Android. Den kan bara inte vara administratör för de klienter som följer med telefonen.

Samtyckesdialogen är inte dekoration

Eftersom din tunnel kan fånga andra appars trafik, kräver systemet att användaren godkänner den uttryckligen. prepare() returnerar ett Intent som du måste starta, godkännandet är knutet till ditt paket, och medan tunneln är uppe visar statusfältet en beständig indikator. En andra VPN som kommer upp inaktiverar den första, eftersom Android kör en aktiv VPN åt gången.

Den regeln om en aktiv får folk att snubbla i test. Du reser din tunnel medan en företagsklient är ansluten och drar slutsatsen att din kod är trasig, när plattformen bara bytte bort från den andra klienten. Godkännanden kan återkallas senare, och prepare() kan returnera null på enheter där samtyckesaktiviteten saknas, så establish() måste fortfarande hantera fel.

Dolda API:er och inställningsintents

Äldre svar pekar på com.android.internal-klasser och AIDL-gränssnitt som den inbyggda klienten använder. De finns inte i SDK:n, de ändras mellan versioner utan varsel och appbutiker ser den åtkomsten som en risk. Att roota enheten gör dem inte stabila heller, eftersom root och åtkomst till dolda API:er är oberoende problem.

Den stödda navigationshjälpen är Settings.ACTION_VPN_SETTINGS, vars värde är android.net.vpn.SETTINGS. Slå upp den innan du startar den, eftersom vissa OEM-byggen inte levererar den aktiviteten, och fall tillbaka på skrivna steg när uppslagningen misslyckas. Den leder användaren till skärmen och konfigurerar ingenting.

Enhetsägare- och MDM-vägar är undantaget folk oftast menar. DevicePolicyManager kan peka ut ett alltid-på VPN-paket, och hanterade konfigurationer kan förladda inställningar för en klient som stöder dem, men det är fortfarande inte den offentliga SDK:n som skriver en PPTP-profil.

Gå igenom beslutet från användarens sida

Om din produkt måste bära trafik, planera VpnService plus en riktig protokollstack, och budgetera tid för samtyckesflödet och regeln om en VPN. Om målet är att ansluta till en befintlig företagsprofil är ditt jobb vägledning: djup länk till inställningsskärmen, dokumentera fälten och låt plattformens klient göra tunnlingen. Om appen bara behöver nå en privat slutpunkt behöver den ingen egen tunnel alls.

Skriv ned det beslutet innan du skriver kod, eftersom de tre vägarna har nästan ingenting gemensamt efter den första sprinten.

En sista kontroll innan du börjar: säger kravet att vår app ansluter, eller att enheten ansluter? Det första är VpnService, det andra är en profil du inte kan skapa. Att få den meningen rätt är billigare än någon refaktorering.

Relaterade artiklar